@intlayer/docs 9.0.0-canary.2 → 9.0.0-canary.3

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.
@@ -1,6 +1,6 @@
1
1
  ---
2
2
  createdAt: 2025-03-13
3
- updatedAt: 2025-12-13
3
+ updatedAt: 2026-06-21
4
4
  title: Sync JSON Plugin
5
5
  description: Synchronisieren Sie Intlayer-Wörterbücher mit Drittanbieter-i18n-JSON-Dateien (i18next, next-intl, react-intl, vue-i18n und mehr). Behalten Sie Ihr bestehendes i18n bei und verwenden Sie Intlayer, um Ihre Nachrichten zu verwalten, zu übersetzen und zu testen.
6
6
  keywords:
@@ -24,6 +24,9 @@ slugs:
24
24
  - sync-json
25
25
  youtubeVideo: https://www.youtube.com/watch?v=MpGMxniDHNg
26
26
  history:
27
+ - version: 9.0.0
28
+ date: 2026-06-21
29
+ changes: "Option `splitKeys` hinzugefügt (ein Wörterbuch pro Top-Level-Namespace-Schlüssel) für next-intl / react-intl Single-File-Layouts"
27
30
  - version: 7.5.0
28
31
  date: 2025-12-13
29
32
  changes: "Unterstützung für ICU- und i18next-Formate hinzugefügt"
@@ -62,7 +65,63 @@ pnpm add -D @intlayer/sync-json-plugin
62
65
  npm i -D @intlayer/sync-json-plugin
63
66
  ```
64
67
 
65
- ## Schnellstart
68
+ ## Plugins
69
+
70
+ Dieses Paket bietet zwei Plugins:
71
+
72
+ - `loadJSON`: Lädt JSON-Dateien in Intlayer-Wörterbücher.
73
+ - Dieses Plugin wird verwendet, um JSON-Dateien aus einer Quelle zu laden, und diese werden in Intlayer-Wörterbücher geladen. Es kann die gesamte Codebasis durchsuchen und nach bestimmten JSON-Dateien suchen.
74
+ Dieses Plugin kann verwendet werden
75
+ - wenn Sie eine i18n-Bibliothek verwenden, die einen bestimmten Speicherort für Ihre zu ladenden JSON-Dateien vorschreibt (z.B. `next-intl`, `i18next`, `react-intl`, `vue-i18n` usw.), Sie aber Ihre Inhaltsdeklaration an einer beliebigen Stelle in Ihrer Codebasis platzieren möchten.
76
+ - Es kann auch verwendet werden, wenn Sie Ihre Nachrichten von einer Remote-Quelle (z.B. einem CMS, einer API usw.) abrufen und Ihre Nachrichten in JSON-Dateien speichern möchten.
77
+
78
+ > Im Hintergrund scannt dieses Plugin die gesamte Codebasis, sucht nach bestimmten JSON-Dateien und lädt sie in Intlayer-Wörterbücher.
79
+ > Beachten Sie, dass dieses Plugin die Ausgabe und Übersetzungen nicht zurück in die JSON-Dateien schreibt.
80
+
81
+ - `syncJSON`: Synchronisiert JSON-Dateien mit Intlayer-Wörterbüchern.
82
+ - Dieses Plugin wird verwendet, um JSON-Dateien mit Intlayer-Wörterbüchern zu synchronisieren. Es kann den angegebenen Speicherort scannen und die JSON-Dateien laden, die dem Muster für bestimmte JSON-Dateien entsprechen. Dieses Plugin ist nützlich, wenn Sie die Vorteile von Intlayer nutzen möchten, während Sie eine andere i18n-Bibliothek verwenden.
83
+
84
+ ## Beide Plugins verwenden
85
+
86
+ ```ts fileName="intlayer.config.ts"
87
+ import { Locales, type IntlayerConfig } from "intlayer";
88
+ import { loadJSON, syncJSON } from "@intlayer/sync-json-plugin";
89
+
90
+ const config: IntlayerConfig = {
91
+ internationalization: {
92
+ locales: [Locales.ENGLISH, Locales.FRENCH, Locales.SPANISH],
93
+ defaultLocale: Locales.ENGLISH,
94
+ },
95
+
96
+ // Halten Sie Ihre aktuellen JSON-Dateien mit den Intlayer-Wörterbüchern synchron
97
+ plugins: [
98
+ /**
99
+ * Lädt alle JSON-Dateien im src-Verzeichnis, die dem Muster {key}.i18n.json entsprechen
100
+ */
101
+ loadJSON({
102
+ source: ({ key }) => `./src/**/${key}.i18n.json`,
103
+ locale: Locales.ENGLISH,
104
+ priority: 1, // Stellt sicher, dass diese JSON-Dateien Vorrang vor Dateien unter `./locales/en/${key}.json` haben
105
+ format: "intlayer", // Format des JSON-Inhalts
106
+ }),
107
+ /**
108
+ * Lädt die Ausgabe und Übersetzungen und schreibt sie zurück in die JSON-Dateien im locales-Verzeichnis
109
+ */
110
+ syncJSON({
111
+ format: "i18next",
112
+ source: ({ key, locale }) => `./locales/${locale}/${key}.json`,
113
+ priority: 0,
114
+ format: "i18next",
115
+ }),
116
+ ],
117
+ };
118
+
119
+ export default config;
120
+ ```
121
+
122
+ ## `syncJSON` plugin
123
+
124
+ ### Schnellstart
66
125
 
67
126
  Fügen Sie das Plugin zu Ihrer `intlayer.config.ts` hinzu und verweisen Sie auf Ihre bestehende JSON-Struktur.
68
127
 
@@ -81,6 +140,7 @@ const config: IntlayerConfig = {
81
140
  syncJSON({
82
141
  // Pro-Locale, pro-Namespace Layout (z.B. next-intl, i18next mit Namespaces)
83
142
  source: ({ key, locale }) => `./locales/${locale}/${key}.json`,
143
+ format: "icu",
84
144
  }),
85
145
  ],
86
146
  };
@@ -91,14 +151,27 @@ export default config;
91
151
  Alternative: Einzelne Datei pro Locale (häufig bei i18next/react-intl Setups):
92
152
 
93
153
  ```ts fileName="intlayer.config.ts"
