Documentación de Laravel 10.x
Aquí encontrarás fragmentos de código de Laravel y consejos útiles sobre desarrollo web.
A lo largo de la documentación de Laravel, verás ejemplos de código que interactúan con las funciones de Laravel a través de "fachadas". Las fachadas proporcionan una interfaz "estática" a las clases disponibles en el contenedor de servicios de la aplicación. Laravel incluye muchas fachadas que brindan acceso a casi todas las características de Laravel.
Las fachadas de Laravel sirven como "proxies estáticos" para clases subyacentes en el contenedor de servicios, proporcionando la ventaja de una sintaxis concisa y expresiva, manteniendo al mismo tiempo más testabilidad y flexibilidad que los métodos estáticos tradicionales. Está perfectamente bien si no comprendes completamente cómo funcionan las fachadas; simplemente sigue adelante y continúa aprendiendo sobre Laravel.
Todas las fachadas de Laravel están definidas en el espacio de nombres Illuminate\Support\Facades
. Entonces, podemos acceder fácilmente a una fachada de la siguiente manera:
use Illuminate\Support\Facades\Cache;use Illuminate\Support\Facades\Route; Route::get('/cache', function () { return Cache::get('key');});
A lo largo de la documentación de Laravel, muchos de los ejemplos utilizarán fachadas para demostrar varias características del framework.
Para complementar las fachadas, Laravel ofrece una variedad de "funciones de ayuda" globales que facilitan aún más la interacción con funciones comunes de Laravel. Algunas de las funciones de ayuda comunes con las que puedes interactuar son view
, response
, url
, config
y más. Cada función de ayuda ofrecida por Laravel está documentada con su función correspondiente; sin embargo, hay una lista completa disponible en la documentación dedicada de funciones de ayuda.
Por ejemplo, en lugar de usar la fachada Illuminate\Support\Facades\Response
para generar una respuesta JSON, simplemente podemos usar la función response
. Debido a que las funciones de ayuda están disponibles globalmente, no es necesario importar ninguna clase para usarlas:
use Illuminate\Support\Facades\Response; Route::get('/users', function () { return Response::json([ // ... ]);}); Route::get('/users', function () { return response()->json([ // ... ]);});
Las fachadas tienen muchos beneficios. Proporcionan una sintaxis concisa y memorable que te permite utilizar las características de Laravel sin recordar nombres largos de clases que deban ser inyectados o configurados manualmente. Además, debido a su uso único de los métodos dinámicos de PHP, son fáciles de probar.
Sin embargo, debes tener cuidado al usar fachadas. El peligro principal de las fachadas es la "expansión de alcance" de la clase. Dado que las fachadas son tan fáciles de usar y no requieren inyección, puede ser fácil dejar que tus clases continúen creciendo y usar muchas fachadas en una sola clase. Al utilizar la inyección de dependencias, este potencial se mitiga mediante la retroalimentación visual que te da un constructor grande, indicando que tu clase está creciendo demasiado. Así que, al usar fachadas, presta especial atención al tamaño de tu clase para que su alcance de responsabilidad se mantenga estrecho. Si tu clase está creciendo demasiado, considera dividirla en varias clases más pequeñas.
Uno de los principales beneficios de la inyección de dependencias es la capacidad de intercambiar implementaciones de la clase inyectada. Esto es útil durante las pruebas, ya que puedes inyectar un objeto simulado o de prueba y afirmar que se llamaron varios métodos en la simulación.
Normalmente, no sería posible simular o poner en espera un método de clase verdaderamente estático. Sin embargo, dado que las fachadas utilizan métodos dinámicos para enviar llamadas de método a objetos resueltos del contenedor de servicios, realmente podemos probar las fachadas de la misma manera que probaríamos una instancia de clase inyectada. Por ejemplo, dada la siguiente ruta:
use Illuminate\Support\Facades\Cache; Route::get('/cache', function () { return Cache::get('key');});
Usando los métodos de prueba de fachadas de Laravel, podemos escribir la siguiente prueba para verificar que el método Cache::get
fue llamado con el argumento que esperábamos:
use Illuminate\Support\Facades\Cache; /** * Un ejemplo básico de prueba funcional. */public function test_basic_example(): void{ Cache::shouldReceive('get') ->with('key') ->andReturn('value'); $response = $this->get('/cache'); $response->assertSee('value');}
Además de las fachadas, Laravel incluye una variedad de funciones de "ayuda" que pueden realizar tareas comunes como generar vistas, disparar eventos, despachar trabajos o enviar respuestas HTTP. Muchas de estas funciones de ayuda realizan la misma función que una fachada correspondiente. Por ejemplo, esta llamada de fachada y llamada de ayuda son equivalentes:
return Illuminate\Support\Facades\View::make('profile'); return view('profile');
No hay absolutamente ninguna diferencia práctica entre las fachadas y las funciones de ayuda. Al usar funciones de ayuda, aún puedes probarlas exactamente de la misma manera que lo harías con la fachada correspondiente. Por ejemplo, dada la siguiente ruta:
Route::get('/cache', function () { return cache('key');});
El ayudante cache
llamará al método get
en la clase subyacente de la fachada Cache
. Entonces, aunque estemos usando la función de ayuda, podemos escribir la siguiente prueba para verificar que el método fue llamado con el argumento que esperábamos:
use Illuminate\Support\Facades\Cache; /** * Un ejemplo básico de prueba funcional. */public function test_basic_example(): void{ Cache::shouldReceive('get') ->with('key') ->andReturn('value'); $response = $this->get('/cache'); $response->assertSee('value');}
En una aplicación Laravel, una fachada es una clase que proporciona acceso a un objeto desde el contenedor. La maquinaria que hace esto posible está en la clase Facade
. Las fachadas de Laravel, y cualquier fachada personalizada que crees, extenderán la clase base Illuminate\Support\Facades\Facade
.
La clase base Facade
utiliza el método mágico __callStatic()
para diferir las llamadas desde tu fachada a un objeto resuelto del contenedor. En el siguiente ejemplo, se realiza una llamada al sistema de caché de Laravel. Al mirar este código, uno podría suponer que se está llamando al método estático get
en la clase Cache
:
<?php namespace App\Http\Controllers; use App\Http\Controllers\Controller;use Illuminate\Support\Facades\Cache;use Illuminate\View\View; class UserController extends Controller{ /** * Mostrar el perfil del usuario proporcionado. */ public function showProfile(string $id): View { $user = Cache::get('user:'.$id); return view('profile', ['user' => $user]); }}
Observa que cerca del inicio del archivo estamos "importando" la fachada Cache
. Esta fachada sirve como un proxy para acceder a la implementación subyacente de la interfaz Illuminate\Contracts\Cache\Factory
. Cualquier llamada que hagamos utilizando la fachada se pasará a la instancia subyacente del servicio de caché de Laravel.
Si observamos la clase Illuminate\Support\Facades\Cache
, verás que no hay un método estático get
:
class Cache extends Facade{ /** * Obtener el nombre registrado del componente. */ protected static function getFacadeAccessor(): string { return 'cache'; }}
En cambio, la fachada Cache
extiende la clase base Facade
y define el método getFacadeAccessor()
. La tarea de este método es devolver el nombre de un enlace del contenedor de servicios. Cuando un usuario referencia cualquier método estático en la fachada Cache
, Laravel resuelve el enlace cache
del contenedor de servicios y ejecuta el método solicitado (en este caso, get
) contra ese objeto.
Usando fachadas en tiempo real, puedes tratar cualquier clase en tu aplicación como si fuera una fachada. Para ilustrar cómo se puede usar esto, examinemos primero un código que no utiliza fachadas en tiempo real. Por ejemplo, supongamos que nuestro modelo Podcast
tiene un método publish
. Sin embargo, para publicar el podcast, necesitamos inyectar una instancia de Publisher
:
<?php namespace App\Models; use App\Contracts\Publisher;use Illuminate\Database\Eloquent\Model; class Podcast extends Model{ /** * Publicar el podcast. */ public function publish(Publisher $publisher): void { $this->update(['publishing' => now()]); $publisher->publish($this); }}
Inyectar una implementación de publisher en el método nos permite probar fácilmente el método de forma aislada, ya que podemos simular el publisher inyectado. Sin embargo, nos obliga a pasar siempre una instancia de publisher cada vez que llamamos al método publish
. Usando fachadas en tiempo real, podemos mantener la misma capacidad de prueba sin tener que pasar explícitamente una instancia de Publisher
. Para generar una fachada en tiempo real, agrega el espacio de nombres de la clase importada con el prefijo Facades
:
<?php namespace App\Models; use App\Contracts\Publisher; use Facades\App\Contracts\Publisher; use Illuminate\Database\Eloquent\Model; class Podcast extends Model{ /** * Publicar el podcast. */ public function publish(Publisher $publisher): void public function publish(): void { $this->update(['publishing' => now()]); $publisher->publish($this); Publisher::publish($this); }}
Cuando se utiliza la fachada en tiempo real, la implementación del publisher se resolverá del contenedor de servicios utilizando la parte de la interfaz o el nombre de la clase que aparece después del prefijo Facades
. Al realizar pruebas, podemos usar las funciones de prueba de fachadas integradas en Laravel para simular esta llamada al método:
<?php namespace Tests\Feature; use App\Models\Podcast;use Facades\App\Contracts\Publisher;use Illuminate\Foundation\Testing\RefreshDatabase;use Tests\TestCase; class PodcastTest extends TestCase{ use RefreshDatabase; /** * Un ejemplo de prueba. */ public function test_podcast_can_be_published(): void { $podcast = Podcast::factory()->create(); Publisher::shouldReceive('publish')->once()->with($podcast); $podcast->publish(); }}
A continuación, encontrarás cada fachada y su clase subyacente. Esta es una herramienta útil para explorar rápidamente la documentación de la API para una fachada específica. También se incluye la clave de enlace del contenedor de servicios cuando sea aplicable.