Laravel:检查路线中的slug是否等于数据库中的slug

时间:2017-03-09 23:18:56

标签: php laravel laravel-5 routes

我有一个像/locations/name-of-the-location.ID

这样的网址

我的路线是:

Route::get('locations/{slug}.{location}', ['as' => 'locations.show', 'uses' => 'LocationsController@show'])->where([
    'location' => '[0-9]+', 
    'slug' => '[a-z0-9-]+'
]);

现在我想检查提供的slug是否与我的模型在数据库列'slug'中保存的slug相同(因为slug可能已更改)。如果没有,那么我想重定向到正确的路径。

最佳去处是哪里?我想到了\ App \ Providers \ RouteServiceProvider-但是当我尝试在那里使用Route::currentRouteName()时,我得到NULL,可能是因为它对于RouteServiceProvider的boot()方法中的那个方法来说太早了。

我可以做的是使用path(),但这对我来说似乎有点脏,因为我使用其他语言的路由前缀。

这是我尝试过的(我正在使用一个小帮助类RouteSlug) - 当然它不起作用:

public function boot()
{
    parent::boot();

    if (strstr(Route::currentRouteName(), '.', true) == 'locations')
    {
        Route::bind('location', function ($location) {
            $location = \App\Location::withTrashed()->find($location);
            $parameters = Route::getCurrentRoute()->parameters();
            $slug = $parameters['slug'];

            if ($redirect = \RouteSlug::checkRedirect(Route::getCurrentRoute()->getName(), $location->id, $location->slug, $slug))
            {
                return redirect($redirect);
            }
            else 
            {
                return $location;
            }

        });
    }
}

2 个答案:

答案 0 :(得分:0)

您的路线应如下所示:

Route::get('locations/{id}/{slug}', ['as' => 'locations.show', 'uses' => 'LocationsController@show'])->where([
    'id' => '[0-9]+', 
    'slug' => '[a-z0-9-]+'
]);

LocationsController@show应如下所示:

public function show($id, $slug)
{
    // Add 'use App\Location' to the top of this controller
    $location = Location::find($id);

    // I'm not sure what you were doing with the soft deleted items
    // but you might want to restore them if you are using them
    if ($location->trashed()) $location->restore();

    if ($slug != $location->slug) {
        return redirect()->route('locations.show', ['id' => $id, 'slug' => $location->slug]);
    }

    // Return the view

}

答案 1 :(得分:0)

最后我想出了一个中间件:

应用\ HTTP \中间件\ CheckSlug

public function handle($request, Closure $next)
{
    if ($redirect = RouteSlug::checkRedirect(Route::currentRouteName(), $request->location->id, $request->location->slug, $request->slug))
    {
        return redirect($redirect);
    }

    return $next($request);
}

我的路线如下:

Route::get('locations/{slug}.{location}', ['as' => 'locations.show', 'uses' => 'LocationsController@show'])->where([
    'location' => '[0-9]+', 
    'slug' => '[a-z0-9-]+'
])->middleware(App\Http\Middleware\CheckSlug::class);