Rud*_*die 6 pipeline middleware exception laravel-5
我有一个可以抛出异常的laravel控制器,以及一个捕获该异常的全局中间件.在半伪代码中:
// App\Controllers\...
class Controller {
function store() {
throw new FormException; // via validation etc, but it's thrown here
}
}
// App\Http\Middleware\...
class Middleware {
function handle(Closure $next) {
try {
// Breakpoint 1
return $next(); // $response
// Breakpoint 2
}
catch (FormException $ex) {
// Breakpoint 3
exit('FormException caught!');
}
}
}
Run Code Online (Sandbox Code Playgroud)
问题是异常永远不会被捕获.在管道中的Somwhere,应用程序捕获异常并打印一个漂亮的错误页面,但它应该被我的中间件捕获,以便它可以正确处理它.
我可以想象我的中间件没有捕获它的唯一方法是,如果它被捕获到管道内部更深处,而不是进一步向上/周围,但我在其他中间件或管道执行代码中找不到任何try/catch.
这个例外在哪里被捕?为什么?
这可能不是一个很好的模式,但我现在不关心.我比其他任何事都更好奇.我是否完全误解了Laravel的中间件?
我自己的超级简单中间件测试做了我的预期:https://3v4l.org/Udr84 - 捕获并处理中间件内的异常.
笔记:
$response物体(返回值$next())为处理异常页面,所以它已经被处理.在哪里以及为何?App\Exceptions\Handler::render()工作中处理异常,但我希望所有逻辑都在中间件包中,而不是在应用程序代码中.相关的Laravel代码:
Kernel::handle() 启动中间件管道<<这有一个catch-all catch(),但我的catch()是第一个,对吗?Pipeline::then() 启动中间件执行Pipeline::getSlice()处理并创建$next闭包Rud*_*die 14
显然这是设计的:
是的,这是从L5.2开始的beavhiour.抛出异常会导致响应被设置为从异常处理程序返回的响应,然后允许中间件从该点退出.
我觉得这很奇怪.可插拔中间件非常适合捕获异常.
有两种方法可以做到这一点:
App\Exceptions\Handler,这是不够好的,因为包不能触及那个Funky:从响应对象中获取原始异常对象:
$response = $next($request);
$exception = $response->exception;
Run Code Online (Sandbox Code Playgroud)我有同样的问题。在阅读Rudie 提到的线程时,他们给出了一个对我有用的可能解决方案:
public function handle(Request $request, Closure $next) {
$response = $next($request);
// 'Catch' our FormValidationException and redirect back.
if (!empty($response->exception) && $response->exception instanceof FormValidationException) {
return redirect()->back()->withErrors($response->exception->form->getErrors())->withInput();
}
return $response;
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
6892 次 |
| 最近记录: |