Building a Multilingual Website with Laravel Localization

In this tutorial, I’m going to show how to build a multilingual website with Laravel. There are many ways of using localization in Laravel. I’ll write two methods here. The output of the project will look like this:

Building a Multilingual Website with Laravel Localization
Building a Multilingual Website with Laravel Localization

Table of Contents

  1. Install Laravel and Basic Configurations
  2. Set Default Language
  3. Translate Using Short Keys
  4. Translation Strings As Keys
  5. Create Controller and Middleware
  6. Make Blade (View) Files
  7. Register Web Routes

Step 1 : Install Laravel and Basic Configurations

Each Laravel project needs this thing. That’s why I have written an article on this topic. Please see this part from here: Install Laravel and Basic Configurations.

Step 2 : Set Default Language

After installation, open this file config/app.php to set the default language.

'locale' => 'en',

By default local is set to en (English). If you check resources/lang folder, you will find a folder named en.

Step 3 : Translate Using Short Keys

We are going to add two more languages. These are Bengali and Hindi. Go to resources/lang directory and create two folders named bn and in. We are going to add a short key named title. The title will be translated into 3 languages.

Let’s create a file called lang.php in all 3 folders and add title key like this:

For English:

en/lang.php
<?php
return [
    'title' => 'Welcome to MyNotePaper'
];

For Bengali:

bn/lang.php
<?php
return [
    'title' => 'MyNotePaper এ আপনাকে স্বাগতম'
];

For Hindi:

in/lang.php
<?php
return [
    'title' => 'MyNotePaper में आपका स्वागत है'
];

We’ve added a title key. We will implement in blade file after a few steps.

Step 4 : Translation Strings As Keys

In this step, we are going to add some strings as keys for translation. Go to resources/lang and create two JSON file including two strings like this:

For Bengali:

bn.json
{
    "Hello!" : "হ্যালো!",
    "Stay with us and keep learning" : "আমাদের সাথে থাকুন এবং শিখতে থাকুন"
}

For Hindi:

in.json
{
    "Hello!" : "नमस्ते!",
    "Stay with us and keep learning" : "हमारे साथ रहें और सीखते रहें"
}

We’ve added some strings as keys. Like short key, we will implement in blade file after a few steps.

Step 5 : Create Controller and Middleware

We need a controller to change language. Create the controller using this command:

php artisan make:controller LocalizationController

Now open the controller from app\Http\Controllers and paste the below code. I’ve written a function to store selected language in session.

LocalizationController.php
<?php

namespace App\Http\Controllers;

use App;
use Illuminate\Http\Request;

class LocalizationController extends Controller
{
    public function index($locale)
    {
        App::setLocale($locale);
        // store the locale in session so that the middleware can register it
        session()->put('locale', $locale);
        return redirect()->back();
    }
}

Now we need a Middleware to register the local. Create the middleware using this command:

php artisan make:middleware Localization

Open the Localization Middleware from app\Http\Middleware and replace the code with this:

Localization.php
<?php

namespace App\Http\Middleware;

use App;
use Closure;

