Php 中间件之前的laravel formrequest
我知道,这是一个复杂的案例,但也许你们中的一位可能有办法做到这一点 概念 我的API中有以下过程:Php 中间件之前的laravel formrequest,php,laravel,laravel-middleware,laravel-authentication,laravel-formrequest,Php,Laravel,Laravel Middleware,Laravel Authentication,Laravel Formrequest,我知道,这是一个复杂的案例,但也许你们中的一位可能有办法做到这一点 概念 我的API中有以下过程: 处理查询字符串参数(FormRequest) 用首选键替换键别名 如果需要数组,则将字符串参数映射到数组 为基于id的参数设置默认值(包括Auth::user()) 等等 检查是否允许用户执行请求(中间件) 使用已处理(验证和消毒)的查询参数 → 否则,我必须为每个可能的别名和映射执行异常,并检查参数是否已检查,这对我来说似乎不合理 问题 然而,如果您只是通过->middleware(
FormRequest
)
- 用首选键替换键别名
- 如果需要数组,则将字符串参数映射到数组
- 为基于
的参数设置默认值(包括id
)Auth::user()
- 等等
中间件
)
- 使用已处理(验证和消毒)的查询参数 → 否则,我必须为每个可能的别名和映射执行异常,并检查参数是否已检查,这对我来说似乎不合理
->middleware('middlewareName')
将中间件分配给路由,并通过控制器方法的依赖注入将FormRequest分配给路由,那么首先调用中间件,然后调用FormRequest。如上所述,这不是我需要的
解决方法
我第一次在中间件上尝试依赖注入,但没有成功
我的解决方案是在控制器构造函数中分配中间件。依赖项注入在这里工作,但突然Auth::user()
返回null
然后,我在\lightlight\Foundation\Providers\FormRequestServiceProvider.php:34中遇到了FormRequest::createFrom($request)
方法以及将$request
对象传递给中间件的handle()
方法的可能性。结果如下所示:
public function\u构造(请求$Request)
{
$middleware=新的MyMiddleware();
$request=MyRequest::createFrom($request);
$middleware->handle($request,function(){})
}
但是现在请求还没有得到验证。只需调用$request->validated()
不会返回任何结果。因此,我进一步挖掘,发现$resolved->validateResolved()
是在\lightlight\Foundation\Providers\FormRequestServiceProvider.php:30
中完成的,但这似乎不会触发验证,因为它会抛出一个异常,表示无法在null
上调用此方法,但$request不是null
:
对null上的成员函数validated()的调用
现在,我完全被难倒了。有人知道如何解决这个问题吗?还是我做错了
提前谢谢 我想,我找到了更好的方法
我的误解
当中间件执行身份验证时,我在那里执行授权,因此我必须使用门
结果代码
控制器
。。。
公共函数getData(MyRequest$request)
{
$filters=$request->query();
//执行查询
}
...
格式请求
类MyRequest扩展了FormRequest
{
/**
*确定用户是否有权提出此请求。
*
*@returnbool
*/
公共职能授权()
{
返回门::允许('get-data',$this);
}
/**
*获取应用于请求的验证规则。
*
*@return数组
*/
公共职能规则()
{
返回[
// ...
];
}
/**
*为验证准备数据。
*
*@返回无效
*/
受保护函数prepareForValidation()
{
$this->replace($this->cleanQueryParameters($this->query());
}
私有函数cleanQueryParameters($queryParams):数组
{
$queryParams=array\u filter($queryParams,function($param){
返回为数组($param)?计数($param):strlen($param);
});
$defaultStartDate=(new\DateTime())->modify('monday nextweek');
$defaultEndDate=(new\DateTime())->modify('friday nextweek');
$defaults=[
'article.created_by_id'=>self::getDefaultEmployeeIds(),
'date_from'=>$defaultStartDate->格式('Y-m-d'),
'date_to'=>$defaultEndDate->格式('Y-m-d')
];
$Alias=[
// ...
];
$mapper=[
// ...
];
foreach($alias=>$key的别名){
如果(数组\键\存在($alias,$queryParams)){
$queryParams[$key]=$queryParams[$alias];
未设置($queryParams[$alias]);
}
}
foreach($key=>$fn的映射器){
如果(数组\键\存在($key,$queryParams)){
$fn($queryParams,$key);
}
}
$allowedFilters=数组\合并(
票证::$AllowedApipParameters,
数组映射(函数(字符串$param){
返回“物品”。$param;
},tickettarticle::$allowedApiParameters)
);
$arrayProps=[
// ..
];
foreach($queryParams作为$param=>$value){
如果(!in_数组($param,$allowedFilters)&&!in_数组($param,['date_from','date_to'])){
中止(400,“筛选器”.$param.“未找到”);
}
if(在数组($param,$arrayProps)中){
$queryParams[$param]=保证('array',$value);
}
}
返回数组合并($defaults,$queryParams);
}
}
大门
classmygate
{
/**
*处理传入的请求。
*
*@param\light\Http\Request$Request
*@return\light\Auth\Access\Response | Void
*@throws\Symfony\Component\HttpKernel\Exception\HttpException
*/
公共函数authorizeGetDataCall(用户$User,MyRequest$request):响应
{
日志::信息(“[MyGate]检查权限…”);
if(在_数组中(LDAPGroups::Admin,session('PermissionGroups',[])){
//不需要进一步检查
日志::信息('[MyGate]用户是管理员。无需进一步说明