---
title: Translation guide
description: How localization works on the Gears docs — locales, the per-language directory convention, and the Lunaria status dashboard.
sidebar:
  label: Translation guide
  order: 3
---

The Gears docs are localizable. Translations live alongside the English source,
and a [status dashboard](../../i18n/) tracks what's done, outdated, or missing per
language.

## The translation dashboard

Visit **[/i18n/](../../i18n/)** to see overall progress for each language. Pages are
marked:

- ✅ **Done** — translated and up to date.
- 🔄 **Outdated** — the English source changed after the translation; needs an update.
- ❌ **Missing** — not yet translated.

The dashboard is generated by [Lunaria](https://lunaria.dev), which compares git
history of the source file against its translation to decide freshness — so always
keep the translated file at the **same path** as its English source.

## How locales work

English is the default locale and is served at the site **root** (`/`). Each
additional language is served under its code, e.g. `/ru/`.

Adding a language is two small edits plus a content directory:

1. In [`astro.config.mjs`](https://github.com/constructorfabric/gears-rust-web-docs/blob/main/astro.config.mjs),
   add one line to `locales`:

   ```js
   locales: {
     root: { label: 'English', lang: 'en' },
     de: { label: 'Deutsch', lang: 'de' } // new
   }
   ```

2. In [`lunaria.config.json`](https://github.com/constructorfabric/gears-rust-web-docs/blob/main/lunaria.config.json),
   add a matching entry to `locales`:

   ```json
   { "label": "Deutsch", "lang": "de" }
   ```

3. Create the content directory `src/content/docs/de/`.

:::note
`ru` is currently wired up as an **example** locale so the dashboard renders. It
shows 0% until translated files exist — that's expected and demonstrates the flow.
:::

## Directory convention

Translations mirror the English file tree under a language-code directory:

```text
src/content/docs/
├── concepts/
│   └── runtime-and-lifecycle.md      # English source
└── ru/
    └── concepts/
        └── runtime-and-lifecycle.md  # Russian translation (same path under ru/)
```

The filename and subdirectory **must match** the English source so Lunaria can pair
them.

## Translating a page

1. Open the [dashboard](../../i18n/) and pick a **Missing** or **Outdated** page.
2. Copy the English source to the matching path under your language directory.
3. Translate the body. **Keep unchanged:**
   - frontmatter **keys** (translate only the `title`/`description` **values**),
   - code blocks and command output,
   - internal link targets (the path stays the same).
4. Run `pnpm dev` and visit the localized URL (e.g. `/ru/concepts/runtime-and-lifecycle/`).
5. Open a pull request following the [contributor guide](../contributor-guide/).

:::tip
Prioritize quality over volume. A small set of accurate, well-reviewed pages is
more valuable than many machine-translated ones. Human review of any machine
translation is essential.
:::
