拦截Laravel路由 [英] Intercept Laravel Routing
问题描述
我正忙于在Laravel 5.1中构建Restful API,其中API版本通过标头传递.这样,我可以对功能进行版本控制,而不是复制并粘贴整个路由组并增加版本号.
I am busy building a Restful API in Laravel 5.1 where the API version is passed through the header. This way I can version the features rather than copy and pasting a whole route group and increment the version number.
我遇到的问题是我想拥有版本化的方法,即IE:
The problem I'm having is that I would like to have versioned methods, IE:
public function store_v1 (){ }
我已经在路由中添加了一个中间件,该中间件从标头捕获版本,但是现在需要修改请求以从控制器中选择正确的方法.
I have added a middleware on my routes where I capture the version from the header, but now need to modify the request to choose the correct method from the controller.
app/Http/routes.php
app/Http/routes.php
Route::group(['middleware' => ['apiversion']], function()
{
Route::post('demo', 'DemoController@store');
}
app/Http/Middleware/ApiVersionMiddleware.php
app/Http/Middleware/ApiVersionMiddleware.php
public function handle($request, Closure $next)
{
$action = app()->router->getCurrentRoute()->getActionName();
// dd($action)
// returns "App\Http\Controllers\DemoController@store"
}
从这里开始,我将标头版本附加到$ action,然后将其通过$ request传递,以使其到达正确的方法.
From here on, I would attach the header version to the $action and then pass it through the $request so that it reaches the correct method.
好吧,那还是理论.
关于如何将动作添加到路线"中的任何想法?
Any ideas on how I would inject actions into the Route?
推荐答案
我认为中间件可能不是最好的选择.您可以访问该路由,但无法修改要调用的控制器方法.
I think Middleware might not be the best place to do that. You have access to the route, but it doesn't offer a away to modify the controller method that will be called.
更简单的选择是注册一个自定义路由调度程序,该调度程序根据请求和路由来处理调用控制器方法的逻辑.看起来可能像这样:
Easier option is to register a custom route dispatcher that handling the logic of calling controller methods based on the request and the route. It could look like that:
<?php
class VersionedRouteDispatcher extends Illuminate\Routing\ControllerDispatcher {
public function dispatch(Route $route, Request $request, $controller, $method)
{
$version = $request->headers->get('version', 'v1'); // take version from the header
$method = sprintf('%s_%s', $method, $version); // create target method name
return parent::dispatch($route, $request, $controller, $method); // run parent logic with altered method name
}
}
拥有此自定义调度程序后,请在您的AppServiceProvider中注册它:
Once you have this custom dispatcher, register it in your AppServiceProvider:
public function register() {
$this->app->singleton('illuminate.route.dispatcher', VersionedRouteDispatcher::class);
}
这样,您将用自己的默认路由分配器覆盖默认路由分配器,该分配器将使用从请求标头中获取的版本作为控制器方法名称的后缀.
This way you'll overwrite the default route dispatcher with your own one that will suffix controller method names with the version taken from request header.
这篇关于拦截Laravel路由的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!