接下来这篇文章是以tp5.1重构参数校验层为基础的。没看过一定要去看看。
tp5.1重构参数校验层
比如,我们需要创建一个用户,则需要对用户名,密码、邮箱等参数进行校验,所以先创建个User验证器。代码如下:
<?php
namespace app\validate;
class User extends Base
{
protected $rule = [
'username' =>'require',
'password' => 'require',
'email' => 'require'
];
protected $message = [
'username' => '用户名不能为空',
'password' => '密码不能为空',
'email' => '邮箱不能为空',
];
}
在User控制器中,代码如下:
public function save($username,$password,$email)
{
(new User())->goCheck();
//验证通过后,写业务代码
}
这是创建用户时所需要验证的参数,但如果是用户登录呢?用户登录只需要username,password两个字段,不需要email。刚才写的验证器就无法使用了。TP5官方提供了一个方法来解决这个问题,就是在验证器中添加验证场景。将验证器User代码改为:
<?php
namespace app\validate;
class User extends Base
{
protected $rule = [
'username' =>'require',
'password' => 'require',
'email' => 'require'
];
protected $message = [
'username' => '用户名不能为空',
'password' => '密码不能为空',
'email' => '邮箱不能为空',
];
//这里就是通过不同的场景,来使用不同的验证规则
protected $scene = [
'save' => ['username','passowrd','email'],
'login' =>['username','password'],
];
}
所以控制器User中,save方法的代码改为:
public function save($username,$password,$email)
{
(new User())->scene('save')->goCheck();
//验证通过后,写业务代码
}
登录自然就很容易能想到:
public function login($username,$password)
{
(new User())->scene('login')->goCheck();
//验证通过后,写业务代码
}
但随着User业务的增多,每次进行参数校验时,都需要在该方法第一行写上:(new User())->scene('场景')->goCheck();
,这样就比较麻烦了。所以中间件就是来解决这些问题的。中间件可以在每个方法执行先,先执行中间件的代码,类似前置操作。
这里我们创建一个Validate中间件:
php think make:middleware Validate
中间件代码如下:
<?php
namespace app\http\middleware;
class Validate
{
public function handle($request, \Closure $next)
{
$moduleName = '\app\validate\\' . ucfirst($request->module()); //根据路由来获取相对应的module名称
$action = $request->action(); //根据路由获取对应的方法
$validate = new $moduleName();
if($validate->hasScene($action)){ //判断验证器是否有该方法的验证场景
$validate ->scene($action)->goCheck();
}
return $next($request);
}
}
如何使用中间件呢?官方给我们提供了几个方法,这里我就使用其中一种方法来注册中间件,首先你的控制器需要继承系统的think\Controller类,然后在控制器中定义middleware属性,例如:
<?php
namespace app\index\controller;
use think\Controller;
class User extends Controller
{
protected $middleware = ['Validate'];
}
当然中间件还有更多的使用方法,建议去官方手册了解。
这样就能自动完成User控制器的参数校验了。
比如User中,update方法需要验证Username
则在User验证器中,添加update的验证场景即可,即:
<?php
namespace app\validate;
class User extends Base
{
protected $rule = [
'username' =>'require',
'password' => 'require',
'email' => 'require'
];
protected $message = [
'username' => '用户名不能为空',
'password' => '密码不能为空',
'email' => '邮箱不能为空',
];
//这里就是通过不同的场景,来使用不同的验证规则
protected $scene = [
'save' => ['username','passowrd','email'],
'login' =>['username','password'],
'update' =>['username']
];
}
User控制器中,update方法:
public function update($username)
{
//这里无需关心username的参数验证,中间件自动帮你完成参数的校验了
//直接可以写业务代码
}
当然不止User控制器能实现,所有验证器都可以,只需要建立相对应的验证器,然后在此验证器中添加相对应的验证字段,验证规则,验证场景即可