skip to Main Content

I’m trying to create a website with multiple languages (with Laravel 5.5). Therefore I follow the tutorial https://mydnic.be/post/how-to-build-an-efficient-and-seo-friendly-multilingual-architecture-for-your-laravel-application, but somehow I have troubles with the language middleware part:

// BeforeLanguage.php 

namespace AppHttpMiddleware;

use Closure;

class BeforeLanguage
{
    /**
     * Handle an incoming request.
     *
     * @param  IlluminateHttpRequest  $request
     * @param  Closure  $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {
        // Check if the first segment matches a language code
        if (!array_key_exists($request->segment(1), config('translatable.locales')) ) {

            // Store segments in array
            $segments = $request->segments();

            // Set the default language code as the first segment
            $segments = array_prepend($segments, config('app.fallback_locale'));

            // Redirect to the correct url
            return redirect()->to(implode('/', $segments));
        }

        return $next($request);
    }
}

It works if I open a URL with the identifier for the language, e. g. http://ps.dev/de/app/login but I get “Sorry, the page you are looking for could not be found.” if I try to open the page without the language identifier in the URI, e. g. http://ps.dev/app/login.

But here I would expect that the middleware adds the language segment to the URI. Any idea what could go wrong?

Below I would like to provide some additional information.

web.php

Route::prefix('app')->group(function () {

    // Authentication routes
    Route::get('login', 'SessionsController@create')->name('login');

    // ...
});

Kernel.php

protected $middlewareGroups = [
    'web' => [
        AppHttpMiddlewareBeforeLanguage::class,
        AppHttpMiddlewareEncryptCookies::class,
        IlluminateCookieMiddlewareAddQueuedCookiesToResponse::class,
        IlluminateSessionMiddlewareStartSession::class,
        // IlluminateSessionMiddlewareAuthenticateSession::class,
        IlluminateViewMiddlewareShareErrorsFromSession::class,
        AppHttpMiddlewareVerifyCsrfToken::class,
        IlluminateRoutingMiddlewareSubstituteBindings::class,
    ],

    'api' => [
        'throttle:60,1',
        'bindings',
    ],
];

According to the Laravel documentation page the middlewares assigned to the middleware group web get executed by default for any route defined inside web.php. (Out of the box, the web middleware group is automatically applied to your routes/web.php file by the RouteServiceProvider.)

RouteServiceProvider.php

protected function mapWebRoutes()
{

    $locale = Request::segment(1);

    Route::prefix($locale)
        ->middleware('web')
        ->namespace($this->namespace)
        ->group(base_path('routes/web.php'));

}

2

Answers


  1. I think you had chosen a hard way something like “Reinvent the Wheel!” 😉

    Although It’s your decision and respectful, as a suggestion try this nice package for localization in Laravel 😀

    Login or Signup to reply.
  2. The reason why it is sending to the 404 is that the url doesn’t exist. In your route file, you have not created the paths for language. So ultimately, if your
    middleware works it will send to the non-existing route path, which will be 404.

    Add an identifier for the language :-

    Route::get('{lang}/login', 'SessionsController@create')->name('login');
    

    Check you routes by the following artisan command in cmd

    php artisan route:list
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search