@intlayer/docs 7.0.3 → 7.0.4

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.
Files changed (159) hide show
  1. package/blog/ar/intlayer_with_i18next.md +68 -106
  2. package/blog/ar/intlayer_with_next-i18next.md +84 -288
  3. package/blog/ar/intlayer_with_next-intl.md +58 -337
  4. package/blog/ar/intlayer_with_react-i18next.md +68 -290
  5. package/blog/ar/intlayer_with_react-intl.md +63 -266
  6. package/blog/de/intlayer_with_i18next.md +77 -97
  7. package/blog/de/intlayer_with_next-i18next.md +69 -296
  8. package/blog/de/intlayer_with_next-intl.md +59 -340
  9. package/blog/de/intlayer_with_react-i18next.md +68 -290
  10. package/blog/de/intlayer_with_react-intl.md +62 -264
  11. package/blog/en/intlayer_with_i18next.md +67 -103
  12. package/blog/en/intlayer_with_next-i18next.md +69 -294
  13. package/blog/en/intlayer_with_next-intl.md +48 -300
  14. package/blog/en/intlayer_with_react-i18next.md +61 -289
  15. package/blog/en/intlayer_with_react-intl.md +61 -284
  16. package/blog/en/next-i18next_vs_next-intl_vs_intlayer.md +1 -1
  17. package/blog/en-GB/intlayer_with_i18next.md +67 -103
  18. package/blog/en-GB/intlayer_with_next-i18next.md +71 -292
  19. package/blog/en-GB/intlayer_with_next-intl.md +58 -337
  20. package/blog/en-GB/intlayer_with_react-i18next.md +67 -289
  21. package/blog/en-GB/intlayer_with_react-intl.md +61 -264
  22. package/blog/es/intlayer_with_i18next.md +67 -103
  23. package/blog/es/intlayer_with_next-i18next.md +71 -296
  24. package/blog/es/intlayer_with_next-intl.md +57 -338
  25. package/blog/es/intlayer_with_react-i18next.md +68 -290
  26. package/blog/es/intlayer_with_react-intl.md +62 -265
  27. package/blog/fr/intlayer_with_i18next.md +66 -104
  28. package/blog/fr/intlayer_with_next-i18next.md +82 -285
  29. package/blog/fr/intlayer_with_next-intl.md +57 -338
  30. package/blog/fr/intlayer_with_react-i18next.md +67 -289
  31. package/blog/fr/intlayer_with_react-intl.md +61 -264
  32. package/blog/hi/intlayer_with_i18next.md +68 -104
  33. package/blog/hi/intlayer_with_next-i18next.md +74 -299
  34. package/blog/hi/intlayer_with_next-intl.md +57 -239
  35. package/blog/hi/intlayer_with_react-i18next.md +69 -291
  36. package/blog/hi/intlayer_with_react-intl.md +65 -268
  37. package/blog/id/intlayer_with_i18next.md +126 -0
  38. package/blog/id/intlayer_with_next-i18next.md +142 -0
  39. package/blog/id/intlayer_with_next-intl.md +113 -0
  40. package/blog/id/intlayer_with_react-i18next.md +124 -0
  41. package/blog/id/intlayer_with_react-intl.md +122 -0
  42. package/blog/it/intlayer_with_i18next.md +67 -103
  43. package/blog/it/intlayer_with_next-i18next.md +71 -296
  44. package/blog/it/intlayer_with_next-intl.md +57 -338
  45. package/blog/it/intlayer_with_react-i18next.md +68 -290
  46. package/blog/it/intlayer_with_react-intl.md +62 -265
  47. package/blog/ja/intlayer_with_i18next.md +68 -103
  48. package/blog/ja/intlayer_with_next-i18next.md +85 -283
  49. package/blog/ja/intlayer_with_next-intl.md +58 -336
  50. package/blog/ja/intlayer_with_react-i18next.md +68 -290
  51. package/blog/ja/intlayer_with_react-intl.md +62 -264
  52. package/blog/ko/intlayer_with_i18next.md +80 -96
  53. package/blog/ko/intlayer_with_next-i18next.md +85 -287
  54. package/blog/ko/intlayer_with_next-intl.md +68 -327
  55. package/blog/ko/intlayer_with_react-i18next.md +68 -290
  56. package/blog/ko/intlayer_with_react-intl.md +64 -266
  57. package/blog/pl/intlayer_with_i18next.md +126 -0
  58. package/blog/pl/intlayer_with_next-i18next.md +142 -0
  59. package/blog/pl/intlayer_with_next-intl.md +111 -0
  60. package/blog/pl/intlayer_with_react-i18next.md +124 -0
  61. package/blog/pl/intlayer_with_react-intl.md +122 -0
  62. package/blog/pt/intlayer_with_i18next.md +67 -103
  63. package/blog/pt/intlayer_with_next-i18next.md +72 -293
  64. package/blog/pt/intlayer_with_next-intl.md +57 -256
  65. package/blog/pt/intlayer_with_react-i18next.md +104 -78
  66. package/blog/pt/intlayer_with_react-intl.md +62 -266
  67. package/blog/ru/intlayer_with_i18next.md +66 -104
  68. package/blog/ru/intlayer_with_next-i18next.md +71 -296
  69. package/blog/ru/intlayer_with_next-intl.md +58 -337
  70. package/blog/ru/intlayer_with_react-i18next.md +68 -290
  71. package/blog/ru/intlayer_with_react-intl.md +62 -265
  72. package/blog/tr/intlayer_with_i18next.md +71 -107
  73. package/blog/tr/intlayer_with_next-i18next.md +72 -297
  74. package/blog/tr/intlayer_with_next-intl.md +58 -339
  75. package/blog/tr/intlayer_with_react-i18next.md +69 -291
  76. package/blog/tr/intlayer_with_react-intl.md +63 -285
  77. package/blog/vi/intlayer_with_i18next.md +126 -0
  78. package/blog/vi/intlayer_with_next-i18next.md +142 -0
  79. package/blog/vi/intlayer_with_next-intl.md +111 -0
  80. package/blog/vi/intlayer_with_react-i18next.md +124 -0
  81. package/blog/vi/intlayer_with_react-intl.md +122 -0
  82. package/blog/zh/intlayer_with_i18next.md +67 -102
  83. package/blog/zh/intlayer_with_next-i18next.md +72 -296
  84. package/blog/zh/intlayer_with_next-intl.md +58 -336
  85. package/blog/zh/intlayer_with_react-i18next.md +68 -290
  86. package/blog/zh/intlayer_with_react-intl.md +63 -106
  87. package/dist/cjs/generated/blog.entry.cjs +13 -1
  88. package/dist/cjs/generated/blog.entry.cjs.map +1 -1
  89. package/dist/cjs/generated/docs.entry.cjs +13 -1
  90. package/dist/cjs/generated/docs.entry.cjs.map +1 -1
  91. package/dist/cjs/generated/frequentQuestions.entry.cjs +13 -1
  92. package/dist/cjs/generated/frequentQuestions.entry.cjs.map +1 -1
  93. package/dist/cjs/generated/legal.entry.cjs +13 -1
  94. package/dist/cjs/generated/legal.entry.cjs.map +1 -1
  95. package/dist/esm/generated/blog.entry.mjs +13 -2
  96. package/dist/esm/generated/blog.entry.mjs.map +1 -1
  97. package/dist/esm/generated/docs.entry.mjs +13 -2
  98. package/dist/esm/generated/docs.entry.mjs.map +1 -1
  99. package/dist/esm/generated/frequentQuestions.entry.mjs +13 -2
  100. package/dist/esm/generated/frequentQuestions.entry.mjs.map +1 -1
  101. package/dist/esm/generated/legal.entry.mjs +13 -2
  102. package/dist/esm/generated/legal.entry.mjs.map +1 -1
  103. package/dist/types/generated/blog.entry.d.ts.map +1 -1
  104. package/dist/types/generated/docs.entry.d.ts.map +1 -1
  105. package/dist/types/generated/frequentQuestions.entry.d.ts.map +1 -1
  106. package/dist/types/generated/legal.entry.d.ts.map +1 -1
  107. package/docs/ar/plugins/sync-json.md +244 -0
  108. package/docs/de/plugins/sync-json.md +244 -0
  109. package/docs/de/releases/v7.md +1 -18
  110. package/docs/en/CI_CD.md +1 -1
  111. package/docs/en/configuration.md +1 -1
  112. package/docs/en/formatters.md +1 -1
  113. package/docs/en/how_works_intlayer.md +1 -1
  114. package/docs/en/intlayer_CMS.md +1 -1
  115. package/docs/en/intlayer_cli.md +26 -1
  116. package/docs/en/intlayer_with_nextjs_14.md +3 -1
  117. package/docs/en/intlayer_with_nextjs_15.md +3 -1
  118. package/docs/en/intlayer_with_nextjs_16.md +3 -1
  119. package/docs/en/intlayer_with_nextjs_page_router.md +1 -1
  120. package/docs/en/intlayer_with_nuxt.md +1 -1
  121. package/docs/en/intlayer_with_react_native+expo.md +1 -1
  122. package/docs/en/intlayer_with_react_router_v7.md +1 -1
  123. package/docs/en/intlayer_with_tanstack.md +1 -1
  124. package/docs/en/intlayer_with_vite+preact.md +1 -1
  125. package/docs/en/intlayer_with_vite+react.md +1 -1
  126. package/docs/en/intlayer_with_vite+solid.md +1 -1
  127. package/docs/en/intlayer_with_vite+svelte.md +1 -1
  128. package/docs/en/intlayer_with_vite+vue.md +1 -1
  129. package/docs/en/plugins/sync-json.md +1 -1
  130. package/docs/en/roadmap.md +1 -1
  131. package/docs/en-GB/plugins/sync-json.md +244 -0
  132. package/docs/es/plugins/sync-json.md +244 -0
  133. package/docs/es/releases/v7.md +1 -18
  134. package/docs/fr/intlayer_with_nextjs_16.md +2 -51
  135. package/docs/fr/plugins/sync-json.md +244 -0
  136. package/docs/fr/releases/v7.md +1 -18
  137. package/docs/hi/intlayer_with_nextjs_16.md +3 -2
  138. package/docs/hi/plugins/sync-json.md +244 -0
  139. package/docs/id/plugins/sync-json.md +244 -0
  140. package/docs/id/releases/v7.md +1 -18
  141. package/docs/it/plugins/sync-json.md +244 -0
  142. package/docs/it/releases/v7.md +1 -18
  143. package/docs/ja/intlayer_with_nextjs_16.md +44 -205
  144. package/docs/ja/plugins/sync-json.md +244 -0
  145. package/docs/ja/releases/v7.md +1 -18
  146. package/docs/ko/plugins/sync-json.md +244 -0
  147. package/docs/ko/releases/v7.md +1 -18
  148. package/docs/pl/plugins/sync-json.md +244 -0
  149. package/docs/pt/intlayer_with_nextjs_16.md +1 -52
  150. package/docs/pt/plugins/sync-json.md +244 -0
  151. package/docs/ru/plugins/sync-json.md +244 -0
  152. package/docs/tr/plugins/sync-json.md +245 -0
  153. package/docs/vi/plugins/sync-json.md +244 -0
  154. package/docs/zh/plugins/sync-json.md +244 -0
  155. package/package.json +14 -14
  156. package/src/generated/blog.entry.ts +26 -3
  157. package/src/generated/docs.entry.ts +26 -3
  158. package/src/generated/frequentQuestions.entry.ts +26 -3
  159. package/src/generated/legal.entry.ts +26 -3
