I am creating localization in Laravel 5.3 application. It must follow such requirements:
If route path contains locale prefix, locale should be set according to this prefix
If there’s no route prefix, it should be set to English.
For instance:
A) mysite.org/pl/blog/133
sets locale to pl
and calls BlogController with parameter 113
B) mysite.org/en/blog/133
sets locale to en
and calls BlogController with parameter 113
C) mysite.org/blog/133
acts in the same way as previous.
To implement this, I was using the following code:
#routes/web.php require base_path('routes/common.php'); // TODO set default locale to en Route::group(['prefix' => '{locale}'], function($group) { require base_path('routes/common.php'); // TODO set locale to $locale foreach ($group -> getRoutes() as $route) { $route->where('locale', 'en|ru|pl|ua|de'); } }); #routes/common.php Route::get('/blog/{id}', function($id) { // Return view of respective blogpost });
The problem is that when I use path A or B i get an extra first parameter in my action function, which derives from the locale prefix.
Can I hide this parameter somehow? Or is there a way to achieve what I want in a way more architecturally correct?
Advertisement
Answer
I’m not sure my solution is the best or not but you can try this
- create new file in app/Http/Middileware/Language.php
…
namespace AppHttpMiddleware; use Closure; use IlluminateRoutingRedirector; use IlluminateHttpRequest; class Language { public function __construct(Redirector $redirector) { // $this->app = $app; $this->redirector = $redirector; // $this->request = $request; } /** * Handle an incoming request. * * @param IlluminateHttpRequest $request * @param Closure $next * @return mixed */ public function handle($request, Closure $next) { // Make sure current locale exists. $segments = $request->segments(); $locale = $segments[0]; $languages = ['en','ru','pl','ua','de']; if (!in_array($locale, $languages)) { $segments = array_merge(['en'], $segments); return $this->redirector->to(implode('/', $segments)); } return $next($request); } }
In app/Http/Kernel.php and this line
protected $middleware = [ AppHttpMiddlewareLanguage::class, IlluminateFoundationHttpMiddlewareCheckForMaintenanceMode::class, ];
In file route (route/web.php) add prefix in group
Route::group(['middleware' => ['web'], 'prefix' => '{locale}'], function () { ...
Hope this help