94
- plugins: [
95
- syncJSON({
96
- source: ({ locale }) => `./locales/${locale}.json`,
97
- }),
98
- ];
154
+ import { Locales, type IntlayerConfig } from "intlayer";
155
+ import { syncJSON } from "@intlayer/sync-json-plugin";
156
+
157
+ const config: IntlayerConfig = {
158
+ internationalization: {
159
+ locales: [Locales.ENGLISH, Locales.FRENCH],
160
+ defaultLocale: Locales.ENGLISH,
161
+ },
162
+ plugins: [
163
+ syncJSON({
164
+ format: "i18next",
165
+ source: ({ locale }) => `./locales/${locale}.json`,
166
+ format: "i18next",
167
+ }),
168
+ ],
169
+ };
170
+
171
+ export default config;
99
172
  ```
100
173
 
101
- ### Funktionsweise
174
+ #### Funktionsweise
102
175
 
103
176
  - Lesen: Das Plugin entdeckt JSON-Dateien über Ihren `source`-Builder und lädt sie als Intlayer-Wörterbücher.
104
177
  - Schreiben: Nach dem Build und Ausfüllen schreibt es die lokalisierten JSON-Dateien zurück an dieselben Pfade (mit einer abschließenden neuen Zeile, um Formatierungsprobleme zu vermeiden).
@@ -112,6 +185,7 @@ syncJSON({
112
185
  location?: string, // optionales Label, Standard: "plugin"
113
186
  priority?: number, // optionale Priorität zur Konfliktlösung, Standard: 0
114
187
  format?: 'intlayer' | 'icu' | 'i18next', // optionaler Formatierer, verwendet für Intlayer-Runtime-Kompatibilität
188
+ splitKeys?: boolean, // optional, teilt eine einzelne Datei in ein Wörterbuch pro Top-Level-Schlüssel (automatisch erkannt)
115
189
  });
116
190
  ```
