middleware在代码执行顺序中,主要位于路由调度与控制器之间,类似于preAction()。middleware在目录结构中说了,位于app/Http/Middleware/目录下,比如librenms中有个middleware是CheckInstalled,关键代码如下:<?phpnamespace AppHttpMiddleware;use Closure;class CheckInstalled{/** * Handle an incoming request. * @param IlluminateHttpRequest $request * @param Closure $next * @return mixed */ public function handle($request, Closure $next){ if (!file_exists(base_path('config.php')) && !$request->is('install.php')) {return redirect(url('/install.php')); //重定向 } return $next($request); //传给下一个中间件 }}
容器
laravel容器一般这样初始化:$app = new IlluminateFoundationApplication( dirname(__DIR__));服务绑定与解析,有如下的方法:$this->app->bind('service1', function(){ return new Service1();}); //绑定注册service1$ser1 = $this->app->make('service1'); //解析service1服务,创建service1 class实例$this->app->singleton('service2', function(){ return new Service2();}); //单例模式绑定service2$ser2 = $this->app->make('service2'); //程序中无论调用多少次make(),都只有一个service2 class实例。
Provider
provider有两种,一种是service provider,服务提供者,用于将服务绑定到容器上。还有一种是普通provider,这类provider一般可能是为了其他组件服务的,比如service provider、guard等。laravel提供了这类的provider接口,比如laravel/framework/src/Illuminate/Contracts/Auth/UserProvider.php,开发者可以选择实现这个接口,然后来实现自己的功能,从接口定义的方法就可以看出来这个provider的用法。<?phpnamespace IlluminateContractsAuth;interface UserProvider{ public function retrieveById($identifier); public function retrieveByToken($identifier, $token); public function updateRememberToken(Authenticatable $user, $token); public function retrieveByCredentials(array $credentials); public function validateCredentials(Authenticatable $user, array $credentials);}而对于第一种的服务提供者,命名格式通常为xxxServiceProvider.php,另一类provider格式通常为xxProvider.php。服务提供者在config/app.php中被providers列表加载。服务提供者用于将一个类/实例....绑定到容器上,也就是上面说的bind()、singleton()等方法。服务提供者主要是为了依赖注入而存在的。看如下控制器代码:<?phpnamespace AppHttpControllers;class Test222{ public $name; public function __construct() { $this->name = 'kkk'; }}class Test111{ public $app; public function __construct(Test222 $app) { $this->app = $app; }}class test1 extends Controller{ public function hello2(){ app()->bind(Test222::class);//注册Test222 app()->bind(Test111::class);//注册Test111 $aa = app()->make(Test111::class);//解析Test111 var_dump($aa); }}访问这个控制器这里在实例化Test111时,由于其中有对Test222的依赖,laravel会去寻找注册的名为Test222的服务名,也就是前面bind()/singleton()等方法绑定的服务。最终使用app()->make()来获取一个Test111实例,而未手动传入任何参数比如new Test111(new Test222());。
评论