class Localization
{
    /**
     * Handle an incoming request.
     *
     * @param \Illuminate\Http\Request $request
     * @param \Closure $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {
        if (session()->has('locale')) {
            App::setLocale(session()->get('locale'));
        }
        return $next($request);
    }
}

We need to register the Localization Middleware. Open app/Http/Kernel.php file add \App\Http\Middleware\Localization::class, in the $middlewareGroups array’s web key.

Kernel.php
protected $middlewareGroups = [
    'web' => [
        \App\Http\Middleware\EncryptCookies::class,
        \Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse::class,
        \Illuminate\Session\Middleware\StartSession::class,
        // \Illuminate\Session\Middleware\AuthenticateSession::class,
        \Illuminate\View\Middleware\ShareErrorsFromSession::class,
        \App\Http\Middleware\VerifyCsrfToken::class,
        \Illuminate\Routing\Middleware\SubstituteBindings::class,
        \App\Http\Middleware\Localization::class, // Localization Middleware
    ],

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

We’ve created and set-up controller & middleware.

Step 6 : Make Blade (View) Files

We are going to create two view files. Create the two files named layout.blade.php and home.blade.php.

Open layout.blade.php and paste the below code. Here’s I’ve added a language selection dropdown menu using Boostrap 4.

layout.blade.php
<!DOCTYPE html>
<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <!-- CSRF Token -->
    <meta name="csrf-token" content="{{ csrf_token() }}">
    <title>{{ config('app.name', 'Laravel') }}</title>
    <!-- Bootstrap CSS -->
    <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css">
</head>
<body>
<div id="app">
    <div style="background-color: #f8f9fa;">
        <nav class="navbar navbar-expand-lg navbar-light bg-light container">
            <a href="https://shouts.dev/" target="_blank"><img src="https://i.imgur.com/hHZjfUq.png"
                                                                        width="140px;"></a>
            <button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarTogglerDemo02"
                    aria-controls="navbarTogglerDemo02" aria-expanded="false" aria-label="Toggle navigation">
                <span class="navbar-toggler-icon"></span>
            </button>

            <div class="collapse navbar-collapse" id="navbarTogglerDemo02">
                <!-- Right Side Of Navbar -->
                <ul class="navbar-nav ml-auto">
                    <!-- Authentication Links -->
                    @php $locale = session()->get('locale'); @endphp
                    <li class="nav-item dropdown">
                        <a id="navbarDropdown" class="nav-link dropdown-toggle" href="#" role="button"
                           data-toggle="dropdown" aria-haspopup="true" aria-expanded="false" v-pre>
                            @switch($locale)
                                @case('us')
                                <img src="{{asset('img/us.png')}}"> English
                                @break
                                @case('bn')
                                <img src="{{asset('img/bn.png')}}"> Bengali
                                @break
                                @case('in')
                                <img src="{{asset('img/in.png')}}"> Hindi
                                @break
                                @default
                                <img src="{{asset('img/us.png')}}"> English
                            @endswitch
                            <span class="caret"></span>
                        </a>
                        <div class="dropdown-menu dropdown-menu-right" aria-labelledby="navbarDropdown">
                            <a class="dropdown-item" href="lang/en"><img src="{{asset('img/us.png')}}"> English</a>
                            <a class="dropdown-item" href="lang/bn"><img src="{{asset('img/bn.png')}}"> Bengali</a>
                            <a class="dropdown-item" href="lang/in"><img src="{{asset('img/in.png')}}"> Hindi</a>
                        </div>
                    </li>
                </ul>
            </div>
        </nav>
    </div>

    <main class="py-4">
        @yield('content')
    </main>
</div>

<!-- jQuery first, then Popper.js, then Bootstrap JS -->
<script src="https://code.jquery.com/jquery-3.2.1.slim.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.12.9/umd/popper.min.js"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/js/bootstrap.min.js"></script>
</body>
</html>

Now open home.blade.php file. In this file, we will display our short key and strings as keys translation.

We can retrieve translation using trans()@lang and __() methods. Let’s retrieve them in this view:

home.blade.php
@extends('layout')
@section('content')
    <div class="container">
        <h1 class="display-4 text-center" style="font-size: 2.5rem">@lang("Hello!")</h1>
        <h3 class="display-4 text-center" style="font-size: 1.5rem">{{ trans('lang.title') }}</h3>
        <h4 class="display-4 text-center" style="font-size: 1.5rem">{{ __("Stay with us and keep learning")}}</h4>
    </div>
@endsection

Step 7 : Register Web Routes

We are at the end. This is the last step. We have to define a route to display home view and another to change the language. Let’s do that:

routes/web.php
<?php
Route::get('/', function () {
    return view('home');
});
Route::get('lang/{locale}', 'LocalizationController@index');

Now run the project and see the output.

The tutorial is over. You can download this project from GitHub. Thank you.


Software Engineer | Ethical Hacker & Cybersecurity...

Md Obydullah is a software engineer and full stack developer specialist at Laravel, Django, Vue.js, Node.js, Android, Linux Server, and Ethichal Hacking.