117
191
 
@@ -136,17 +210,49 @@ syncJSON({
136
210
  }),
137
211
  ```
138
212
 
139
- ## Mehrere JSON-Quellen und Priorität
213
+ #### `splitKeys` (boolean)
214
+
215
+ Steuert, ob eine einzelne JSON-Datei, deren **Top-Level-Schlüssel Namespaces sind**, zu einem Wörterbuch pro Top-Level-Schlüssel werden soll, anstatt eines einzelnen Wörterbuchs, das die gesamte Datei enthält.
216
+
217
+ Dies entspricht dem Namespace-Modell von Bibliotheken wie `next-intl` und `react-intl`, bei denen eine `messages/{locale}.json`-Datei mehrere Namespaces durch ihre Top-Level-Schlüssel gruppiert, wobei jeder unabhängig angesprochen wird (z.B. `useTranslations('Hero')` löst sich in das `Hero`-Wörterbuch auf).
218
+
219
+ - `undefined` (Standard): **automatisch erkannt** — die Datei wird aufgeteilt, wenn das `source`-Muster kein `{key}`-Segment enthält (eine Datei enthält jeden Namespace), und andernfalls als einzelnes Wörterbuch beibehalten (eine Datei pro Schlüssel).
220
+ - `true`: teilt jeden Top-Level-Schlüssel immer in ein eigenes Wörterbuch auf.
221
+ - `false`: niemals aufteilen; die gesamte Datei wird zu einem einzigen Wörterbuch.
222
+
223
+ Angenommen, eine einzelne `messages/{locale}.json`-Datei:
224
+
225
+ ```json fileName="messages/en.json"
226
+ {
227
+ "Hero": { "title": "Full-stack developer" },
228
+ "Nav": { "work": "Work", "about": "About" },
229
+ "About": { "lead": "I build apps end to end." }
230
+ }
231
+ ```
232
+
233
+ ```ts fileName="intlayer.config.ts"
234
+ syncJSON({
235
+ format: "icu",
236
+ source: ({ locale }) => `./messages/${locale}.json`,
237
+ // splitKeys: true, // impliziert, da das Muster kein `{key}`-Segment enthält
238
+ }),
239
+ ```
240
+
241
+ Dies erzeugt drei Wörterbücher — `Hero`, `Nav` und `About` — sodass `useTranslations('Hero')` (next-intl) korrekt aufgelöst wird. Beim Zurückschreiben werden alle Namespaces wieder in derselben pro-Locale-Datei zusammengeführt.
242
+
243
+ > Wenn Sie das explizite `{key}`-Segment in Ihrer `source` beibehalten (z.B. `./locales/${locale}/${key}.json`), ist jede Datei bereits ein Namespace, sodass die Aufteilung standardmäßig deaktiviert ist.
244
+
245
+ ### Mehrere JSON-Quellen und Priorität
140
246
 
141
247
  Sie können mehrere `syncJSON`-Plugins hinzufügen, um verschiedene JSON-Quellen zu synchronisieren. Dies ist nützlich, wenn Sie mehrere i18n-Bibliotheken oder unterschiedliche JSON-Strukturen in Ihrem Projekt haben.
142
248
 
143
- ### Prioritätssystem
249
+ #### Prioritätssystem
144
250
 
145
251
  Wenn mehrere Plugins denselben Wörterbuchschlüssel ansprechen, bestimmt der Parameter `priority`, welches Plugin Vorrang hat:
146
252
 
147
253
  - Höhere Prioritätszahlen haben Vorrang vor niedrigeren
148
254
  - Die Standardpriorität von `.content`-Dateien ist `0`
149
- - Die Standardpriorität von Plugin-Content-Dateien ist `-1`
255
+ - Die Standardpriorität von Plugins ist `0`
150
256
  - Plugins mit derselben Priorität werden in der Reihenfolge verarbeitet, in der sie in der Konfiguration erscheinen
151
257
 
152
258
  ```ts fileName="intlayer.config.ts"
