Search code examples
phplaravelsessioninternationalization

Laravel Session Getting Lost


I am using Laravel 11 for a small project and I am trying to handle internationalization.

I have a dropdown where I allow a user to select languages and based on the selection, it takes the user to the following code in my web.php file in my routes directory:

Route::get('/lang/{locale}', function ($locale) {
    if (in_array($locale, ['en', 'fr'])) {
        session(['locale' => $locale]);
        App::setLocale($locale);
    }
    return redirect()->back();
});

Then I have middleware set up to help with the internationalization as well. It looks like this:

public function handle(Request $request, Closure $next): Response
{
    if (session()->has('locale')) {
        App::setLocale(session('locale'));
    }
    else{
        App::setLocale(config('app.locale'));
    }
    return $next($request);
}

The problem I am seeing is that when I click on the language option in a dropdown, and the request goes through the route. I am not seeing any change within the session. If the route is redirecting back, is the session not being set? I have tried dumping all the session variables in the middleware, and it is blank. There is no "locale" property in the session. Where am I going wrong?

I can confirm that the middleware is hit after the redirect->back() fires...help?


Solution

  • Based on your comment on how you registered the middleware, I think it has to do with the order middlewares are executed. The Illuminate\Session\Middleware\StartSession middleware is part of the web group so you have to append your middleware to that group to ensure the session is started before your middleware is executed. The fix is to register your middleware like this:

    return Application::configure(...)
        ->withMiddleware(function (Middleware $middleware) {
            $middleware->web(append: [
                SetLocale::class,
            ]);
        })
    

    This should fix your problem.

    Docs: Laravel Middleware Groups