@intlayer/docs 9.3.0 → 9.3.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +24 -24
- package/blog/ar/rag_powered_documentation_assistant.md +1 -1
- package/blog/pl/rag_powered_documentation_assistant.md +1 -1
- package/dist/cjs/_virtual/_rolldown/runtime.cjs +1 -2
- package/dist/cjs/authors2.cjs +0 -1
- package/dist/cjs/common.cjs.map +1 -1
- package/dist/cjs/generated/blog.entry.cjs +4 -2
- package/dist/cjs/generated/blog.entry.cjs.map +1 -1
- package/dist/cjs/generated/docs.entry.cjs +24 -2
- package/dist/cjs/generated/docs.entry.cjs.map +1 -1
- package/dist/cjs/generated/frequentQuestions.entry.cjs +4 -2
- package/dist/cjs/generated/frequentQuestions.entry.cjs.map +1 -1
- package/dist/cjs/generated/legal.entry.cjs +4 -2
- package/dist/cjs/generated/legal.entry.cjs.map +1 -1
- package/dist/esm/generated/blog.entry.mjs +4 -2
- package/dist/esm/generated/blog.entry.mjs.map +1 -1
- package/dist/esm/generated/docs.entry.mjs +24 -2
- package/dist/esm/generated/docs.entry.mjs.map +1 -1
- package/dist/esm/generated/frequentQuestions.entry.mjs +4 -2
- package/dist/esm/generated/frequentQuestions.entry.mjs.map +1 -1
- package/dist/esm/generated/legal.entry.mjs +4 -2
- package/dist/esm/generated/legal.entry.mjs.map +1 -1
- package/dist/types/generated/docs.entry.d.ts +1 -0
- package/dist/types/generated/docs.entry.d.ts.map +1 -1
- package/docs/ar/configuration.md +10 -10
- package/docs/ar/eslint.md +336 -0
- package/docs/ar/interest_of_intlayer.md +24 -22
- package/docs/ar/intlayer_with_express.md +1 -1
- package/docs/ar/intlayer_with_react_router_v7_fs_routes.md +1 -1
- package/docs/ar/intlayer_with_svelte_kit.md +1 -1
- package/docs/ar/intlayer_with_tanstack+solid.md +5 -3
- package/docs/ar/intlayer_with_tanstack.md +5 -3
- package/docs/ar/lsp.md +114 -175
- package/docs/ar/readme.md +25 -25
- package/docs/bn/configuration.md +10 -10
- package/docs/bn/eslint.md +336 -0
- package/docs/bn/interest_of_intlayer.md +24 -22
- package/docs/cs/configuration.md +10 -10
- package/docs/cs/eslint.md +336 -0
- package/docs/cs/interest_of_intlayer.md +24 -22
- package/docs/de/configuration.md +10 -10
- package/docs/de/eslint.md +336 -0
- package/docs/de/interest_of_intlayer.md +24 -22
- package/docs/de/intlayer_with_svelte_kit.md +1 -1
- package/docs/de/intlayer_with_tanstack+solid.md +5 -3
- package/docs/de/intlayer_with_tanstack.md +5 -3
- package/docs/de/lsp.md +111 -172
- package/docs/de/readme.md +24 -24
- package/docs/en/configuration.md +10 -10
- package/docs/en/eslint.md +336 -0
- package/docs/en/interest_of_intlayer.md +24 -22
- package/docs/en/intlayer_with_svelte_kit.md +1 -1
- package/docs/en/intlayer_with_tanstack+solid.md +5 -3
- package/docs/en/intlayer_with_tanstack.md +5 -3
- package/docs/en/lsp.md +109 -170
- package/docs/en/readme.md +24 -24
- package/docs/en-GB/configuration.md +10 -10
- package/docs/en-GB/eslint.md +336 -0
- package/docs/en-GB/interest_of_intlayer.md +24 -22
- package/docs/en-GB/intlayer_with_create_react_app.md +32 -35
- package/docs/en-GB/intlayer_with_react_router_v7_fs_routes.md +1 -1
- package/docs/en-GB/intlayer_with_svelte_kit.md +1 -1
- package/docs/en-GB/intlayer_with_tanstack+solid.md +5 -3
- package/docs/en-GB/intlayer_with_tanstack.md +5 -3
- package/docs/en-GB/lsp.md +109 -170
- package/docs/en-GB/readme.md +24 -24
- package/docs/es/configuration.md +10 -10
- package/docs/es/eslint.md +336 -0
- package/docs/es/interest_of_intlayer.md +24 -22
- package/docs/es/intlayer_with_svelte_kit.md +1 -1
- package/docs/es/intlayer_with_tanstack+solid.md +5 -3
- package/docs/es/intlayer_with_tanstack.md +5 -3
- package/docs/es/lsp.md +114 -175
- package/docs/es/readme.md +24 -24
- package/docs/fr/configuration.md +10 -10
- package/docs/fr/eslint.md +336 -0
- package/docs/fr/interest_of_intlayer.md +24 -22
- package/docs/fr/intlayer_with_svelte_kit.md +1 -1
- package/docs/fr/intlayer_with_tanstack+solid.md +5 -3
- package/docs/fr/intlayer_with_tanstack.md +5 -3
- package/docs/fr/lsp.md +110 -171
- package/docs/fr/readme.md +24 -24
- package/docs/hi/configuration.md +10 -10
- package/docs/hi/eslint.md +336 -0
- package/docs/hi/interest_of_intlayer.md +24 -22
- package/docs/hi/intlayer_with_express.md +1 -1
- package/docs/hi/intlayer_with_react_router_v7_fs_routes.md +1 -1
- package/docs/hi/intlayer_with_svelte_kit.md +1 -1
- package/docs/hi/intlayer_with_tanstack+solid.md +5 -3
- package/docs/hi/intlayer_with_tanstack.md +5 -3
- package/docs/hi/intlayer_with_vite+svelte.md +2 -2
- package/docs/hi/lsp.md +113 -174
- package/docs/hi/readme.md +24 -24
- package/docs/id/configuration.md +10 -10
- package/docs/id/eslint.md +336 -0
- package/docs/id/interest_of_intlayer.md +24 -22
- package/docs/id/intlayer_with_svelte_kit.md +1 -1
- package/docs/id/intlayer_with_tanstack+solid.md +5 -3
- package/docs/id/intlayer_with_tanstack.md +5 -3
- package/docs/id/lsp.md +113 -174
- package/docs/id/readme.md +24 -24
- package/docs/it/configuration.md +10 -10
- package/docs/it/eslint.md +336 -0
- package/docs/it/interest_of_intlayer.md +24 -22
- package/docs/it/intlayer_with_svelte_kit.md +1 -1
- package/docs/it/intlayer_with_tanstack+solid.md +5 -3
- package/docs/it/intlayer_with_tanstack.md +5 -3
- package/docs/it/lsp.md +115 -176
- package/docs/it/readme.md +24 -24
- package/docs/ja/configuration.md +10 -10
- package/docs/ja/eslint.md +336 -0
- package/docs/ja/interest_of_intlayer.md +24 -22
- package/docs/ja/intlayer_with_react_router_v7.md +1 -146
- package/docs/ja/intlayer_with_tanstack+solid.md +5 -3
- package/docs/ja/intlayer_with_tanstack.md +5 -3
- package/docs/ja/intlayer_with_vite+react.md +5 -1
- package/docs/ja/lsp.md +113 -174
- package/docs/ja/readme.md +24 -24
- package/docs/ko/configuration.md +10 -10
- package/docs/ko/eslint.md +336 -0
- package/docs/ko/interest_of_intlayer.md +24 -22
- package/docs/ko/intlayer_with_lynx+react.md +4 -0
- package/docs/ko/intlayer_with_react_router_v7_fs_routes.md +1 -1
- package/docs/ko/intlayer_with_storybook.md +5 -5
- package/docs/ko/intlayer_with_svelte_kit.md +1 -1
- package/docs/ko/intlayer_with_tanstack+solid.md +5 -3
- package/docs/ko/intlayer_with_tanstack.md +5 -3
- package/docs/ko/lsp.md +112 -173
- package/docs/ko/readme.md +24 -24
- package/docs/nl/configuration.md +10 -10
- package/docs/nl/eslint.md +336 -0
- package/docs/nl/interest_of_intlayer.md +24 -22
- package/docs/pl/configuration.md +10 -10
- package/docs/pl/eslint.md +336 -0
- package/docs/pl/interest_of_intlayer.md +4 -2
- package/docs/pl/intlayer_with_astro.md +1 -114
- package/docs/pl/intlayer_with_svelte_kit.md +1 -1
- package/docs/pl/intlayer_with_tanstack+solid.md +5 -3
- package/docs/pl/intlayer_with_tanstack.md +5 -3
- package/docs/pl/lsp.md +115 -176
- package/docs/pl/migration_from_i18next_to_intlayer.md +4 -0
- package/docs/pl/migration_from_next-i18next_to_intlayer.md +8 -4
- package/docs/pl/migration_from_next-intl_to_intlayer.md +11 -5
- package/docs/pl/migration_from_nuxtjs_i18n_to_intlayer.md +8 -4
- package/docs/pl/migration_from_react-i18next_to_intlayer.md +8 -4
- package/docs/pl/migration_from_vue-i18n_to_intlayer.md +4 -0
- package/docs/pl/readme.md +24 -24
- package/docs/pt/configuration.md +10 -10
- package/docs/pt/eslint.md +336 -0
- package/docs/pt/interest_of_intlayer.md +24 -22
- package/docs/pt/intlayer_with_astro.md +1 -114
- package/docs/pt/intlayer_with_svelte_kit.md +1 -1
- package/docs/pt/intlayer_with_tanstack+solid.md +5 -3
- package/docs/pt/intlayer_with_tanstack.md +5 -3
- package/docs/pt/lsp.md +113 -174
- package/docs/pt/readme.md +24 -24
- package/docs/ru/configuration.md +10 -10
- package/docs/ru/eslint.md +336 -0
- package/docs/ru/interest_of_intlayer.md +24 -22
- package/docs/ru/intlayer_with_nextjs_14.md +1 -1
- package/docs/ru/intlayer_with_nextjs_15.md +1 -1
- package/docs/ru/intlayer_with_svelte_kit.md +1 -1
- package/docs/ru/intlayer_with_tanstack+solid.md +5 -3
- package/docs/ru/intlayer_with_tanstack.md +5 -3
- package/docs/ru/lsp.md +112 -173
- package/docs/ru/readme.md +24 -24
- package/docs/tr/configuration.md +10 -10
- package/docs/tr/eslint.md +336 -0
- package/docs/tr/interest_of_intlayer.md +24 -22
- package/docs/tr/intlayer_with_svelte_kit.md +1 -1
- package/docs/tr/intlayer_with_tanstack+solid.md +5 -3
- package/docs/tr/intlayer_with_tanstack.md +5 -3
- package/docs/tr/lsp.md +113 -174
- package/docs/tr/readme.md +24 -24
- package/docs/uk/configuration.md +10 -10
- package/docs/uk/eslint.md +336 -0
- package/docs/uk/interest_of_intlayer.md +4 -2
- package/docs/uk/intlayer_with_svelte_kit.md +1 -1
- package/docs/uk/intlayer_with_tanstack+solid.md +5 -3
- package/docs/uk/intlayer_with_tanstack.md +5 -3
- package/docs/uk/lsp.md +113 -174
- package/docs/uk/packages/angular-intlayer/exports.md +2 -2
- package/docs/uk/per_locale_file.md +1 -1
- package/docs/uk/readme.md +24 -24
- package/docs/ur/configuration.md +10 -10
- package/docs/ur/eslint.md +336 -0
- package/docs/ur/interest_of_intlayer.md +24 -22
- package/docs/vi/configuration.md +10 -10
- package/docs/vi/eslint.md +336 -0
- package/docs/vi/interest_of_intlayer.md +24 -22
- package/docs/vi/intlayer_with_svelte_kit.md +1 -1
- package/docs/vi/intlayer_with_tanstack+solid.md +5 -3
- package/docs/vi/intlayer_with_tanstack.md +5 -3
- package/docs/vi/lsp.md +115 -176
- package/docs/vi/readme.md +24 -24
- package/docs/zh/configuration.md +10 -10
- package/docs/zh/eslint.md +336 -0
- package/docs/zh/interest_of_intlayer.md +24 -22
- package/docs/zh/intlayer_with_create_react_app.md +4 -0
- package/docs/zh/intlayer_with_lynx+react.md +4 -0
- package/docs/zh/intlayer_with_nextjs_14.md +0 -2
- package/docs/zh/intlayer_with_nextjs_15.md +0 -2
- package/docs/zh/intlayer_with_nextjs_page_router.md +0 -2
- package/docs/zh/intlayer_with_nuxt.md +1 -1
- package/docs/zh/intlayer_with_react_router_v7.md +4 -0
- package/docs/zh/intlayer_with_react_router_v7_fs_routes.md +4 -0
- package/docs/zh/intlayer_with_solid_start.md +1 -1
- package/docs/zh/intlayer_with_svelte_kit.md +1 -1
- package/docs/zh/intlayer_with_tanstack+solid.md +5 -3
- package/docs/zh/intlayer_with_tanstack.md +5 -3
- package/docs/zh/intlayer_with_vite+vue.md +0 -2
- package/docs/zh/lsp.md +113 -174
- package/docs/zh/readme.md +21 -21
- package/docs/zh-TW/eslint.md +336 -0
- package/docs/zh-TW/interest_of_intlayer.md +24 -22
- package/package.json +6 -6
- package/src/generated/docs.entry.ts +20 -0
|
@@ -0,0 +1,336 @@
|
|
|
1
|
+
---
|
|
2
|
+
createdAt: 2026-08-12
|
|
3
|
+
updatedAt: 2026-08-12
|
|
4
|
+
title: ESLint Plugin | Lint rules for Intlayer
|
|
5
|
+
description: Catch hardcoded strings, dynamic calls the Intlayer compiler cannot optimize, and unused dictionary content, with eslint-plugin-intlayer. Works with ESLint and oxlint, across React, Vue, Svelte, Angular and Astro.
|
|
6
|
+
keywords:
|
|
7
|
+
- Intlayer
|
|
8
|
+
- ESLint
|
|
9
|
+
- oxlint
|
|
10
|
+
- Linting
|
|
11
|
+
- i18n
|
|
12
|
+
- Internationalization
|
|
13
|
+
- no-raw-text
|
|
14
|
+
- Hardcoded strings
|
|
15
|
+
- Unused translations
|
|
16
|
+
- Dead content
|
|
17
|
+
- React
|
|
18
|
+
- Vue
|
|
19
|
+
- Svelte
|
|
20
|
+
- Angular
|
|
21
|
+
slugs:
|
|
22
|
+
- doc
|
|
23
|
+
- eslint
|
|
24
|
+
history:
|
|
25
|
+
- version: 9.3.1
|
|
26
|
+
date: 2026-08-12
|
|
27
|
+
changes: "Init history"
|
|
28
|
+
author: aymericzip
|
|
29
|
+
---
|
|
30
|
+
|
|
31
|
+
# ESLint x OXLint Plugin
|
|
32
|
+
|
|
33
|
+
`eslint-plugin-intlayer` catches the kinds of i18n mistake TypeScript cannot:
|
|
34
|
+
|
|
35
|
+
1. **Hardcoded text** that never made it into a dictionary.
|
|
36
|
+
2. **Dynamic calls** that type-check and run, but that the Intlayer compiler cannot optimize.
|
|
37
|
+
3. **Dead content** — dictionaries and fields nothing in the project reads (opt-in).
|
|
38
|
+
|
|
39
|
+
Unknown dictionary keys, unknown field paths and missing locales are already compile errors, so the plugin does not repeat them.
|
|
40
|
+
|
|
41
|
+
## Installation
|
|
42
|
+
|
|
43
|
+
```bash packageManager="npm"
|
|
44
|
+
npm install --save-dev eslint-plugin-intlayer
|
|
45
|
+
```
|
|
46
|
+
|
|
47
|
+
```bash packageManager="pnpm"
|
|
48
|
+
pnpm add --save-dev eslint-plugin-intlayer
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
```bash packageManager="yarn"
|
|
52
|
+
yarn add --dev eslint-plugin-intlayer
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
Requires ESLint 9 or later (flat config).
|
|
56
|
+
|
|
57
|
+
## Usage
|
|
58
|
+
|
|
59
|
+
The plugin runs in both ESLint and [oxlint](https://oxc.rs) — the same rules, the same options.
|
|
60
|
+
|
|
61
|
+
<Tabs defaultTab="eslint">
|
|
62
|
+
<Tab label="ESLint" value="eslint">
|
|
63
|
+
|
|
64
|
+
```javascript fileName="eslint.config.mjs" codeFormat="esm"
|
|
65
|
+
import intlayer from "eslint-plugin-intlayer";
|
|
66
|
+
|
|
67
|
+
export default [...intlayer.configs.recommended];
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
Or enable rules one by one:
|
|
71
|
+
|
|
72
|
+
```javascript fileName="eslint.config.mjs" codeFormat="esm"
|
|
73
|
+
import intlayer from "eslint-plugin-intlayer";
|
|
74
|
+
|
|
75
|
+
export default [
|
|
76
|
+
{
|
|
77
|
+
plugins: { intlayer },
|
|
78
|
+
rules: {
|
|
79
|
+
"intlayer/no-raw-text": "warn",
|
|
80
|
+
"intlayer/static-dictionary-key": "error",
|
|
81
|
+
"intlayer/no-dynamic-field-access": "error",
|
|
82
|
+
"intlayer/enforce-adapter-import": "warn",
|
|
83
|
+
"intlayer/no-unused-content": "warn",
|
|
84
|
+
},
|
|
85
|
+
},
|
|
86
|
+
];
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
</Tab>
|
|
90
|
+
<Tab label="oxlint" value="oxlint">
|
|
91
|
+
|
|
92
|
+
```json fileName=".oxlintrc.json"
|
|
93
|
+
{
|
|
94
|
+
"jsPlugins": ["eslint-plugin-intlayer"],
|
|
95
|
+
"rules": {
|
|
96
|
+
"intlayer/no-raw-text": "warn",
|
|
97
|
+
"intlayer/static-dictionary-key": "error",
|
|
98
|
+
"intlayer/no-dynamic-field-access": "error",
|
|
99
|
+
"intlayer/enforce-adapter-import": "warn"
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
Two caveats: oxlint's JS plugin support is still alpha, and oxlint does not support custom parsers — so `.vue`, `.svelte`, `.astro` and Angular templates are not linted there. Run oxlint over your JS/TS/JSX files and keep ESLint for the rest.
|
|
105
|
+
|
|
106
|
+
`no-unused-content` is left out above on purpose: it needs the working directory and the linted file path from the rule context, which the alpha JS plugin bridge does not guarantee. Run it under ESLint.
|
|
107
|
+
|
|
108
|
+
</Tab>
|
|
109
|
+
</Tabs>
|
|
110
|
+
|
|
111
|
+
### Configs
|
|
112
|
+
|
|
113
|
+
| Config | `no-raw-text` | `static-dictionary-key` | `no-dynamic-field-access` | `enforce-adapter-import` | `no-unused-content` |
|
|
114
|
+
| --------------- | -------------------------- | ----------------------- | ------------------------- | ------------------------ | ------------------- |
|
|
115
|
+
| `recommended` | warn | error | error | off | off |
|
|
116
|
+
| `strict` | error (+ non-JSX literals) | error | error | error | off |
|
|
117
|
+
| `contract-only` | off | error | error | off | off |
|
|
118
|
+
|
|
119
|
+
`recommended` keeps `no-raw-text` at `warn` on purpose: pointing it at an existing codebase surfaces every untranslated string at once, which should not break your build on day one.
|
|
120
|
+
|
|
121
|
+
`enforce-adapter-import` is off by default — enable it explicitly if you want it.
|
|
122
|
+
|
|
123
|
+
`no-unused-content` is off in every config, `strict` included. It is the one rule that reads your Intlayer configuration and walks your source files from disk, so turning it on should be a deliberate choice rather than something a preset does for you.
|
|
124
|
+
|
|
125
|
+
## Rules
|
|
126
|
+
|
|
127
|
+
### `no-raw-text`
|
|
128
|
+
|
|
129
|
+
Reports user-facing text that is not declared in a dictionary. It uses the same detection as `intlayer extract`, so brand names, CSS classes and technical identifiers are ignored.
|
|
130
|
+
|
|
131
|
+
```jsx
|
|
132
|
+
// ✗ Reported
|
|
133
|
+
<h1>Welcome to our documentation</h1>
|
|
134
|
+
<input placeholder="Enter your email address" />
|
|
135
|
+
|
|
136
|
+
// ✓ Fine
|
|
137
|
+
const { title } = useIntlayer("home");
|
|
138
|
+
<h1>{title}</h1>
|
|
139
|
+
```
|
|
140
|
+
|
|
141
|
+
Content declaration files (`*.content.ts`, …) are skipped.
|
|
142
|
+
|
|
143
|
+
To fix a whole file at once, run `npx intlayer extract` and let the compiler move the strings into a dictionary for you.
|
|
144
|
+
|
|
145
|
+
**Options**
|
|
146
|
+
|
|
147
|
+
```javascript fileName="eslint.config.mjs" codeFormat="esm"
|
|
148
|
+
{
|
|
149
|
+
"intlayer/no-raw-text": [
|
|
150
|
+
"warn",
|
|
151
|
+
{
|
|
152
|
+
// Attributes whose value is user-facing text.
|
|
153
|
+
// Default: title, placeholder, alt, aria-label, label
|
|
154
|
+
attributes: ["title", "placeholder", "alt", "aria-label", "label"],
|
|
155
|
+
|
|
156
|
+
// Elements whose content is never user-facing text.
|
|
157
|
+
// Default: code, pre, script, style
|
|
158
|
+
ignoreElements: ["code", "pre", "script", "style"],
|
|
159
|
+
|
|
160
|
+
// Regular expressions for text to never report.
|
|
161
|
+
ignorePatterns: ["^Powered by"],
|
|
162
|
+
|
|
163
|
+
// Also report string literals outside markup. Default: false
|
|
164
|
+
includeStringLiterals: false,
|
|
165
|
+
},
|
|
166
|
+
],
|
|
167
|
+
}
|
|
168
|
+
```
|
|
169
|
+
|
|
170
|
+
### `static-dictionary-key`
|
|
171
|
+
|
|
172
|
+
Requires the dictionary key to be a string literal.
|
|
173
|
+
|
|
174
|
+
The compiler can only pre-load a dictionary when it can read the key directly at the call site. With a computed key it silently skips the optimization and bundles every dictionary instead.
|
|
175
|
+
|
|
176
|
+
```typescript
|
|
177
|
+
// ✗ Reported
|
|
178
|
+
useIntlayer(dictionaryKey);
|
|
179
|
+
useIntlayer(`home-${suffix}`);
|
|
180
|
+
getTranslations({ namespace: page });
|
|
181
|
+
|
|
182
|
+
// ✗ A variable is still not a literal
|
|
183
|
+
const key = "home";
|
|
184
|
+
useIntlayer(key);
|
|
185
|
+
|
|
186
|
+
// ✓ Fine
|
|
187
|
+
useIntlayer("home");
|
|
188
|
+
getTranslations({ namespace: "home" });
|
|
189
|
+
```
|
|
190
|
+
|
|
191
|
+
This applies to `useIntlayer`, `getIntlayer` and every compat adapter (`useTranslation`, `useTranslations`, `formatMessage`, `<FormattedMessage id>`, `<Trans i18nKey>`, …).
|
|
192
|
+
|
|
193
|
+
### `no-dynamic-field-access`
|
|
194
|
+
|
|
195
|
+
Requires the field you read from a dictionary to be statically known.
|
|
196
|
+
|
|
197
|
+
The compiler removes fields it does not see used. A computed access is invisible to it, so the read can return `undefined` at runtime.
|
|
198
|
+
|
|
199
|
+
```typescript
|
|
200
|
+
// ✗ Reported
|
|
201
|
+
const content = useIntlayer("home");
|
|
202
|
+
content[fieldName];
|
|
203
|
+
|
|
204
|
+
const t = useTranslations("home");
|
|
205
|
+
t(messageKey);
|
|
206
|
+
|
|
207
|
+
// ✓ Fine
|
|
208
|
+
content.title;
|
|
209
|
+
content["title"];
|
|
210
|
+
content.items[0];
|
|
211
|
+
t("hero.title");
|
|
212
|
+
```
|
|
213
|
+
|
|
214
|
+
### `enforce-adapter-import`
|
|
215
|
+
|
|
216
|
+
Prefers the `@intlayer/*` compat adapter over the original package. The original only resolves to Intlayer when the bundler alias is configured; the adapter always does. Autofixable with `--fix`.
|
|
217
|
+
|
|
218
|
+
```typescript
|
|
219
|
+
// ✗ Reported
|
|
220
|
+
import { useTranslation } from "react-i18next";
|
|
221
|
+
import { getTranslations } from "next-intl/server";
|
|
222
|
+
|
|
223
|
+
// ✓ Fine
|
|
224
|
+
import { useTranslation } from "@intlayer/react-i18next";
|
|
225
|
+
import { getTranslations } from "@intlayer/next-intl/server";
|
|
226
|
+
```
|
|
227
|
+
|
|
228
|
+
### `no-unused-content`
|
|
229
|
+
|
|
230
|
+
**Off by default.** Reports content nothing in your project reads, plus dictionary keys declared in more than one place.
|
|
231
|
+
|
|
232
|
+
```typescript fileName="src/home.content.ts"
|
|
233
|
+
export default {
|
|
234
|
+
key: "home", // ✗ Reported when no caller anywhere asks for "home"
|
|
235
|
+
content: {
|
|
236
|
+
title: t({ "en-GB": "Title", en: "Title" }),
|
|
237
|
+
|
|
238
|
+
// ✗ Reported when nothing reads `hero`
|
|
239
|
+
hero: {
|
|
240
|
+
subtitle: t({ "en-GB": "Subtitle", en: "Subtitle" }),
|
|
241
|
+
},
|
|
242
|
+
},
|
|
243
|
+
};
|
|
244
|
+
```
|
|
245
|
+
|
|
246
|
+
Unlike the other rules, this one cannot answer from the file in front of it — a field is unused only relative to the whole project. On the first content declaration of a lint run it loads your Intlayer configuration, globs the source files that configuration declares (`build.traversePattern`, `compiler.transformPattern`) and runs the same usage analyser that powers `@intlayer/lsp` and the "unused" strikethrough in the VS Code extension. The result is cached for `cacheTtl` milliseconds, so the scan happens once per run rather than once per file.
|
|
247
|
+
|
|
248
|
+
**Options**
|
|
249
|
+
|
|
250
|
+
```javascript fileName="eslint.config.mjs" codeFormat="esm"
|
|
251
|
+
{
|
|
252
|
+
"intlayer/no-unused-content": [
|
|
253
|
+
"warn",
|
|
254
|
+
{
|
|
255
|
+
// Report dictionary keys nothing references. Default: true
|
|
256
|
+
reportUnusedDictionaries: true,
|
|
257
|
+
|
|
258
|
+
// Report content fields nothing reads. Default: true
|
|
259
|
+
reportUnusedFields: true,
|
|
260
|
+
|
|
261
|
+
// Report keys declared in more than one place. Default: true
|
|
262
|
+
reportDuplicateKeys: true,
|
|
263
|
+
|
|
264
|
+
// Regular expressions for field paths to never report.
|
|
265
|
+
ignoreFields: ["^meta"],
|
|
266
|
+
|
|
267
|
+
// Project root the scan starts from. Default: ESLint's working directory
|
|
268
|
+
baseDir: process.cwd(),
|
|
269
|
+
|
|
270
|
+
// How long one project scan is reused, in ms. Default: 30000
|
|
271
|
+
cacheTtl: 30000,
|
|
272
|
+
},
|
|
273
|
+
],
|
|
274
|
+
}
|
|
275
|
+
```
|
|
276
|
+
|
|
277
|
+
Lower `cacheTtl` when you lint from a long-lived editor server and want your edits reflected sooner; set `baseDir` when a single lint run spans several Intlayer projects in a monorepo.
|
|
278
|
+
|
|
279
|
+
> **It errs towards silence.** A false positive here deletes a translation, so nothing is reported when the dictionary is consumed in a way the analysis cannot follow: the content object passed on as a whole, a translator function bound from it (`const t = useTranslations("home")`), a declaration reached through a direct import (`useDictionary(myDictionary)`), a `nest()` from another dictionary, or a field list made non-exhaustive by a spread. Single-file components (`.vue`, `.svelte`, `.astro`) count as using every field of the dictionaries they mention, because their script blocks are not parsed here.
|
|
280
|
+
|
|
281
|
+
`reportDuplicateKeys` reads the unmerged dictionaries the build writes under `.intlayer/`, so it stays quiet until the project has been built at least once. Two declarations sharing a key are merged, which is a legitimate pattern — the report exists because a field defined on both sides silently keeps only one of the two values.
|
|
282
|
+
|
|
283
|
+
The analyser is loaded from `@intlayer/lsp`, which ships as ESM. The rule therefore needs a Node version that can `require()` an ES module — Node 20.19+ or 22.12+. On anything older it reports nothing rather than failing the lint run.
|
|
284
|
+
|
|
285
|
+
## Frameworks
|
|
286
|
+
|
|
287
|
+
Every rule works across all Intlayer integrations, including inside Vue, Svelte and Angular templates. You only need to tell ESLint which parser reads each file type.
|
|
288
|
+
|
|
289
|
+
| Framework | Files | Parser |
|
|
290
|
+
| ------------------------- | ----------------- | --------------------------------- |
|
|
291
|
+
| React, Preact, Solid, Lit | `.jsx` `.tsx` | `typescript-eslint` |
|
|
292
|
+
| Next.js | `.jsx` `.tsx` | `typescript-eslint` |
|
|
293
|
+
| Vue, Nuxt | `.vue` | `vue-eslint-parser` |
|
|
294
|
+
| Svelte, SvelteKit | `.svelte` | `svelte-eslint-parser` |
|
|
295
|
+
| Angular | `.ts` | `typescript-eslint` |
|
|
296
|
+
| Angular templates | `.component.html` | `@angular-eslint/template-parser` |
|
|
297
|
+
| Astro | `.astro` | `astro-eslint-parser` |
|
|
298
|
+
|
|
299
|
+
```javascript fileName="eslint.config.mjs" codeFormat="esm"
|
|
300
|
+
import intlayer from "eslint-plugin-intlayer";
|
|
301
|
+
import tseslint from "typescript-eslint";
|
|
302
|
+
import vueParser from "vue-eslint-parser";
|
|
303
|
+
import svelteParser from "svelte-eslint-parser";
|
|
304
|
+
import angularTemplateParser from "@angular-eslint/template-parser";
|
|
305
|
+
|
|
306
|
+
export default [
|
|
307
|
+
...intlayer.configs.recommended,
|
|
308
|
+
|
|
309
|
+
{
|
|
310
|
+
files: ["**/*.{ts,tsx,jsx}"],
|
|
311
|
+
languageOptions: { parser: tseslint.parser },
|
|
312
|
+
},
|
|
313
|
+
{
|
|
314
|
+
files: ["**/*.vue"],
|
|
315
|
+
languageOptions: {
|
|
316
|
+
parser: vueParser,
|
|
317
|
+
parserOptions: { parser: tseslint.parser },
|
|
318
|
+
},
|
|
319
|
+
},
|
|
320
|
+
{
|
|
321
|
+
files: ["**/*.svelte"],
|
|
322
|
+
languageOptions: {
|
|
323
|
+
parser: svelteParser,
|
|
324
|
+
parserOptions: { parser: tseslint.parser },
|
|
325
|
+
},
|
|
326
|
+
},
|
|
327
|
+
{
|
|
328
|
+
files: ["**/*.component.html"],
|
|
329
|
+
languageOptions: { parser: angularTemplateParser },
|
|
330
|
+
},
|
|
331
|
+
];
|
|
332
|
+
```
|
|
333
|
+
|
|
334
|
+
Install only the parsers your project needs.
|
|
335
|
+
|
|
336
|
+
> **Known limitation.** In Vue and Angular templates, an expression such as `{{ content[key] }}` is not checked by `no-dynamic-field-access`. Dynamic reads written in the script block are caught normally.
|
|
@@ -207,7 +207,7 @@ export const ComponentExample = () => {
|
|
|
207
207
|
This approach allows you to:
|
|
208
208
|
|
|
209
209
|
1. **Increase the speed of development**
|
|
210
|
-
- `.content.{
|
|
210
|
+
- `.content.{ts|js|mjs|cjs|json|tsx|jsx|md|mdx|yaml|yml}` files can be created using a VSCode extension
|
|
211
211
|
- Autocompletion AI tools in your IDE (such as GitHub Copilot) can help you declare your content, reducing copy/paste
|
|
212
212
|
|
|
213
213
|
2. **Clean your codebase**
|
|
@@ -231,27 +231,27 @@ This approach allows you to:
|
|
|
231
231
|
|
|
232
232
|
## Additional features of Intlayer
|
|
233
233
|
|
|
234
|
-
| Feature | Description
|
|
235
|
-
| ------------------------------------------------------------------------------------------------------------------------- |
|
|
236
|
-
|  | **Cross-Frameworks Support**<br><br>Intlayer is compatible with all major frameworks and libraries, including Next.js, React, Vite, Vue.js, Nuxt, Preact, Express, and more.
|
|
237
|
-
|  | **JavaScript-Powered Content Management**<br><br>Harness the flexibility of JavaScript to define and manage your content efficiently. <br><br> - [Content declaration](https://intlayer.org/doc/concept/content)
|
|
238
|
-
| <img src="https://github.com/aymericzip/intlayer/blob/main/docs/assets/compiler.jpg?raw=true" alt="Feature" width="700"> | **Compiler**<br><br>The Intlayer Compiler extract automatically the content from the components and generate the dictionary files.<br><br> - [Compiler](https://intlayer.org/doc/compiler)
|
|
239
|
-
|  | **Per-Locale Content Declaration File**<br><br>Speed up your development by declaring your content once, before auto generation.<br><br> - [Per-Locale Content Declaration File](https://intlayer.org/doc/concept/per-locale-file)
|
|
240
|
-
|  | **Type-Safe Environment**<br><br>Leverage TypeScript to ensure your content definitions and code are error-free, while also benefiting from IDE autocompletion.<br><br> - [TypeScript configuration](https://intlayer.org/doc/environment/vite-and-react#configure-typescript)
|
|
241
|
-
|  | **Simplified Setup**<br><br>Get up and running quickly with minimal configuration. Adjust settings for internationalization, routing, AI, build, and content handling with ease. <br><br> - [Explore Next.js integration](https://intlayer.org/doc/environment/nextjs)
|
|
242
|
-
|  | **Simplified Content Retrieval**<br><br>No need to call your `t` function for each piece of content. Retrieve all your content directly using a single hook.<br><br> - [React integration](https://intlayer.org/doc/environment/create-react-app)
|
|
243
|
-
|  | **Consistent Server Component Implementation**<br><br>Perfectly suited for Next.js server components, use the same implementation for both client and server components, no need to pass your `t` function across each server component. <br><br> - [Server Components](https://intlayer.org/doc/environment/nextjs#step-7-utilize-content-in-your-code)
|
|
244
|
-
|  | **Organized Codebase**<br><br>Keep your codebase more organized: 1 component = 1 dictionary in the same folder. Translations close to their respective components enhance maintainability and clarity. <br><br> - [How Intlayer works](https://intlayer.org/doc/concept/how-works-intlayer)
|
|
245
|
-
|  | **Enhanced Routing**<br><br>Full support of app routing, adapting seamlessly to complex application structures, for Next.js, React, Vite, Vue.js, etc.<br><br> - [Explore Next.js integration](https://intlayer.org/doc/environment/nextjs)
|
|
246
|
-
|  | **Markdown Support**<br><br>Import and interpret locale files and remote Markdown for multilingual content like privacy policies, documentation, etc. Interpret and make Markdown metadata accessible in your code.<br><br> - [Content files](https://intlayer.org/doc/concept/content/file)
|
|
247
|
-
|  | **Free Visual Editor & CMS**<br><br>A free visual editor and CMS are available for content writers, removing the need for a localization platform. Keep your content synchronized using Git, or externalize it totally or partially with the CMS.<br><br> - [Intlayer Editor](https://intlayer.org/doc/concept/editor) <br> - [Intlayer CMS](https://intlayer.org/doc/concept/cms)
|
|
248
|
-
|  | **Tree-shakable Content**<br><br>Tree-shakable content, reducing the size of the final bundle. Loads content per component, excluding any unused content from your bundle. Supports lazy loading to enhance app loading efficiency. <br><br> - [App build optimization](https://intlayer.org/doc/concept/how-works-intlayer#app-build-optimization)
|
|
249
|
-
|  | **Static Rendering**<br><br>Doesn't block Static Rendering. <br><br> - [Next.js integration](https://intlayer.org/doc/environment/nextjs)
|
|
250
|
-
|  | **AI-Powered Translation**<br><br>Transform your website into 231 languages with just one click using Intlayer's advanced AI-powered translation tools using your own AI provider/API key. <br><br> - [CI/CD integration](https://intlayer.org/doc/concept/ci-cd) <br> - [Intlayer CLI](https://intlayer.org/doc/concept/cli) <br> - [Auto fill](https://intlayer.org/doc/concept/auto-fill)
|
|
251
|
-
|  | **MCP Server Integration**<br><br>Provides an MCP (Model Context Protocol) server for IDE automation, enabling seamless content management and i18n workflows directly within your development environment. <br><br> - [MCP Server](https://github.com/aymericzip/intlayer/blob/main/docs/en/mcp_server.md)
|
|
252
|
-
|  | **VSCode Extension**<br><br>Intlayer provides a VSCode extension to help you manage your content and translations, building your dictionaries, translating your content, and more. <br><br> - [VSCode Extension](https://intlayer.org/doc/vs-code-extension)
|
|
253
|
-
|  | **Interoperability**<br><br>Allows interoperability with react-i18next, next-i18next, next-intl, and react-intl. <br><br> - [Intlayer and react-intl](https://intlayer.org/blog/intlayer-with-react-intl) <br> - [Intlayer and next-intl](https://intlayer.org/blog/intlayer-with-next-intl) <br> - [Intlayer and next-i18next](https://intlayer.org/blog/intlayer-with-next-i18next)
|
|
254
|
-
| Testing Missing Translations (CLI/CI) | ✅ CLI: npx intlayer content test (CI-friendly audit)
|
|
234
|
+
| Feature | Description |
|
|
235
|
+
| ------------------------------------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
236
|
+
|  | **Cross-Frameworks Support**<br><br>Intlayer is compatible with all major frameworks and libraries, including Next.js, React, Vite, Vue.js, Nuxt, Preact, Express, and more. |
|
|
237
|
+
|  | **JavaScript-Powered Content Management**<br><br>Harness the flexibility of JavaScript to define and manage your content efficiently. <br><br> - [Content declaration](https://intlayer.org/doc/concept/content) |
|
|
238
|
+
| <img src="https://github.com/aymericzip/intlayer/blob/main/docs/assets/compiler.jpg?raw=true" alt="Feature" width="700"> | **Compiler**<br><br>The Intlayer Compiler extract automatically the content from the components and generate the dictionary files.<br><br> - [Compiler](https://intlayer.org/doc/compiler) |
|
|
239
|
+
|  | **Per-Locale Content Declaration File**<br><br>Speed up your development by declaring your content once, before auto generation.<br><br> - [Per-Locale Content Declaration File](https://intlayer.org/doc/concept/per-locale-file) |
|
|
240
|
+
|  | **Type-Safe Environment**<br><br>Leverage TypeScript to ensure your content definitions and code are error-free, while also benefiting from IDE autocompletion.<br><br> - [TypeScript configuration](https://intlayer.org/doc/environment/vite-and-react#configure-typescript) |
|
|
241
|
+
|  | **Simplified Setup**<br><br>Get up and running quickly with minimal configuration. Adjust settings for internationalization, routing, AI, build, and content handling with ease. <br><br> - [Explore Next.js integration](https://intlayer.org/doc/environment/nextjs) |
|
|
242
|
+
|  | **Simplified Content Retrieval**<br><br>No need to call your `t` function for each piece of content. Retrieve all your content directly using a single hook.<br><br> - [React integration](https://intlayer.org/doc/environment/create-react-app) |
|
|
243
|
+
|  | **Consistent Server Component Implementation**<br><br>Perfectly suited for Next.js server components, use the same implementation for both client and server components, no need to pass your `t` function across each server component. <br><br> - [Server Components](https://intlayer.org/doc/environment/nextjs#step-7-utilize-content-in-your-code) |
|
|
244
|
+
|  | **Organized Codebase**<br><br>Keep your codebase more organized: 1 component = 1 dictionary in the same folder. Translations close to their respective components enhance maintainability and clarity. <br><br> - [How Intlayer works](https://intlayer.org/doc/concept/how-works-intlayer) |
|
|
245
|
+
|  | **Enhanced Routing**<br><br>Full support of app routing, adapting seamlessly to complex application structures, for Next.js, React, Vite, Vue.js, etc.<br><br> - [Explore Next.js integration](https://intlayer.org/doc/environment/nextjs) |
|
|
246
|
+
|  | **Markdown Support**<br><br>Import and interpret locale files and remote Markdown for multilingual content like privacy policies, documentation, etc. Interpret and make Markdown metadata accessible in your code.<br><br> - [Content files](https://intlayer.org/doc/concept/content/file) |
|
|
247
|
+
|  | **Free Visual Editor & CMS**<br><br>A free visual editor and CMS are available for content writers, removing the need for a localization platform. Keep your content synchronized using Git, or externalize it totally or partially with the CMS.<br><br> - [Intlayer Editor](https://intlayer.org/doc/concept/editor) <br> - [Intlayer CMS](https://intlayer.org/doc/concept/cms) |
|
|
248
|
+
|  | **Tree-shakable Content**<br><br>Tree-shakable content, reducing the size of the final bundle. Loads content per component, excluding any unused content from your bundle. Supports lazy loading to enhance app loading efficiency. <br><br> - [App build optimization](https://intlayer.org/doc/concept/how-works-intlayer#app-build-optimization) |
|
|
249
|
+
|  | **Static Rendering**<br><br>Doesn't block Static Rendering. <br><br> - [Next.js integration](https://intlayer.org/doc/environment/nextjs) |
|
|
250
|
+
|  | **AI-Powered Translation**<br><br>Transform your website into 231 languages with just one click using Intlayer's advanced AI-powered translation tools using your own AI provider/API key. <br><br> - [CI/CD integration](https://intlayer.org/doc/concept/ci-cd) <br> - [Intlayer CLI](https://intlayer.org/doc/concept/cli) <br> - [Auto fill](https://intlayer.org/doc/concept/auto-fill) |
|
|
251
|
+
|  | **MCP Server Integration**<br><br>Provides an MCP (Model Context Protocol) server for IDE automation, enabling seamless content management and i18n workflows directly within your development environment. <br><br> - [MCP Server](https://github.com/aymericzip/intlayer/blob/main/docs/en/mcp_server.md) |
|
|
252
|
+
|  | **VSCode Extension**<br><br>Intlayer provides a VSCode extension to help you manage your content and translations, building your dictionaries, translating your content, and more. <br><br> - [VSCode Extension](https://intlayer.org/doc/vs-code-extension) |
|
|
253
|
+
|  | **Interoperability**<br><br>Allows interoperability with react-i18next, next-i18next, next-intl, and react-intl. <br><br> - [Intlayer and react-intl](https://intlayer.org/blog/intlayer-with-react-intl) <br> - [Intlayer and next-intl](https://intlayer.org/blog/intlayer-with-next-intl) <br> - [Intlayer and next-i18next](https://intlayer.org/blog/intlayer-with-next-i18next) <br> - [Intlayer compat adapters](https://intlayer.org/doc/compatibility) |
|
|
254
|
+
| Testing Missing Translations (CLI/CI) | ✅ CLI: npx intlayer content test (CI-friendly audit) |
|
|
255
255
|
|
|
256
256
|
## Comparison of Intlayer with other solutions
|
|
257
257
|
|
|
@@ -290,3 +290,5 @@ GitHub stars are a strong indicator of a project's popularity, community trust,
|
|
|
290
290
|
`intlayer` can also help to manage your `react-intl`, `react-i18next`, `next-intl`, `next-i18next`, and `vue-i18n` namespaces.
|
|
291
291
|
|
|
292
292
|
Using `intlayer`, you can declare your content in the format of your favorite i18n library, and intlayer will generate your namespaces in the location of your choice (example: `/messages/{{locale}}/{{namespace}}.json`).
|
|
293
|
+
|
|
294
|
+
If you want to keep using the API of your current i18n library, `intlayer` also provides **compat adapters**: packages exposing the exact same API as `react-i18next`, `next-intl`, `react-intl`, `vue-i18n`, and more, but served by Intlayer dictionaries. This lets you migrate progressively without rewriting your code. See the [Compat Adapters documentation](https://github.com/aymericzip/intlayer/blob/main/docs/docs/en/compat/index.md).
|
|
@@ -33,59 +33,56 @@ author: aymericzip
|
|
|
33
33
|
|
|
34
34
|
See [Application Template](https://github.com/aymericzip/intlayer-react-cra-template) on GitHub.
|
|
35
35
|
|
|
36
|
-
##
|
|
36
|
+
## Why Intlayer over alternatives?
|
|
37
37
|
|
|
38
|
-
|
|
38
|
+
Compared to main solutions like `react-i18next` or `i18next`, Intlayer is a solution that comes with integrated optimisations such as:
|
|
39
39
|
|
|
40
|
-
<
|
|
40
|
+
<AccordionGroup>
|
|
41
41
|
|
|
42
|
-
|
|
42
|
+
<Accordion header="Full React coverage">
|
|
43
43
|
|
|
44
|
-
|
|
45
|
-
npx intlayer init --interactive
|
|
46
|
-
```
|
|
44
|
+
Intlayer is optimised to work perfectly with React by offering **component-level content scoping**, **lazy-loaded translations**, and all the features needed for scaling internationalisation (i18n).
|
|
47
45
|
|
|
48
|
-
|
|
49
|
-
pnpm dlx intlayer@canary init --interactive
|
|
50
|
-
```
|
|
46
|
+
</Accordion>
|
|
51
47
|
|
|
52
|
-
|
|
53
|
-
yarn dlx intlayer@canary init --interactive
|
|
54
|
-
```
|
|
48
|
+
<Accordion header="Bundle size">
|
|
55
49
|
|
|
56
|
-
|
|
57
|
-
bunx intlayer@canary init --interactive
|
|
58
|
-
```
|
|
50
|
+
Instead of loading massive JSON files into your pages, load only the necessary content. Intlayer helps **reduce your bundle and page sizes by up to 50%**.
|
|
59
51
|
|
|
60
|
-
>
|
|
52
|
+
</Accordion>
|
|
61
53
|
|
|
62
|
-
>
|
|
54
|
+
<Accordion header="Maintainability">
|
|
63
55
|
|
|
64
|
-
|
|
65
|
-
npm install intlayer react-intlayer react-scripts-intlayer
|
|
66
|
-
```
|
|
56
|
+
Scoping your application's content **facilitates maintenance** for large-scale applications. You can duplicate or delete a single feature folder without the mental burden of reviewing your entire content codebase. Additionally, Intlayer is **fully typed** to ensure your content's accuracy.
|
|
67
57
|
|
|
68
|
-
|
|
69
|
-
pnpm add intlayer react-intlayer react-scripts-intlayer
|
|
70
|
-
```
|
|
58
|
+
</Accordion>
|
|
71
59
|
|
|
72
|
-
|
|
73
|
-
yarn add intlayer react-intlayer react-scripts-intlayer
|
|
74
|
-
```
|
|
60
|
+
<Accordion header="AI Agent">
|
|
75
61
|
|
|
76
|
-
|
|
77
|
-
bun add intlayer react-intlayer react-scripts-intlayer
|
|
78
|
-
```
|
|
62
|
+
Co-locating content **reduces the context needed** by Large Language Models (LLMs). Intlayer also comes with a suite of tools, such as a **CLI** to test for missing translations, **[LSP](https://github.com/aymericzip/intlayer/blob/main/docs/docs/en-GB/lsp.md)**, **[MCP](https://github.com/aymericzip/intlayer/blob/main/docs/docs/en-GB/mcp_server.md)**, and **[agent skills](https://github.com/aymericzip/intlayer/blob/main/docs/docs/en-GB/agent_skills.md)**, to make the developer experience (DX) even smoother for AI agents.
|
|
79
63
|
|
|
80
|
-
|
|
64
|
+
</Accordion>
|
|
81
65
|
|
|
82
|
-
|
|
66
|
+
<Accordion header="Automation">
|
|
83
67
|
|
|
84
|
-
|
|
68
|
+
Use automation to translate in your CI/CD pipeline using the LLM of your choice at the cost of your AI provider. Intlayer also offers a **compiler** to automate content extraction, as well as a [web platform](https://github.com/aymericzip/intlayer/blob/main/docs/docs/en-GB/intlayer_CMS.md) to help **translate in the background**.
|
|
85
69
|
|
|
86
|
-
|
|
70
|
+
</Accordion>
|
|
87
71
|
|
|
88
|
-
|
|
72
|
+
<Accordion header="Performance">
|
|
73
|
+
|
|
74
|
+
Connecting massive JSON files to components can lead to performance and reactivity issues. Intlayer optimises your content loading at build time.
|
|
75
|
+
|
|
76
|
+
</Accordion>
|
|
77
|
+
|
|
78
|
+
<Accordion header="Scaling with none-dev">
|
|
79
|
+
|
|
80
|
+
More than just an i18n solution, Intlayer provides a **self-hosted [visual editor](https://github.com/aymericzip/intlayer/blob/main/docs/docs/en-GB/intlayer_visual_editor.md)** and a **[full CMS](https://github.com/aymericzip/intlayer/blob/main/docs/docs/en-GB/intlayer_CMS.md)** to help you manage your multilingual content in **real-time**, making collaboration with translators, copywriters, and other team members seamless. Content can be stored locally and/or remotely.
|
|
81
|
+
|
|
82
|
+
</Accordion>
|
|
83
|
+
</AccordionGroup>
|
|
84
|
+
|
|
85
|
+
---
|
|
89
86
|
|
|
90
87
|
## Step-by-Step Guide to Set Up Intlayer in a React Application
|
|
91
88
|
|
|
@@ -404,7 +404,7 @@ export const getLocale = (event: RequestEvent): Locale => {
|
|
|
404
404
|
};
|
|
405
405
|
```
|
|
406
406
|
|
|
407
|
-
> `getLocaleFromStorage` will check the locale from header or cookie depending on your configuration. See [Configuration](https://intlayer.org/doc/configuration) for more details.
|
|
407
|
+
> `getLocaleFromStorage` will check the locale from header or cookie depending on your configuration. See [Configuration](https://intlayer.org/doc/concept/configuration) for more details.
|
|
408
408
|
|
|
409
409
|
> The `localeDetector` function will process the `Accept-Language` header and return the best match.
|
|
410
410
|
|
|
@@ -253,19 +253,21 @@ import {
|
|
|
253
253
|
HeadContent,
|
|
254
254
|
Scripts,
|
|
255
255
|
createRootRouteWithContext,
|
|
256
|
+
getRouteApi,
|
|
256
257
|
} from "@tanstack/solid-router";
|
|
257
258
|
import { HydrationScript } from "solid-js/web";
|
|
258
259
|
import { Suspense, type ParentComponent } from "solid-js";
|
|
259
260
|
import { IntlayerProvider } from "solid-intlayer";
|
|
260
261
|
import { defaultLocale, getHTMLTextDir } from "intlayer";
|
|
261
|
-
|
|
262
|
+
|
|
263
|
+
const localeRoute = getRouteApi("/{-$locale}");
|
|
262
264
|
|
|
263
265
|
export const Route = createRootRouteWithContext()({
|
|
264
266
|
shellComponent: RootComponent,
|
|
265
267
|
});
|
|
266
268
|
|
|
267
269
|
const RootComponent: ParentComponent = (props) => {
|
|
268
|
-
const params =
|
|
270
|
+
const params = localeRoute.useParams();
|
|
269
271
|
const locale = params()?.locale ?? defaultLocale;
|
|
270
272
|
|
|
271
273
|
return (
|
|
@@ -551,7 +553,7 @@ As seen in Step 5, you can manage the `lang` and `dir` attributes of the `html`
|
|
|
551
553
|
|
|
552
554
|
```tsx fileName="src/routes/__root.tsx"
|
|
553
555
|
const RootComponent: ParentComponent = (props) => {
|
|
554
|
-
const params =
|
|
556
|
+
const params = localeRoute.useParams();
|
|
555
557
|
const locale = params()?.locale ?? defaultLocale;
|
|
556
558
|
|
|
557
559
|
return (
|
|
@@ -270,13 +270,15 @@ Configure your root layout to support internationalisation by using `useParams`
|
|
|
270
270
|
```tsx fileName="src/routes/__root.tsx"
|
|
271
271
|
import {
|
|
272
272
|
createRootRouteWithContext,
|
|
273
|
+
getRouteApi,
|
|
273
274
|
HeadContent,
|
|
274
275
|
Scripts,
|
|
275
276
|
} from "@tanstack/react-router";
|
|
276
277
|
import { defaultLocale, getHTMLTextDir } from "intlayer";
|
|
277
278
|
import { type ReactNode } from "react";
|
|
278
279
|
import { IntlayerProvider } from "react-intlayer";
|
|
279
|
-
|
|
280
|
+
|
|
281
|
+
const localeRoute = getRouteApi("/{-$locale}");
|
|
280
282
|
|
|
281
283
|
export const Route = createRootRouteWithContext<{}>()({
|
|
282
284
|
head: () => ({
|
|
@@ -298,7 +300,7 @@ export const Route = createRootRouteWithContext<{}>()({
|
|
|
298
300
|
});
|
|
299
301
|
|
|
300
302
|
function RootDocument({ children }: { children: ReactNode }) {
|
|
301
|
-
const params =
|
|
303
|
+
const params = localeRoute.useParams();
|
|
302
304
|
const locale = params?.locale ?? defaultLocale;
|
|
303
305
|
|
|
304
306
|
return (
|
|
@@ -631,7 +633,7 @@ As seen in Step 5, you can manage the `lang` and `dir` attributes of the `html`
|
|
|
631
633
|
|
|
632
634
|
```tsx fileName="src/routes/__root.tsx"
|
|
633
635
|
function RootDocument({ children }: { children: ReactNode }) {
|
|
634
|
-
const params =
|
|
636
|
+
const params = localeRoute.useParams();
|
|
635
637
|
const locale = params?.locale ?? defaultLocale;
|
|
636
638
|
|
|
637
639
|
return (
|