Tutorial

Pre‑rendered Multilingual Gatsby Site with SiteLocaleAI

Published September 23, 2026

Pre‑rendered Multilingual Gatsby Site with SiteLocaleAI

Pre‑rendered Multilingual Gatsby Site with SiteLocaleAI

International visitors should see your site in their language, and Google must be able to crawl those pages. This tutorial shows how to integrate SiteLocaleAI, a self‑hosted JavaScript library, into a Gatsby static site, generate pre‑rendered translations with the CLI, and ship a fully indexed multilingual site.


📋 Prerequisites

  • Gatsby v5 project (or any static site generated with Gatsby)
  • Node.js ≥ 18
  • An LLM API key (Claude, GPT‑4o‑mini, etc.) – SiteLocaleAI works with any provider you prefer
  • Basic knowledge of npm/yarn and Git

1️⃣ Install the SiteLocaleAI library

# Using npm
npm i @sitelocaleai/core

# Or with yarn
yarn add @sitelocaleai/core

The package is framework‑agnostic, so you can import it directly in any component.


2️⃣ Create a tiny wrapper for translation

Create a file src/utils/translate.js:

import { SiteLocale } from "@sitelocaleai/core";

// Load your LLM API key from environment (never commit it)
const LLM_API_KEY = process.env.GATSBY_LLM_API_KEY;

export const translator = new SiteLocale({
  apiKey: LLM_API_KEY,
  provider: "openai", // or "anthropic", "gemini", etc.
  // Optional: custom prompt to keep tone consistent
  prompt: "Translate the following HTML content into {{lang}} while preserving markup.",
});

Now you can call translator.translate(html, "fr") to get a French version of any HTML string.


3️⃣ Add translation data to your pages

In Gatsby, each page is a React component. Wrap the page’s JSX with a helper that fetches translations at build time.

// src/pages/index.js
import React from "react";
import { translator } from "../utils/translate";

export const Head = () => (
  <title>My Awesome Site</title>
);\nexport default function Home({ pageContext }) {
  const { locale, html } = pageContext; // injected by the CLI (see later)
  return (
    <main dangerouslySetInnerHTML={{ __html: html }} />
  );
}

The pageContext will contain the pre‑rendered HTML for the requested locale. We’ll generate those contexts with the SiteLocaleAI CLI.


4️⃣ Configure the SiteLocaleAI CLI for Gatsby

SiteLocaleAI ships with a CLI that can crawl your site, translate each page, and write the results to the Gatsby data layer.

Create a config file sitelocale.config.js at the project root:

module.exports = {
  // Languages you want to support (ISO 639‑1 codes)
  locales: ["en", "es", "de", "fr", "ja"],

  // Path to the page that renders the source HTML
  sourcePath: "src/pages/**/*.js",

  // Where to write the translated pages (Gatsby will pick them up automatically)
  outDir: "src/generated-locales",

  // Psychological rounding for price localization (optional)
  priceRounding: {
    USD: "0.99",
    EUR: "0.95",
    JPY: "0",
  },

  // LLM provider configuration – same as the wrapper above
  llm: {
    provider: "openai",
    apiKey: process.env.LLM_API_KEY,
    model: "gpt-4o-mini",
  },
};

Add a script to package.json:

"scripts": {
  "build": "gatsby build",
  "translate": "node ./node_modules/@sitelocaleai/cli translate"
}

5️⃣ Run the translation step

# Ensure your LLM key is available
export LLM_API_KEY=sk-xxxxxxxxxxxx

# Generate translated pages
npm run translate

The CLI does the following:
1. Renders each page to static HTML using Gatsby’s SSR.
2. Sends the HTML to the LLM with the prompt defined in the wrapper.
3. Writes a new file for each locale under src/generated-locales/<locale>/….
4. Adds a pageContext entry so the React component receives locale and the translated html.

Now the site contains a full set of pre‑rendered pages for every language, ready for crawlers.


6️⃣ Wire the generated pages into Gatsby’s routing

Create a small plugin file gatsby-node.js to tell Gatsby about the extra pages:

const path = require("path");
const fs = require("fs");

exports.createPages = async ({ actions }) => {
  const { createPage } = actions;
  const locales = ["en", "es", "de", "fr", "ja"];

  const srcPages = fs.readdirSync(path.resolve("src/pages"));

  srcPages.forEach((file) => {
    const pageName = file.replace(/\.js$/, "");
    locales.forEach((locale) => {
      const pagePath = locale === "en" ? `/${pageName}` : `/${locale}/${pageName}`;
      createPage({
        path: pagePath,
        component: path.resolve(`src/pages/${file}`),
        context: { locale, html: fs.readFileSync(path.resolve(`src/generated-locales/${locale}/${pageName}.html`), "utf8") },
      });
    });
  });
};

Now gatsby build will output static HTML for every language, e.g.:
- public/index.html (English)
- public/es/index.html (Spanish)
- public/de/index.html (German)


7️⃣ SEO: Add hreflang tags and language‑specific meta data

In the Head component of each page, inject language tags:

export const Head = ({ pageContext }) => {
  const { locale } = pageContext;
  const hreflangs = [
    { lang: "en", href: "https://example.com/" },
    { lang: "es", href: "https://example.com/es/" },
    { lang: "de", href: "https://example.com/de/" },
    { lang: "fr", href: "https://example.com/fr/" },
    { lang: "ja", href: "https://example.com/ja/" },
  ];

  return (
    <>
      <title>{locale === "en" ? "My Awesome Site" : "My Awesome Site"}</title>
      <meta name="description" content="International version of My Awesome Site" />
      {hreflangs.map((h) => (
        <link rel="alternate" hreflang={h.lang} href={h.href} key={h.lang} />
      ))}
    </>
  );
};

These tags tell Google which URL serves which language, improving indexing and avoiding duplicate‑content penalties.


8️⃣ Deploy

Push the public/ folder to any static‑host (Netlify, Vercel, AWS S3 + CloudFront, etc.). Because the translations are pre‑rendered, search bots receive fully translated HTML without JavaScript execution.


9️⃣ Verify with Google Search Console

  • Submit each language URL in the URL Inspection tool.
  • Check the Coverage report for language‑specific pages.
  • Use the International Targeting report to confirm hreflang implementation.

📚 Further reading


🎉 Wrap‑up

You now have a Gatsby site that:
1. Uses SiteLocaleAI to translate content with your own LLM API key.
2. Generates static, SEO‑friendly pages for every target language.
3. Serves price values rounded psychologically per currency.
4. Is ready for Google to index each locale independently.

The result is faster load times, lower translation costs, and a massive boost in international organic traffic.


Ready to go global? Try SiteLocaleAI today and see how effortless multilingual SEO can be. 🚀