中间件&&服务&&门面
中间件
6.x版本提供了中间件,分别为系统中间件和应用中间,系统中间件为核心框架内置的中间件,应用中间件是在应用里面创建的中间件。
中间件的主要应用场景可以包括对HTTP请求的数据过滤、权限检测、请求拦截等行为,使用中间件能够让控制器的定义更加简单,
很多额外的非核心业务流程的处理都可以交给中间件执行
通过指令快速创建中间件
# 单应用模式创建中间件 这个指令会在app/middleware目录下生成一个Test中间件
php think make:middleware Test
# 多应用模式创建中间件 这个指令会在app/index/middleware目录下生成一个Test中间件
php think make:middleware index@Test
中间件的入口执行方法必须是handle方法,而且第一个参数是Request对象,第二个参数是一个闭包
基础实例(登录前置中间件)
通过中间件检测是否登录
app\index\controller\Index.php
<?php
namespace app\index\controller;
class Index
{
public function index()
{
return '您好!这是一个[index]示例应用';
}
public function login()
{
return '这是login的方法';
}
}
注意:中间件handle方法的返回值必须是一个Response对象。
接下通过指令创建一个Auth
的中间件,注意:这里是多应用模式
,代码如下
app\index\middleware\Auth.php
<?php
namespace app\index\middleware;
class Auth
{
/**
* 处理请求
*
* @param \think\Request $request
* @param \Closure $next
* @return Response
*/
public function handle($request, \Closure $next)
{
// 判断session是否存在,并且同时判断访问的地址是否为index/login
if(empty(session('LoginUser')) && !preg_match('/index\/login/',$request->pathinfo()))
{
// 如果条件成立,则重定向回登录页面
return redirect((string)url('index/index/login'));
}
// 返回Request对象
return $next($request);
}
}
写完Auth
中间件的代码,还差一个步骤,就是要注册中间件。由于这里是多应用模式,则是应用中间件定义,你可以找到在应用目录下面middleware.php
文件,定义方式和全局中间件定义一样,只是只会在该应用下面生效。
app\index\middleware.php
,
<?php
// 这是系统自动生成的middleware定义文件
return [
// 注册Auth中间件
app\index\middleware\Auth::class
];
中间件别名
在config\middleware.php
配置中间件别名
<?php
// 中间件配置
return [
// 别名或分组
'alias' => [
'Auth' => app\index\middleware\Auth::class
],
// 优先级设置,此数组中的中间件会按照数组中的顺序优先执行
'priority' => [],
];
如果Auth
中间件只对index
应用生效,那么在app\index\middleware.php
配置
<?php
// 这是系统自动生成的middleware定义文件
return [
'Auth'
];
中间件优先级
全局中间件->应用中间件->路由中间件->控制器中间件
服务
系统服务的概念是指在执行框架的某些组件或者功能的时候需要依赖的一些基础服务,服务类通常可以继承系统的think\Service
类,但并不强制(如果继承think\Service
)的话可以直接调用$this->app
获取应用实例。
你可以在系统服务中注册一个对象到容器,或者对某些对象进行相关的依赖注入。由于系统服务的执行优先级问题,可以确保相关组件在执行的时候已经完成相关依赖注入
内置服务
为了更好的完成核心组件的单元测试,框架内置了一些系统服务类,主要都是用于核心类的依赖注入,包括ModelService
、PaginatorService
和ValidateService
类。这些服务不需要注册,并且也不能卸载。
门面(
Facade
)
门面为容器中的(动态)类提供了一个静态调用接口,相比于传统的静态方法调用,带来了更好的可测试的扩展性,你可以为任何的非静态类库定义一个facade
类。
系统已经为大部分核心类库定义了Facade
,所以你可以通过Facade
来访问这些系统类,当然也可以为你的应用类库添加静态代理。系统给内置的常用类库定义了Facade类库,包括:
(动态)类库 | Facade类 |
---|---|
think\App | think\facade\App |
think\Cache | think\facade\Cache |
think\Config | think\facade\Config |
think\Cookie | think\facade\Cookie |
think\Db | think\facade\Db |
think\Env | think\facade\Env |
think\Event | think\facade\Event |
think\Filesystem | think\facade\Filesystem |
think\Lang | think\facade\Lang |
think\Log | think\facade\Log |
think\Middleware | think\facade\Middleware |
think\Request | think\facade\Request |
think\Route | think\facade\Route |
think\Session | think\facade\Session |
think\Validate | think\facade\Validate |
think\View | think\facade\View |
所以你无需进行实例化就可以很方便的进行方法调用,例如:
use think\facade\Cache;
// 设置值
Cache::set('name','value');
// 获取值
echo Cache::get('name');