Express

ExpressJS: Modularizing Routes and Implementing Multi-Language Support

admin  

In the ever-evolving web development landscape, embracing a global audience often means integrating multi-language support into our applications. Suppose we're working with an Express application where we've established a standard route handling structure, typically resembling router.get('/:page', async function(req, res){...}). Our challenge is to ensure the primary language content remains accessible through a standard path like domain1.com/page while also serving content in other languages through prefixed paths such as domain1.com/de/page. To tackle this, we need to fine-tune our route handling to adeptly manage both patterns. Let's explore how we can achieve this in a structured and efficient manner.

Step 1: Safeguarding the Primary Language Route

Firstly, we must ensure that our existing setup for the main language continues without interruption. This means our existing routes should reliably handle URLs without a language prefix. Here's how we maintain our current routing for the primary language:

router.get('/:page', async function(req, res){
    // Our existing handling for the main language content remains intact here
});

Step 2: Crafting Middleware for Language Detection

Our next move is to introduce middleware capable of detecting a language prefix within the URL. The responsibility of this middleware is to determine if the first segment of the path is a language code. If it identifies such a segment, the middleware will proceed to strip it from the URL and set a language variable within the request object. Here's how we implement it:

app.use((req, res, next) => {
    const host = req.hostname;
    const parts = req.url.split('/');

    if (multiLangDomains[host] && parts[1].match(/^[a-z]{2}$/i)) {
        req.lang = parts[1]; // e.g., 'de'
        req.url = '/' + parts.slice(2).join('/'); // Effortlessly removing the language part here
    } else {
        req.lang = 'default'; // Defaulting to the primary language if no prefix is present
    }

    next();
});

Step 3: Establishing Routes for Multi-Language Content

Having laid the groundwork with our middleware, it's time for us to establish a route that can handle language-specific content based on the URL prefix. We'll rely on the req.lang parameter, set by our middleware, to determine the language and serve the corresponding content:

router.get('/:page', async function(req, res){
    if(req.lang && req.lang !== 'default') {
        // Fetch and serve content for non-primary languages
        const content = getMultilanguageContent(req.params.page, req.lang);
        res.send(content);
    } else {
        // Serve content for the primary language
        const content = getMainContent(req.params.page);
        res.send(content);
    }
});

function getMultilanguageContent(page, lang) {
    // Define our logic to fetch and return content based on the page and language
    // ...
}

function getMainContent(page) {
    // Define our logic to fetch and return the primary language content for the page
    // ...
}

Step 4: Prioritizing Middleware and Route Order

In Express, the sequence in which we define our middleware and routes is paramount. We need to ensure that our language detection middleware is positioned before our routes. This setup allows for the necessary preprocessing and variable assignment to occur before any route handling takes place:

app.use(languageDetectionMiddleware);
app.use(router);

By adopting this methodical approach, our application is well-equipped to serve the primary language content through standard paths like domain1.com/page, while also proficiently handling additional languages through prefixed paths such as domain1.com/de/page. Our thoughtfully designed middleware ensures accurate detection and processing of the language prefix, thereby enabling our route handlers to deliver content that resonates with our diverse user base.

    Express