@@ -189,73 +295,140 @@ const config: IntlayerConfig = {
189
295
  export default config;
190
296
  ```
191
297
 
192
- ### Konfliktlösung
298
+ ## Load JSON Plugin
193
299
 
194
- Wenn derselbe Übersetzungsschlüssel in mehreren JSON-Quellen vorhanden ist:
300
+ ### Schnellstart
195
301
 
196
- 1. Bestimmt das Plugin mit der höchsten Priorität den endgültigen Wert
197
- 2. Werden Quellen mit niedrigerer Priorität als Fallbacks für fehlende Schlüssel verwendet
198
- 3. Ermöglicht es Ihnen, Legacy-Übersetzungen beizubehalten und gleichzeitig schrittweise auf neue Strukturen umzusteigen
302
+ Fügen Sie das Plugin zu Ihrer `intlayer.config.ts` hinzu, um vorhandene JSON-Dateien als Intlayer-Wörterbücher zu importieren. Dieses Plugin ist schreibgeschützt (keine Schreibvorgänge auf die Festplatte):
199
303
 
200
- ## Integrationen
304
+ ```ts fileName="intlayer.config.ts"
305
+ import { Locales, type IntlayerConfig } from "intlayer";
306
+ import { loadJSON } from "@intlayer/sync-json-plugin";
201
307
 
202
- Nachfolgend sind gängige Zuordnungen aufgeführt. Belassen Sie Ihre Laufzeit unverändert; fügen Sie nur das Plugin hinzu.
308
+ const config: IntlayerConfig = {
309
+ internationalization: {
310
+ locales: [Locales.ENGLISH, Locales.FRENCH, Locales.SPANISH],
311
+ defaultLocale: Locales.ENGLISH,
312
+ },
203
313
 
204
- ### i18next
314
+ plugins: [
315
+ // Importiert JSON-Nachrichten, die sich überall in Ihrem Quellbaum befinden
316
+ loadJSON({
317
+ source: ({ key }) => `./src/**/${key}.i18n.json`,
318
+ // Lädt eine einzelne Locale pro Plugin-Instanz (standardmäßig die Standard-Locale der Konfiguration)
319
+ locale: Locales.ENGLISH,
320
+ priority: 0,
321
+ }),
322
+ ],
323
+ };
205
324
 
206
- Typische Dateistruktur: `./public/locales/{locale}/{namespace}.json` oder `./locales/{locale}/{namespace}.json`.
325
+ export default config;
326
+ ```
327
+
328
+ Alternative: Pro-Locale-Layout, weiterhin schreibgeschützt (nur die ausgewählte Locale wird geladen):
207
329
 
208
330
  ```ts fileName="intlayer.config.ts"
209
- import { syncJSON } from "@intlayer/sync-json-plugin";
331
+ import { Locales, type IntlayerConfig } from "intlayer";
332
+ import { loadJSON } from "@intlayer/sync-json-plugin";
210
333
 
211
- export default {
334
+ const config: IntlayerConfig = {
335
+ internationalization: {
336
+ locales: [Locales.ENGLISH, Locales.FRENCH],
337
+ defaultLocale: Locales.ENGLISH,
338
+ },
212
339
  plugins: [
213
- syncJSON({
214
- format: "i18next",
340
+ loadJSON({
341
+ // Nur Dateien für Locales.FRENCH werden aus diesem Muster geladen
215
342
  source: ({ key, locale }) => `./locales/${locale}/${key}.json`,
343
+ locale: Locales.FRENCH,
216
344
  }),
217
345
  ],
218
346
  };
347
+
348
+ export default config;
219
349
  ```
220
350
 
221
- ### next-intl
351
+ ### Funktionsweise
222
352
 
223
- JSON-Nachrichten pro Locale (oft `./messages/{locale}.json`) oder pro Namespace.
353
+ - Entdecken: Erstellt einen Glob aus Ihrem `source`-Builder und sammelt passende JSON-Dateien.
354
+ - Importieren: Lädt jede JSON-Datei als Intlayer-Wörterbuch mit der angegebenen `locale`.
355
+ - Schreibgeschützt: Schreibt oder formatiert keine Ausgabedateien; verwenden Sie `syncJSON`, wenn Sie eine Roundtrip-Synchronisierung benötigen.
356
+ - Auto-Fill bereit: Definiert ein `fill`-Muster, sodass `intlayer content fill` fehlende Schlüssel füllen kann.
224
357
 
225
- ```ts fileName="intlayer.config.ts"
226
- plugins: [
227
- syncJSON({
228
- source: ({ locale, key }) => `./messages/${locale}/${key}.json`,
229
- }),
230
- ];
358
+ ### API
359
+
360
+ ```ts
361
+ loadJSON({
362
+ // Erstellt Pfade zu Ihren JSON-Dateien. `locale` ist optional, wenn Ihre Struktur kein Locale-Segment hat
363
+ source: ({ key, locale }) => string,
364
+
365
+ // Ziel-Locale für die von dieser Plugin-Instanz geladenen Wörterbücher
366
+ // Standardmäßig configuration.internationalization.defaultLocale
367
+ locale?: Locale,
368
+
369
+ // Optionales Label zur Identifizierung der Quelle
370
+ location?: string, // Standard: "plugin"
371
+
372
+ // Priorität zur Konfliktlösung gegenüber anderen Quellen
373
+ priority?: number, // Standard: 0
374
+
375
+ // Optionaler Formatierer für den JSON-Inhalt
376
+ format?: 'intlayer' | 'icu' | 'i18next', // Standard: 'intlayer'
377
+
378
+ // Teilt eine einzelne Datei in ein Wörterbuch pro Top-Level-Schlüssel (automatisch erkannt)
379
+ splitKeys?: boolean,
380
+ });
231
381
  ```
232
382
 
233
- Siehe auch: `docs/de/intlayer_with_next-intl.md`.
383
+ #### `format` ('intlayer' | 'icu' | 'i18next')
234
384
 
235
- ### react-intl
385
+ Gibt den Formatierer an, der für den Wörterbuchinhalt beim Laden von JSON-Dateien verwendet werden soll. Dies ermöglicht die Verwendung verschiedener Nachrichtenformatierungssyntaxen, die mit verschiedenen i18n-Bibliotheken kompatibel sind.
236
386
 
237
- Einzelne JSON-Datei pro Locale ist üblich:
387
+ - `'intlayer'`: Der Standard-Intlayer-Formatierer (Standard).
388
+ - `'icu'`: Verwendet ICU-Nachrichtenformatierung (kompatibel mit Bibliotheken wie react-intl, vue-i18n).
389
+ - `'i18next'`: Verwendet i18next-Nachrichtenformatierung (kompatibel mit i18next, next-i18next, Solid-i18next).
238
390
 
239
- ```ts fileName="intlayer.config.ts"
240
- plugins: [
241
- syncJSON({
242
- source: ({ locale }) => `./locales/${locale}.json`,
243
- }),
244
- ];
391
+ **Beispiel:**
392
+
393
+ ```ts
394
+ loadJSON({
395
+ source: ({ key }) => `./src/**/${key}.i18n.json`,
396
+ locale: Locales.ENGLISH,
397
+ format: "icu", // ICU-Formatierung für Kompatibilität verwenden
398
+ }),
245
399
  ```
246
400
 
247
- ### vue-i18n
401
+ #### `splitKeys` (boolean)
248
402
 
249
- Entweder eine einzelne Datei pro Locale oder pro Namespace:
403
+ Gleiches Verhalten wie bei [`syncJSON`](#splitkeys-boolean): Wenn eine einzelne JSON-Datei mehrere Namespaces durch ihre Top-Level-Schlüssel gruppiert, wird jeder Top-Level-Schlüssel zu einem eigenen Wörterbuch.
250
404
 
251
- ```ts fileName="intlayer.config.ts"
252
- plugins: [
253
- syncJSON({
254
- source: ({ key, locale }) => `./src/locales/${locale}/${key}.json`,
255
- }),
256
- ];
405
+ - `undefined` (Standard): **automatisch erkannt** — Aufteilung, wenn das `source`-Muster kein `{key}`-Segment enthält, andernfalls ein einzelnes Wörterbuch.
406
+ - `true` / `false`: Aufteilung erzwingen oder deaktivieren.
407
+
408
+ ```ts
409
+ loadJSON({
410
+ source: ({ locale }) => `./messages/${locale}.json`,
411
+ format: "icu",
412
+ // splitKeys automatisch aktiviert: `Hero`, `Nav`, `About`, … jeder wird zu einem Wörterbuch
413
+ }),
257
414
  ```
258
415
 
416
+ ### Verhalten und Konventionen
417
+
418
+ - Wenn Ihre `source`-Maske einen Locale-Platzhalter enthält, werden nur Dateien für die ausgewählte `locale` importiert.
419
+ - Wenn in Ihrer Maske kein `{key}`-Segment vorhanden ist, wird jeder Top-Level-Schlüssel der Datei standardmäßig zu einem eigenen Wörterbuch (siehe [`splitKeys`](#splitkeys-boolean)). Setzen Sie `splitKeys: false`, um stattdessen die gesamte Datei als ein einziges `index`-Wörterbuch zu laden.
420
+ - Schlüssel werden aus Dateipfaden abgeleitet, indem der `{key}`-Platzhalter in Ihrem `source`-Builder ersetzt wird.
421
+ - Das Plugin verwendet nur entdeckte Dateien und erstellt keine fehlenden Locales oder Schlüssel.
422
+ - Der `fill`-Pfad wird aus Ihrer `source` abgeleitet und verwendet, um fehlende Werte über die CLI zu aktualisieren, wenn Sie sich dafür entscheiden.
423
+
424
+ ## Konfliktlösung
425
+
426
+ Wenn derselbe Übersetzungsschlüssel in mehreren JSON-Quellen vorhanden ist:
427
+
428
+ 1. Bestimmt das Plugin mit der höchsten Priorität den endgültigen Wert
429
+ 2. Werden Quellen mit niedrigerer Priorität als Fallbacks für fehlende Schlüssel verwendet
430
+ 3. Ermöglicht es Ihnen, Legacy-Übersetzungen beizubehalten und gleichzeitig schrittweise auf neue Strukturen umzusteigen
431
+
259
432
  ## CLI
260
433
 
261
434
  Die synchronisierten JSON-Dateien werden wie andere `.content`-Dateien behandelt. Das bedeutet, dass alle intlayer-Befehle für die synchronisierten JSON-Dateien verfügbar sind. Einschließlich:
@@ -1,6 +1,6 @@
1
1
  ---
2
2
  createdAt: 2025-03-13
3
- updatedAt: 2025-12-13
3
+ updatedAt: 2026-06-21
4
4
  title: Sync JSON plugin
5
5
  description: Synchronize Intlayer dictionaries with third‑party i18n JSON files (i18next, next-intl, react-intl, vue-i18n, and more). Keep your existing i18n while using Intlayer to manage, translate, and test your messages.
6
6
  keywords:
@@ -24,6 +24,9 @@ slugs:
24
24
  - sync-json
25
25
  youtubeVideo: https://www.youtube.com/watch?v=MpGMxniDHNg
26
26
  history:
27
+ - version: 9.0.0
28
+ date: 2026-06-21
29
+ changes: "Add splitKeys option (one dictionary per top-level namespace key) for next-intl / react-intl single-file layouts"
27
30
  - version: 7.5.0
28
31
  date: 2025-12-13
29
32
  changes: "Add ICU and i18next format support"
@@ -182,6 +185,7 @@ syncJSON({
182
185
  location?: string, // optional label, default: "plugin"
183
186
  priority?: number, // optional priority for conflict resolution, default: 0
184
187
  format?: 'intlayer' | 'icu' | 'i18next', // optional formatter, used for intlayer runtime compatibility
188
+ splitKeys?: boolean, // optional, split a single file into one dictionary per top-level key (auto-detected)
185
189
  });
186
190
  ```
187
191
 
@@ -206,6 +210,38 @@ syncJSON({
206
210
  }),
207
211
  ```
208
212
 
213
+ #### `splitKeys` (boolean)
214
+
215
+ Controls whether a single JSON file whose **first-level keys are namespaces** should become one dictionary per top-level key, instead of a single dictionary holding the whole file.
216
+
217
+ This matches the namespace model of libraries like `next-intl` and `react-intl`, where one `messages/{locale}.json` file groups several namespaces by its first-level keys, each addressed independently (e.g. `useTranslations('Hero')` resolves to the `Hero` dictionary).
218
+
219
+ - `undefined` (default): **auto-detected** — the file is split when the `source` pattern has no `{key}` segment (one file holds every namespace), and kept as a single dictionary otherwise (one file per key).
220
+ - `true`: always split each top-level key into its own dictionary.
221
+ - `false`: never split; the whole file becomes a single dictionary.
222
+
223
+ Given a single `messages/{locale}.json` file:
224
+
225
+ ```json fileName="messages/en.json"
226
+ {
227
+ "Hero": { "title": "Full-stack developer" },
228
+ "Nav": { "work": "Work", "about": "About" },
229
+ "About": { "lead": "I build apps end to end." }
230
+ }
231
+ ```
232
+
233
+ ```ts fileName="intlayer.config.ts"
234
+ syncJSON({
235
+ format: "icu",
236
+ source: ({ locale }) => `./messages/${locale}.json`,
237
+ // splitKeys: true, // implied because the pattern has no `{key}` segment
238
+ }),
239
+ ```
240
+
241
+ This produces three dictionaries — `Hero`, `Nav`, and `About` — so `useTranslations('Hero')` (next-intl) resolves correctly. On write-back, all namespaces are re-assembled into the same per-locale file.
242
+
243
+ > When you keep the explicit `{key}` segment in your `source` (e.g. `./locales/${locale}/${key}.json`), each file is already one namespace, so splitting is disabled by default.
244
+
209
245
  ### Multiple JSON sources and priority
210
246
 
211
247
  You can add multiple `syncJSON` plugins to synchronize different JSON sources. This is useful when you have multiple i18n libraries or different JSON structures in your project.
@@ -338,6 +374,9 @@ loadJSON({
338
374
 
339
375
  // Optional formatter for the JSON content
340
376
  format?: 'intlayer' | 'icu' | 'i18next', // default: 'intlayer'
377
+
378
+ // Split a single file into one dictionary per top-level key (auto-detected)
379
+ splitKeys?: boolean,
341
380
  });
342
381
  ```
343
382
 
@@ -359,10 +398,25 @@ loadJSON({
359
398
  }),
360
399
  ```
361
400
 
401
+ #### `splitKeys` (boolean)
402
+
403
+ Same behavior as in [`syncJSON`](#splitkeys-boolean): when a single JSON file groups several namespaces by its first-level keys, each top-level key becomes its own dictionary.
404
+
405
+ - `undefined` (default): **auto-detected** — split when the `source` pattern has no `{key}` segment, single dictionary otherwise.
406
+ - `true` / `false`: force or disable splitting.
407
+
408
+ ```ts
409
+ loadJSON({
410
+ source: ({ locale }) => `./messages/${locale}.json`,
411
+ format: "icu",
412
+ // splitKeys auto-enabled: `Hero`, `Nav`, `About`, … each become a dictionary
413
+ }),
414
+ ```
415
+
362
416
  ### Behavior and conventions
363
417
 
364
418
  - If your `source` mask includes a locale placeholder, only files for the selected `locale` are ingested.
365
- - If there is no `{key}` segment in your mask, the dictionary key is "index".
419
+ - If there is no `{key}` segment in your mask, each top-level key of the file becomes its own dictionary by default (see [`splitKeys`](#splitkeys-boolean)). Set `splitKeys: false` to instead load the whole file as a single `index` dictionary.
366
420
  - Keys are derived from file paths by substituting the `{key}` placeholder in your `source` builder.
367
421
  - The plugin only uses discovered files and does not fabricate missing locales or keys.
368
422
  - The `fill` path is inferred from your `source` and used to update missing values via CLI when you opt‑in.