在我使用多个中间件的时候。全局中间件使用的是跨域中间件,然后针对登录验证使用了路由中间件,中间件判断用户登录成功以后获取了redis里面的存储的用户信息,然后通过
$request->userData = Token::getAuthData($token);
return $next($request);
对控制器传了参数,但是这时候前端通过api请求对应的路由就会出现跨域的问题,针对这个问题是如何解决好呢?属于bug还是属于代码层面需要优化呢?
注:只有走了这个登录中间件的才会出现跨域问题,若不走登录中间件的路由则不会出现跨域问题。
跨域中间件代码:
public function process(Request $request, callable $next): Response
{
$response = $request->method() == 'OPTIONS' ? response('') : $next($request);
$response->withHeaders([
'Access-Control-Allow-Origin' => '*',
'Access-Control-Allow-Methods' =>'GET,POST,PUT,DELETE,OPTIONS',
'Access-Control-Allow-Headers' => 'Content-Type,Authorization,X-Requested-With,Accept,Origin,Referer,User-Agent,token'
]);
return $response;
}
估计是传参导致出错了,所以才报跨域问题的,自己仔细调试检查下吧. 还有中间件的执行顺序问题导致的错误,确定是不是先执行的跨域中间件再到验证中间件
并没有 本地测试使用postman请求并没有问题。线上使用postman请求也没有问题。可以获取到参数。文档里面也有注明执行顺序为:
中间件执行顺序为全局中间件->应用中间件->路由中间件。
当我把$request->userData = Token::getAuthData($token);这行代码注释掉的时候,api接口请求是ok的 也没有跨域问题。
那你改成 $request->userData =1;你看看会不会还跑不下去呀
改为1...可以跑下去。。。。。但是不应该呀,我里面加了判断,若key不存在或者没有数据的话 会抛出异常的来着。。。
说明就是代码层面的错误,一个可能是调用报错,还有一个可能是执行顺序问题,如果option请求也访问到了那里,是不是会报错呢?如果报错了option请求自然就失败了,也就跨域失败,无法进行正常请求了
刚刚一行一行调试了一下,就是代码层面手动抛出了异常 throw new \Exception('登录已超时,请重新登录', 300),导致信息获取失败,然后前端就直接提示跨域了,option响应是ok的 有
Route::options('[{path:.+}]', function (){
return response('');
});拦截着
然后测试了一下。。发现在中间件里 不能手动抛异常。。。。
好了 处理了 目前在中间件里 针对代码层面的异常开启了try,然后出现异常的时候进行return response掉就Ok了
Route::options('[{path:.+}]', function (){
return response('');
});
这行没生效导致的,
我之前也遇到这个问题,只能在中间件里判断请求是否options,options的话返回CORS信息不验证token
但是不加这行的话,也会出现跨域问题。
这是因为没走到这行,所以导致无法正确响应cors信息,你直接把这行取消肯定也会出现跨域。
$request->userData = Token::getAuthData($token);
看起来是这行代码出错导致的。发生500错误后就会导致跨域错误。是的,已经处理了,但是在中间件手动抛出异常都会出现跨域错误。所以我开try 处理了。
抛出异常也是500错误,所以会有跨域错误
因为也做了异常处理,所以我的理解是,我抛出了异常,那么代码也应该走异常处理,然后响应错误信息来着。
我也是在中间件中抛出异常就会导致跨域错误,很无奈啊
@walkor 目前中间件里返回的错误异常是直接return json返回错误信息。就会提示跨域问题。
你这样在中间件抛异常不会产生跨域吗,我用的也是你的异常插件,然后自定义了一个异常,中间件中抛异常就会产生跨域
目前我也发现是有这个问题。
使用参考:https://github.com/Tinywan/webman-admin