@@ -1,345 +1,122 @@
1
1
  ---
2
2
  createdAt: 2025-01-02
3
- updatedAt: 2025-06-29
4
- title: Intlayer and react-intl
5
- description: Integrate Intlayer with react-intl for a React app
3
+ updatedAt: 2025-10-29
4
+ title: How to automate your react-intl JSON translations using Intlayer
5
+ description: Automate your JSON translations with Intlayer and react-intl for enhanced internationalization in React applications.
6
6
  keywords:
7
7
  - react-intl
8
8
  - Intlayer
9
9
  - Internationalization
10
10
  - Blog
11
- - Next.js
11
+ - i18n
12
12
  - JavaScript
13
13
  - React
14
+ - FormatJS
14
15
  slugs:
15
16
  - blog
16
17
  - intlayer-with-react-intl
18
+ history:
19
+ - version: 7.0.0
20
+ date: 2025-10-29
21
+ changes: Change to syncJSON plugin
17
22
  ---
18
23
 
19
- # React Internationalization (i18n) with **react-intl** and Intlayer
24
+ # How to automate your react-intl JSON translations using Intlayer
20
25
 
21
- This guide shows how to integrate **Intlayer** with **react-intl** to manage translations in a React application. You’ll declare your translatable content with Intlayer and then consume those messages with **react-intl**, a popular library from the [FormatJS](https://formatjs.io/docs/react-intl) ecosystem.
26
+ ## What is Intlayer?
22
27
 
23
- ## Overview
28
+ **Intlayer** is an innovative, open-source internationalization library designed to address the shortcomings of traditional i18n solutions. It offers a modern approach to content management in React applications.
24
29
 
25
- - **Intlayer** allows you to store translations in **component-level** content declaration files (JSON, JS, TS, etc.) within your project.
26
- - **react-intl** provides React components and hooks (like `<FormattedMessage>` and `useIntl()`) to display localized strings.
30
+ See a concrete comparison with react-intl in our [react-i18next vs. react-intl vs. Intlayer](https://github.com/aymericzip/intlayer/blob/main/docs/blog/en/react-i18next_vs_react-intl_vs_intlayer.md) blog post.
27
31
 
28
- By configuring Intlayer to **export** translations in a **react-intl–compatible** format, you can automatically **generate** and **update** the message files that `<IntlProvider>` (from react-intl) requires.
32
+ ## Why Combine Intlayer with react-intl?
29
33
 
30
- ---
34
+ While Intlayer provides an excellent standalone i18n solution (see our [React integration guide](https://github.com/aymericzip/intlayer/blob/main/docs/docs/en/intlayer_with_vite+react.md)), you might want to combine it with react-intl for several reasons:
31
35
 
32
- ## Why Use Intlayer with react-intl?
36
+ 1. **Existing codebase**: You have an established react-intl implementation and want to gradually migrate to Intlayer's improved developer experience.
37
+ 2. **Legacy requirements**: Your project requires compatibility with existing react-intl plugins or workflows.
38
+ 3. **Team familiarity**: Your team is comfortable with react-intl but wants better content management.
33
39
 
34
- 1. **Per-Component Dictionarys**
35
- Intlayer content declaration files can live alongside your React components, preventing “orphaned” translations if components are moved or removed. For example:
40
+ **For that, Intlayer can be implemented as an adapter for react-intl to help automating your JSON translations in CLI or CI/CD pipelines, testing your translations, and more.**
36
41
 
37
- ```bash
38
- .
39
- └── src
40
- └── components
41
- └── MyComponent
42
- ├── index.content.ts # Intlayer content declaration
43
- └── index.tsx # React component
44
- ```
42
+ This guide shows you how to leverage Intlayer's superior content declaration system while maintaining compatibility with react-intl.
45
43
 
46
- 2. **Centralized Translations**
47
- Each content declaration file collects all translations needed by a component. This is particularly helpful in TypeScript projects: missing translations can be caught at **compile time**.
44
+ ## Table of Contents
48
45
 
49
- 3. **Automatic Build and Regeneration**
50
- Whenever you add or update translations, Intlayer regenerates message JSON files. You can then pass these into react-intl’s `<IntlProvider>`.
46
+ <TOC/>
51
47
 
52
- ---
48
+ ## Step-by-Step Guide to Set Up Intlayer with react-intl
53
49
 
54
- ## Installation
50
+ ### Step 1: Install Dependencies
55
51
 
56
- In a typical React project, install the following:
52
+ Install the necessary packages:
57
53
 
58
- ```bash
59
- # with npm
60
- npm install intlayer react-intl
54
+ ```bash packageManager="npm"
55
+ npm install intlayer @intlayer/sync-json-plugin
56
+ ```
61
57
 
62
- # with yarn
63
- yarn add intlayer react-intl
58
+ ```bash packageManager="pnpm"
59
+ pnpm add intlayer @intlayer/sync-json-plugin
60
+ ```
64
61
 
65
- # with pnpm
66
- pnpm add intlayer react-intl
62
+ ```bash packageManager="yarn"
63
+ yarn add intlayer @intlayer/sync-json-plugin
67
64
  ```
68
65
 
69
- ### Why These Packages?
66
+ **Package descriptions:**
70
67
 
71
- - **intlayer**: Core CLI and library that scans for content declarations, merges them, and builds dictionary outputs.
72
- - **react-intl**: The main library from FormatJS that provides `<IntlProvider>`, `<FormattedMessage>`, `useIntl()` and other internationalization primitives.
68
+ - **intlayer**: Core library for internationalization management, content declaration, and building
69
+ - **@intlayer/sync-json-plugin**: Plugin to export Intlayer content declarations to react-intl compatible JSON format
73
70
 
74
- > If you don’t already have React itself installed, you’ll need it, too (`react` and `react-dom`).
71
+ ### Step 2: Implement the Intlayer plugin to wrap the JSON
75
72
 
76
- ## Configuring Intlayer to Export react-intl Messages
73
+ Create an Intlayer configuration file to define your supported locales:
77
74
 
78
- In your project’s root, create **`intlayer.config.ts`** (or `.js`, `.mjs`, `.cjs`) like so:
75
+ **If you want to also export JSON dictionaries for react-intl**, add the `syncJSON` plugin:
79
76
 
80
- ```typescript title="intlayer.config.ts"
77
+ ```typescript fileName="intlayer.config.ts"
81
78
  import { Locales, type IntlayerConfig } from "intlayer";
79
+ import { syncJSON } from "@intlayer/sync-json-plugin";
82
80
 
83
81
  const config: IntlayerConfig = {
84
82
  internationalization: {
85
- // Add as many locales as you wish
86
83
  locales: [Locales.ENGLISH, Locales.FRENCH, Locales.SPANISH],
87
84
  defaultLocale: Locales.ENGLISH,
88
85
  },
89
- content: {
90
- // Tells Intlayer to generate message files for react-intl
91
- dictionaryOutput: ["react-intl"],
92
-
93
- // The directory where Intlayer will write your message JSON files
94
- reactIntlMessagesDir: "./react-intl/messages",
95
- },
86
+ plugins: [
87
+ syncJSON({
88
+ source: ({ key, locale }) => `./intl/messages/${locale}/${key}.json`,
89
+ }),
90
+ ],
96
91
  };
97
92
 
98
93
  export default config;
99
94
  ```
100
95
 
101
- > **Note**: For other file extensions (`.mjs`, `.cjs`, `.js`), see the [Intlayer docs](https://intlayer.org/en/doc/concept/configuration) for usage details.
102
-
103
- ---
104
-
105
- ## Creating Your Intlayer Dictionarys
106
-
107
- Intlayer scans your codebase (by default, under `./src`) for files matching `*.content.{ts,tsx,js,jsx,mjs,mjx,cjs,cjx,json}`.
108
- Here’s a **TypeScript** example:
109
-
110
- ```typescript title="src/components/MyComponent/index.content.ts"
111
- import { t, type Dictionary } from "intlayer";
112
-
113
- const content = {
114
- // "key" becomes the top-level message key in your react-intl JSON file
115
- key: "my-component",
116
-
117
- content: {
118
- // Each call to t() declares a translatable field
119
- helloWorld: t({
120
- en: "Hello World",
121
- es: "Hola Mundo",
122
- fr: "Bonjour le monde",
123
- }),
124
- description: t({
125
- en: "This is a description",
126
- fr: "Ceci est une description",
127
- es: "Esta es una descripción",
128
- }),
129
- },
130
- } satisfies Dictionary;
131
-
132
- export default content;
133
- ```
134
-
135
- If you prefer JSON or different JS flavors (`.cjs`, `.mjs`), the structure is largely the same see [Intlayer docs on content declaration](https://intlayer.org/en/doc/concept/content).
136
-
137
- ---
138
-
139
- ## Building the react-intl Messages
140
-
141
- To generate the actual message JSON files for **react-intl**, run:
142
-
143
- ```bash
144
- # with npm
145
- npx intlayer dictionaries build
146
-
147
- # with yarn
148
- yarn intlayer build
149
-
150
- # with pnpm
151
- pnpm intlayer build
152
- ```
153
-
154
- This scans all `*.content.*` files, compiles them, and writes the results to the directory specified in your **`intlayer.config.ts`** in this example, `./react-intl/messages`.
155
- A typical output might look like:
156
-
157
- ```bash
158
- .
159
- └── react-intl
160
- └── messages
161
- ├── en.json
162
- ├── fr.json
163
- └── es.json
164
- ```
165
-
166
- Each file is a JSON object whose **top-level keys** correspond to each **`content.key`** from your declarations. The **sub-keys** (like `helloWorld`) reflect the translations declared within that content item.
167
-
168
- For example, the **en.json** might look like:
169
-
170
- ```json fileName="react-intl/messages/en/my-component.json"
171
- {
172
- "helloWorld": "Hello World",
173
- "description": "This is a description"
174
- }
175
- ```
176
-
177
- ---
178
-
179
- ## Initializing react-intl in Your React App
180
-
181
- ### 1. Load the Generated Messages
182
-
183
- Where you configure your app’s root component (e.g., `src/main.tsx` or `src/index.tsx`), you’ll need to:
184
-
185
- 1. **Import** the generated message files (either statically or dynamically).
186
- 2. **Provide** them to `<IntlProvider>` from `react-intl`.
187
-
188
- A simple approach is to import them **statically**:
189
-
190
- ```typescript title="src/index.tsx"
191
- import React from "react";
192
- import ReactDOM from "react-dom/client";
193
- import { IntlProvider } from "react-intl";
194
- import App from "./App";
195
-
196
- // Import the JSON files from the build output.
197
- // Alternatively, you can import dynamically based on the user's chosen locale.
198
- import en from "../react-intl/messages/en.json";
199
- import fr from "../react-intl/messages/fr.json";
200
- import es from "../react-intl/messages/es.json";
96
+ The `syncJSON` plugin will automatically wrap the JSON. It will read and write the JSON files without changing the content architecture.
201
97
 
98
+ If you want to make coexist that JSON with intlayer content declaration files (`.content` files), Intlayer will proceed this way:
202
99
 
100
+ 1. load both JSON and content declaration files and transform them into a intlayer dictionary.
101
+ 2. if there is conflicts between the JSON and the content declaration files, Intlayer will process to the merge of that all dictionaries. Depending of the priority of the plugins, and the one of the content declaration file (all are configurable).
203
102
 
204
- // Dynamically import all JSON files using Vite's import.meta.glob
205
- const messages = import.meta.glob("../react-intl/messages/**/*.json", {
206
- eager: true,
207
- });
103
+ If changes are made using the CLI to translate the JSON, or using the CMS, Intlayer will update the JSON file with the new translations.
208
104
 
209
- // Collate messages into a structured record
210
- const messagesRecord: Record<string, Record<string, any>> = {};
105
+ To see more details about the `syncJSON` plugin, please refer to the [syncJSON plugin documentation](https://github.com/aymericzip/intlayer/blob/main/docs/docs/en/plugins/sync-json.md).
211
106
 
212
- Object.entries(messages).forEach(([path, module]) => {
213
- // Extract locale and namespace from the file path
214
- const [, locale, namespace] = path.match(/messages\/(\w+)\/(.+?)\.json$/) ?? [];
215
- if (locale && namespace) {
216
- messagesRecord[locale] = messagesRecord[locale] ?? {};
217
- messagesRecord[locale][namespace] = module.default; // Assign JSON content
218
- }
219
- });
220
-
221
- // Merge namespaces for each locale
222
- const mergeMessages = (locale: string) =>
223
- Object.values(messagesRecord[locale] ?? {}).reduce(
224
- (acc, namespaceMessages) => ({ ...acc, ...namespaceMessages }),
225
- {}
226
- );
227
-
228
- // If you have a mechanism to detect the user's language, set it here.
229
- // For simplicity, let's pick English.
230
- const locale = "en";
231
-
232
-
233
- ReactDOM.createRoot(document.getElementById("root") as HTMLElement).render(
234
- <React.StrictMode>
235
- <IntlProvider locale={locale} messages={mergeMessages(locale)}>
236
- <App />
237
- </IntlProvider>
238
- </React.StrictMode>
239
- );
240
- ```
241
-
242
- > **Tip**: For real projects, you might:
243
- >
244
- > - Dynamically load the JSON messages at runtime.
245
- > - Use environment-based, browser-based, or user account–based locale detection.
246
-
247
- ### 2. Use `<FormattedMessage>` or `useIntl()`
248
-
249
- Once your messages are loaded into `<IntlProvider>`, any child component can use react-intl to access localized strings. There are two main approaches:
250
-
251
- - **`<FormattedMessage>`** component
252
- - **`useIntl()`** hook
253
-
254
- ---
255
-
256
- ## Using Translations in React Components
257
-
258
- ### Approach A: `<FormattedMessage>`
259
-
260
- For quick inline usage:
261
-
262
- ```tsx title="src/components/MyComponent/index.tsx"
263
- import React from "react";
264
- import { FormattedMessage } from "react-intl";
265
-
266
- export default function MyComponent() {
267
- return (
268
- <div>
269
- <h1>
270
- {/* “my-component.helloWorld” references the key from en.json, fr.json, etc. */}
271
- <FormattedMessage id="my-component.helloWorld" />
272
- </h1>
273
-
274
- <p>
275
- <FormattedMessage id="my-component.description" />
276
- </p>
277
- </div>
278
- );
279
- }
280
- ```
281
-
282
- > The **`id`** prop in `<FormattedMessage>` must match the **top-level key** (`my-component`) plus any sub-keys (`helloWorld`).
283
-
284
- ### Approach B: `useIntl()`
285
-
286
- For more dynamic usage:
287
-
288
- ```tsx title="src/components/MyComponent/index.tsx"
289
- import React from "react";
290
- import { useIntl } from "react-intl";
291
-
292
- export default function MyComponent() {
293
- const intl = useIntl();
294
-
295
- return (
296
- <div>
297
- <h1>{intl.formatMessage({ id: "my-component.helloWorld" })}</h1>
298
- <p>{intl.formatMessage({ id: "my-component.description" })}</p>
299
- </div>
300
- );
301
- }
302
- ```
303
-
304
- Either approach is valid choose whichever style suits your app.
305
-
306
- ---
307
-
308
- ## Updating or Adding New Translations
309
-
310
- 1. **Add or modify** content in any `*.content.*` file.
311
- 2. Rerun `intlayer build` to regenerate the JSON files under `./react-intl/messages`.
312
- 3. React (and react-intl) will pick up the updates next time you rebuild or reload your application.
313
-
314
- ---
315
-
316
- ## TypeScript Integration (Optional)
317
-
318
- If you’re using TypeScript, Intlayer can **generate type definitions** for your translations.
107
+ ## Git Configuration
319
108
 
320
- - Make sure `tsconfig.json` includes your `types` folder (or whichever output folder Intlayer generates) in the `"include"` array.
109
+ It's recommended to ignore auto-generated Intlayer files:
321
110
 
322
- ```json5
323
- {
324
- "compilerOptions": {
325
- // ...
326
- },
327
- "include": ["src", "types"],
328
- }
111
+ ```plaintext fileName=".gitignore"
112
+ # Ignore files generated by Intlayer
113
+ .intlayer
329
114
  ```
330
115
 
331
- The generated types can help detect missing translations or invalid keys in your React components at compile time.
332
-
333
- ---
334
-
335
- ## Git Configuration
116
+ These files can be regenerated during your build process and don't need to be committed to version control.
336
117
 
337
- It’s common to **exclude** Intlayer’s internal build artifacts from version control. In your `.gitignore`, add:
118
+ ### VS Code Extension
338
119
 
339
- ```plaintext
340
- # Ignore intlayer build artifacts
341
- .intlayer
342
- react-intl
343
- ```
120
+ For improved developer experience, install the official **Intlayer VS Code Extension**:
344
121
 
345
- Depending on your workflow, you may also want to ignore or commit the final dictionaries in `./react-intl/messages`. If your CI/CD pipeline regenerates them, you can safely ignore them; otherwise, commit them if you need them for production deployments.
122
+ [Install from the VS Code Marketplace](https://marketplace.visualstudio.com/items?itemName=intlayer.intlayer-vs-code-extension)
@@ -27,7 +27,7 @@ This is not a full tutorial. It’s a comparison to help you pick.
27
27
 
28
28
  We focus on **Next.js 13+ App Router** (with **React Server Components**) and evaluate:
29
29
 
30
- <TOC>
30
+ <TOC/>
31
31
 
32
32
  > **tl;dr**: All three can localize a Next.js app. If you want **component-scoped content**, **strict TypeScript types**, **build-time missing-key checks**, **tree-shaken dictionaries**, and **first-class App Router + SEO helpers**, **Intlayer** is the most complete, modern choice.
33
33
 
@@ -1,8 +1,8 @@
1
1
  ---
2
2
  createdAt: 2024-12-24
3
- updatedAt: 2025-06-29
4
- title: Intlayer and i18next
5
- description: Integrate Intlayer with i18next for optimal internationalisation. Compare the two frameworks and learn how to configure them together.
3
+ updatedAt: 2025-10-29
4
+ title: How to automate your i18next JSON translations using Intlayer
5
+ description: Automate your JSON translations with Intlayer and i18next for enhanced internationalisation in JavaScript applications.
6
6
  keywords:
7
7
  - Intlayer
8
8
  - i18next
@@ -14,149 +14,113 @@ keywords:
14
14
  - Next.js
15
15
  - JavaScript
16
16
  - TypeScript
17
+ - Migration
18
+ - Integration
17
19
  slugs:
18
20
  - blog
19
21
  - intlayer-with-i18next
22
+ history:
23
+ - version: 7.0.0
24
+ date: 2025-10-29
25
+ changes: Change to syncJSON plugin
20
26
  ---
21
27
 
22
- # Internationalization with Intlayer and i18next
28
+ # How to automate your i18next JSON translations using Intlayer
23
29
 
24
- i18next is an open-source internationalization (i18n) framework designed for JavaScript applications. It is widely used for managing translations, localization, and language switching in software projects. However, it has some limitations that can complicate scalability and development.
30
+ ## What is Intlayer?
25
31
 
26
- Intlayer is another internationalization framework that addresses these limitations, offering a more flexible approach to content declaration and management. Let's explore some key differences between i18next and Intlayer, and how to configure both for optimal internationalization.
32
+ **Intlayer** is an innovative, open-source internationalisation library designed to address the shortcomings of traditional i18n solutions. It offers a modern approach to content management in JavaScript applications.
27
33
 
28
- ## Intlayer vs. i18next: Key Differences
34
+ See a concrete comparison with i18next in our [next-i18next vs. next-intl vs. Intlayer](https://github.com/aymericzip/intlayer/blob/main/docs/blog/en/next-i18next_vs_next-intl_vs_intlayer.md) blog post.
29
35
 
30
- ### 1. Dictionary
36
+ ## Why Combine Intlayer with i18next?
31
37
 
32
- With i18next, translation dictionaries must be declared in a specific folder, which can complicate application scalability. In contrast, Intlayer allows content to be declared within the same directory as your component. This has several advantages:
38
+ While Intlayer provides an excellent standalone i18n solution (see our [Next.js integration guide](https://github.com/aymericzip/intlayer/blob/main/docs/docs/en/intlayer_with_nextjs_16.md)), you might want to combine it with i18next for several reasons:
33
39
 
34
- - **Simplified Content Editing**: Users don't have to search for the correct dictionary to edit, reducing the chance of errors.
35
- - **Automatic Adaptation**: If a component changes location or is removed, Intlayer detects and adapts automatically.
40
+ 1. **Existing codebase**: You have an established i18next implementation and want to gradually migrate to Intlayer's improved developer experience.
41
+ 2. **Legacy requirements**: Your project requires compatibility with existing i18next plugins or workflows.
42
+ 3. **Team familiarity**: Your team is comfortable with i18next but wants better content management.
36
43
 
37
- ### 2. Configuration Complexity
44
+ **For that, Intlayer can be implemented as an adapter for i18next to help automate your JSON translations in CLI or CI/CD pipelines, test your translations, and more.**
38
45
 
39
- Configuring i18next can be complex, especially when integrating with server-side components or configuring middleware for frameworks like Next.js. Intlayer simplifies this process, offering more straightforward configuration.
46
+ This guide shows you how to leverage Intlayer's superior content declaration system while maintaining compatibility with i18next.
40
47
 
41
- ### 3. Consistency of Translation Dictionaries
48
+ ## Table of Contents
42
49
 
43
- Ensuring that translation dictionaries are consistent across different languages can be challenging with i18next. This inconsistency can lead to application crashes if not handled properly. Intlayer addresses this by enforcing constraints on translated content, ensuring no translation is missed and that the translated content is accurate.
50
+ <TOC/>
44
51
 
45
- ### 4. TypeScript Integration
52
+ ## Step-by-Step Guide to Set Up Intlayer with i18next
46
53
 
47
- Intlayer offers better integration with TypeScript, allowing for auto-suggestions of content in your code, thereby enhancing development efficiency.
54
+ ### Step 1: Install Dependencies
48
55
 
49
- ### 5. Sharing Content Across Applications
56
+ Install the necessary packages:
50
57
 
51
- Intlayer facilitates the sharing of content declaration files across multiple applications and shared libraries. This feature makes it easier to maintain consistent translations across a larger codebase.
52
-
53
- ## How to Generate i18next Dictionaries with Intlayer
58
+ ```bash packageManager="npm"
59
+ npm install intlayer @intlayer/sync-json-plugin
60
+ ```
54
61
 
55
- ### Configuring Intlayer to Export i18next Dictionaries
62
+ ```bash packageManager="pnpm"
63
+ pnpm add intlayer @intlayer/sync-json-plugin
64
+ ```
56
65
 
57
- > Important Notes
66
+ ```bash packageManager="yarn"
67
+ yarn add intlayer @intlayer/sync-json-plugin
68
+ ```
58
69
 
59
- > The exportation of i18next dictionaries is currently in beta and does not ensure a 1: 1 compatibility with other frameworks. It is recommended to stick to a configuration based on Intlayer to minimise issues.
70
+ **Package descriptions:**
60
71
 
61
- To export i18next dictionaries, you need to configure Intlayer appropriately. Below is an example of how to set up Intlayer to export both Intlayer and i18next dictionaries.
72
+ - **intlayer**: Core library for internationalisation management, content declaration, and building
73
+ - **@intlayer/sync-json-plugin**: Plugin to export Intlayer content declarations to i18next compatible JSON format
62
74
 
63
- ```typescript fileName="intlayer.config.ts" codeFormat="typescript"
64
- import { Locales, type IntlayerConfig } from "intlayer";
75
+ ### Step 2: Implement the Intlayer plugin to wrap the JSON
65
76
 
66
- const config: IntlayerConfig = {
67
- content: {
68
- // Indicate that Intlayer will export both Intlayer and i18next dictionaries
69
- dictionaryOutput: ["intlayer", "i18next"],
70
- // Relative path from the project root to the directory where i18n dictionaries will be exported
71
- i18nextResourcesDir: "./i18next/dictionaries",
72
- },
73
- };
77
+ Create an Intlayer configuration file to define your supported locales:
74
78
 
75
- export default config;
76
- ```
79
+ **If you want to also export JSON dictionaries for i18next**, add the `syncJSON` plugin:
77
80
 
78
- ```javascript fileName="intlayer.config.mjs" codeFormat="esm"
79
- import { Locales } from "intlayer";
81
+ ```typescript fileName="intlayer.config.ts"
82
+ import { Locales, type IntlayerConfig } from "intlayer";
83
+ import { syncJSON } from "@intlayer/sync-json-plugin";
80
84
 
81
- /** @type {import('intlayer').IntlayerConfig} */
82
- const config = {
83
- content: {
84
- // Indicate that Intlayer will export both Intlayer and i18next dictionaries
85
- dictionaryOutput: ["intlayer", "i18next"],
86
- // Relative path from the project root to the directory where i18n dictionaries will be exported
87
- i18nextResourcesDir: "./i18next/dictionaries",
85
+ const config: IntlayerConfig = {
86
+ internationalization: {
87
+ locales: [Locales.ENGLISH, Locales.FRENCH, Locales.SPANISH],
88
+ defaultLocale: Locales.ENGLISH,
88
89
  },
90
+ plugins: [
91
+ syncJSON({
92
+ source: ({ key, locale }) => `./intl/messages/${locale}/${key}.json`,
93
+ }),
94
+ ],
89
95
  };
90
96
 
91
97
  export default config;
92
98
  ```
93
99
 
94
- ```javascript fileName="intlayer.config.cjs" codeFormat="commonjs"
95
- const { Locales } = require("intlayer");
96
-
97
- /** @type {import('intlayer').IntlayerConfig} */
98
- const config = {
99
- content: {
100
- // Indicate that Intlayer will export both Intlayer and i18next dictionaries
101
- dictionaryOutput: ["intlayer", "i18next"],
102
- // Relative path from the project root to the directory where i18n dictionaries will be exported
103
- i18nextResourcesDir: "./i18next/dictionaries",
104
- },
105
- };
106
-
107
- module.exports = config;
108
- ```
100
+ The `syncJSON` plugin will automatically wrap the JSON. It will read and write the JSON files without changing the content architecture.
109
101
 
110
- By including 'i18next' in the configuration, Intlayer generates dedicated i18next dictionaries in addition to the Intlayer dictionaries. Note that removing 'intlayer' from the configuration may break compatibility with React-Intlayer or Next-Intlayer.
102
+ If you want to make that JSON coexist with Intlayer content declaration files (`.content` files), Intlayer will proceed as follows:
111
103
 
112
- ### Importing Dictionaries into Your i18next Configuration
104
+ 1. load both JSON and content declaration files and transform them into an Intlayer dictionary.
105
+ 2. if there are conflicts between the JSON and the content declaration files, Intlayer will proceed to merge all those dictionaries. This depends on the priority of the plugins and that of the content declaration file (all are configurable).
113
106
 
114
- To import the generated dictionaries into your i18next configuration, you can use 'i18next-resources-to-backend'. Here is an example of how to import your i18next dictionaries:
107
+ If changes are made using the CLI to translate the JSON, or using the CMS, Intlayer will update the JSON file with the new translations.
115
108
 
116
- ```typescript fileName="i18n/client.ts" codeFormat="typescript"
117
- // i18n/client.ts
109
+ ## Git Configuration
118
110
 
119
- import i18next from "i18next";
120
- import resourcesToBackend from "i18next-resources-to-backend";
111
+ It is recommended to ignore auto-generated Intlayer files:
121
112
 
122
- i18next
123
- // Your i18next configuration
124
- .use(
125
- resourcesToBackend(
126
- (language: string, namespace: string) =>
127
- import(`../i18next/dictionaries/${language}/${namespace}.json`)
128
- )
129
- );
113
+ ```plaintext fileName=".gitignore"
114
+ # Ignore files generated by Intlayer
115
+ .intlayer
130
116
  ```
131
117
 
132
- ```javascript fileName="i18n/client.mjs" codeFormat="esm"
133
- // i18n/client.mjs
118
+ These files can be regenerated during your build process and do not need to be committed to version control.
134
119
 
135
- import i18next from "i18next";
136
- import resourcesToBackend from "i18next-resources-to-backend";
120
+ ### VS Code Extension
137
121
 
138
- i18next
139
- // Your i18next configuration
140
- .use(
141
- resourcesToBackend(
142
- (language, namespace) =>
143
- import(`../i18next/dictionaries/${language}/${namespace}.json`)
144
- )
145
- );
146
- ```
122
+ For an improved developer experience, install the official **Intlayer VS Code Extension**:
147
123
 
148
- ```javascript fileName="i18n/client.cjs" codeFormat="commonjs"
149
- // i18n/client.cjs
124
+ [Install from the VS Code Marketplace](https://marketplace.visualstudio.com/items?itemName=intlayer.intlayer-vs-code-extension)
150
125
 
151
- const i18next = require("i18next");
152
- const resourcesToBackend = require("i18next-resources-to-backend");
153
-
154
- i18next
155
- // Your i18next configuration
156
- .use(
157
- resourcesToBackend(
158
- (language, namespace) =>
159
- import(`../i18next/dictionaries/${language}/${namespace}.json`)
160
- )
161
- );
162
- ```
126
+ [Install from the VS Code Marketplace](https://marketplace.visualstudio.com/items?itemName=intlayer.intlayer-vs-code-extension)