@intlayer/docs 6.1.5 → 6.1.6
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/blog/ar/next-i18next_vs_next-intl_vs_intlayer.md +404 -173
- package/blog/de/next-i18next_vs_next-intl_vs_intlayer.md +262 -113
- package/blog/en/intlayer_with_next-i18next.mdx +431 -0
- package/blog/en/intlayer_with_next-intl.mdx +335 -0
- package/blog/en/next-i18next_vs_next-intl_vs_intlayer.md +463 -209
- package/blog/en-GB/next-i18next_vs_next-intl_vs_intlayer.md +38 -28
- package/blog/es/next-i18next_vs_next-intl_vs_intlayer.md +185 -71
- package/blog/fr/next-i18next_vs_next-intl_vs_intlayer.md +38 -28
- package/blog/it/next-i18next_vs_next-intl_vs_intlayer.md +38 -28
- package/blog/ja/next-i18next_vs_next-intl_vs_intlayer.md +38 -28
- package/blog/ko/next-i18next_vs_next-intl_vs_intlayer.md +38 -28
- package/blog/pt/next-i18next_vs_next-intl_vs_intlayer.md +38 -28
- package/blog/ru/next-i18next_vs_next-intl_vs_intlayer.md +36 -28
- package/blog/tr/next-i18next_vs_next-intl_vs_intlayer.md +2 -0
- package/blog/zh/next-i18next_vs_next-intl_vs_intlayer.md +38 -28
- package/dist/cjs/generated/docs.entry.cjs +32 -0
- package/dist/cjs/generated/docs.entry.cjs.map +1 -1
- package/dist/esm/generated/docs.entry.mjs +32 -0
- package/dist/esm/generated/docs.entry.mjs.map +1 -1
- package/dist/types/generated/docs.entry.d.ts +2 -0
- package/dist/types/generated/docs.entry.d.ts.map +1 -1
- package/docs/ar/component_i18n.md +186 -0
- package/docs/ar/intlayer_with_angular.md +2 -2
- package/docs/ar/intlayer_with_astro.md +246 -0
- package/docs/ar/intlayer_with_create_react_app.md +3 -2
- package/docs/ar/intlayer_with_express.md +2 -2
- package/docs/ar/intlayer_with_nestjs.md +2 -2
- package/docs/ar/intlayer_with_nextjs_14.md +2 -2
- package/docs/ar/intlayer_with_nextjs_15.md +2 -2
- package/docs/ar/intlayer_with_nextjs_page_router.md +2 -2
- package/docs/ar/intlayer_with_nuxt.md +2 -2
- package/docs/ar/intlayer_with_react_native+expo.md +11 -20
- package/docs/ar/intlayer_with_react_router_v7.md +195 -241
- package/docs/ar/intlayer_with_tanstack.md +198 -272
- package/docs/ar/intlayer_with_vite+preact.md +9 -9
- package/docs/ar/intlayer_with_vite+react.md +7 -7
- package/docs/ar/intlayer_with_vite+vue.md +9 -9
- package/docs/ar/vs_code_extension.md +48 -109
- package/docs/de/component_i18n.md +186 -0
- package/docs/de/intlayer_with_angular.md +2 -2
- package/docs/de/intlayer_with_astro.md +246 -0
- package/docs/de/intlayer_with_create_react_app.md +2 -2
- package/docs/de/intlayer_with_express.md +2 -2
- package/docs/de/intlayer_with_nestjs.md +2 -2
- package/docs/de/intlayer_with_nextjs_14.md +2 -2
- package/docs/de/intlayer_with_nextjs_15.md +2 -2
- package/docs/de/intlayer_with_nextjs_page_router.md +2 -2
- package/docs/de/intlayer_with_nuxt.md +2 -2
- package/docs/de/intlayer_with_react_native+expo.md +11 -20
- package/docs/de/intlayer_with_react_router_v7.md +193 -242
- package/docs/de/intlayer_with_tanstack.md +194 -266
- package/docs/de/intlayer_with_vite+preact.md +9 -9
- package/docs/de/intlayer_with_vite+react.md +9 -9
- package/docs/de/intlayer_with_vite+vue.md +11 -11
- package/docs/de/packages/vite-intlayer/index.md +3 -3
- package/docs/de/vs_code_extension.md +46 -107
- package/docs/en/component_i18n.md +186 -0
- package/docs/en/how_works_intlayer.md +1 -1
- package/docs/en/index.md +1 -1
- package/docs/en/intlayer_cli.md +1 -1
- package/docs/en/intlayer_with_angular.md +4 -4
- package/docs/en/intlayer_with_astro.md +246 -0
- package/docs/en/intlayer_with_create_react_app.md +4 -4
- package/docs/en/intlayer_with_express.md +3 -3
- package/docs/en/intlayer_with_lynx+react.md +1 -1
- package/docs/en/intlayer_with_nestjs.md +2 -2
- package/docs/en/intlayer_with_nextjs_14.md +31 -5
- package/docs/en/intlayer_with_nextjs_15.md +31 -5
- package/docs/en/intlayer_with_nextjs_page_router.md +5 -5
- package/docs/en/intlayer_with_nuxt.md +4 -4
- package/docs/en/intlayer_with_react_native+expo.md +46 -24
- package/docs/en/intlayer_with_react_router_v7.md +164 -211
- package/docs/en/intlayer_with_tanstack.md +166 -241
- package/docs/en/intlayer_with_vite+preact.md +12 -12
- package/docs/en/intlayer_with_vite+react.md +12 -12
- package/docs/en/intlayer_with_vite+solid.md +2 -2
- package/docs/en/intlayer_with_vite+svelte.md +2 -2
- package/docs/en/intlayer_with_vite+vue.md +12 -12
- package/docs/en/introduction.md +1 -1
- package/docs/en/packages/next-intlayer/useDictionary.md +1 -1
- package/docs/en/packages/next-intlayer/useIntlayer.md +1 -1
- package/docs/en/packages/react-intlayer/useDictionary.md +1 -1
- package/docs/en/packages/react-intlayer/useI18n.md +1 -1
- package/docs/en/packages/react-intlayer/useIntlayer.md +1 -1
- package/docs/en/releases/v6.md +1 -0
- package/docs/en/roadmap.md +1 -1
- package/docs/en/vs_code_extension.md +24 -114
- package/docs/en-GB/component_i18n.md +186 -0
- package/docs/en-GB/intlayer_with_angular.md +3 -3
- package/docs/en-GB/intlayer_with_astro.md +246 -0
- package/docs/en-GB/intlayer_with_create_react_app.md +5 -4
- package/docs/en-GB/intlayer_with_express.md +2 -2
- package/docs/en-GB/intlayer_with_nestjs.md +2 -2
- package/docs/en-GB/intlayer_with_nextjs_14.md +4 -4
- package/docs/en-GB/intlayer_with_nextjs_15.md +2 -2
- package/docs/en-GB/intlayer_with_nextjs_page_router.md +2 -2
- package/docs/en-GB/intlayer_with_nuxt.md +2 -2
- package/docs/en-GB/intlayer_with_react_native+expo.md +11 -20
- package/docs/en-GB/intlayer_with_react_router_v7.md +171 -220
- package/docs/en-GB/intlayer_with_tanstack.md +174 -248
- package/docs/en-GB/intlayer_with_vite+preact.md +9 -9
- package/docs/en-GB/intlayer_with_vite+react.md +9 -9
- package/docs/en-GB/intlayer_with_vite+vue.md +11 -11
- package/docs/en-GB/packages/next-intlayer/useIntlayer.md +1 -1
- package/docs/en-GB/packages/react-intlayer/useIntlayer.md +1 -1
- package/docs/en-GB/vs_code_extension.md +42 -103
- package/docs/es/component_i18n.md +182 -0
- package/docs/es/intlayer_with_angular.md +2 -2
- package/docs/es/intlayer_with_astro.md +246 -0
- package/docs/es/intlayer_with_create_react_app.md +3 -2
- package/docs/es/intlayer_with_express.md +2 -2
- package/docs/es/intlayer_with_nextjs_14.md +2 -2
- package/docs/es/intlayer_with_nextjs_15.md +2 -2
- package/docs/es/intlayer_with_react_native+expo.md +11 -20
- package/docs/es/intlayer_with_react_router_v7.md +188 -232
- package/docs/es/intlayer_with_tanstack.md +203 -273
- package/docs/es/intlayer_with_vite+preact.md +7 -7
- package/docs/es/intlayer_with_vite+react.md +7 -7
- package/docs/es/intlayer_with_vite+vue.md +9 -9
- package/docs/es/vs_code_extension.md +53 -114
- package/docs/fr/component_i18n.md +186 -0
- package/docs/fr/intlayer_with_angular.md +2 -2
- package/docs/fr/intlayer_with_astro.md +246 -0
- package/docs/fr/intlayer_with_create_react_app.md +3 -2
- package/docs/fr/intlayer_with_express.md +2 -2
- package/docs/fr/intlayer_with_nestjs.md +2 -2
- package/docs/fr/intlayer_with_nextjs_14.md +2 -2
- package/docs/fr/intlayer_with_react_native+expo.md +11 -20
- package/docs/fr/intlayer_with_react_router_v7.md +188 -248
- package/docs/fr/intlayer_with_tanstack.md +192 -265
- package/docs/fr/intlayer_with_vite+preact.md +7 -7
- package/docs/fr/intlayer_with_vite+react.md +7 -7
- package/docs/fr/intlayer_with_vite+vue.md +9 -9
- package/docs/fr/vs_code_extension.md +50 -111
- package/docs/hi/component_i18n.md +186 -0
- package/docs/hi/intlayer_cli.md +1 -4
- package/docs/hi/intlayer_with_angular.md +2 -2
- package/docs/hi/intlayer_with_astro.md +246 -0
- package/docs/hi/intlayer_with_create_react_app.md +2 -2
- package/docs/hi/intlayer_with_express.md +2 -2
- package/docs/hi/intlayer_with_nestjs.md +2 -2
- package/docs/hi/intlayer_with_nextjs_14.md +2 -2
- package/docs/hi/intlayer_with_nextjs_15.md +2 -2
- package/docs/hi/intlayer_with_nextjs_page_router.md +2 -2
- package/docs/hi/intlayer_with_nuxt.md +2 -2
- package/docs/hi/intlayer_with_react_native+expo.md +11 -20
- package/docs/hi/intlayer_with_react_router_v7.md +199 -243
- package/docs/hi/intlayer_with_tanstack.md +210 -285
- package/docs/hi/intlayer_with_vite+preact.md +9 -9
- package/docs/hi/intlayer_with_vite+react.md +9 -9
- package/docs/hi/intlayer_with_vite+solid.md +1 -1
- package/docs/hi/intlayer_with_vite+vue.md +11 -11
- package/docs/hi/vs_code_extension.md +49 -110
- package/docs/it/component_i18n.md +186 -0
- package/docs/it/intlayer_with_angular.md +2 -2
- package/docs/it/intlayer_with_astro.md +246 -0
- package/docs/it/intlayer_with_create_react_app.md +3 -2
- package/docs/it/intlayer_with_express.md +2 -2
- package/docs/it/intlayer_with_nestjs.md +2 -2
- package/docs/it/intlayer_with_nextjs_14.md +2 -2
- package/docs/it/intlayer_with_nextjs_15.md +2 -2
- package/docs/it/intlayer_with_nextjs_page_router.md +2 -2
- package/docs/it/intlayer_with_nuxt.md +2 -2
- package/docs/it/intlayer_with_react_native+expo.md +11 -21
- package/docs/it/intlayer_with_react_router_v7.md +195 -242
- package/docs/it/intlayer_with_tanstack.md +203 -267
- package/docs/it/intlayer_with_vite+preact.md +9 -9
- package/docs/it/intlayer_with_vite+react.md +13 -11
- package/docs/it/intlayer_with_vite+vue.md +11 -11
- package/docs/it/vs_code_extension.md +50 -111
- package/docs/ja/component_i18n.md +186 -0
- package/docs/ja/intlayer_with_angular.md +2 -2
- package/docs/ja/intlayer_with_astro.md +246 -0
- package/docs/ja/intlayer_with_create_react_app.md +3 -2
- package/docs/ja/intlayer_with_express.md +2 -2
- package/docs/ja/intlayer_with_nestjs.md +2 -2
- package/docs/ja/intlayer_with_nextjs_14.md +2 -2
- package/docs/ja/intlayer_with_nextjs_15.md +2 -2
- package/docs/ja/intlayer_with_nextjs_page_router.md +2 -2
- package/docs/ja/intlayer_with_nuxt.md +2 -2
- package/docs/ja/intlayer_with_react_native+expo.md +18 -29
- package/docs/ja/intlayer_with_react_router_v7.md +204 -250
- package/docs/ja/intlayer_with_tanstack.md +218 -286
- package/docs/ja/intlayer_with_vite+preact.md +9 -9
- package/docs/ja/intlayer_with_vite+react.md +11 -11
- package/docs/ja/intlayer_with_vite+vue.md +11 -11
- package/docs/ja/vs_code_extension.md +50 -111
- package/docs/ko/component_i18n.md +186 -0
- package/docs/ko/intlayer_with_angular.md +2 -2
- package/docs/ko/intlayer_with_astro.md +246 -0
- package/docs/ko/intlayer_with_create_react_app.md +3 -2
- package/docs/ko/intlayer_with_express.md +2 -2
- package/docs/ko/intlayer_with_nestjs.md +2 -2
- package/docs/ko/intlayer_with_nextjs_14.md +2 -2
- package/docs/ko/intlayer_with_nextjs_15.md +2 -2
- package/docs/ko/intlayer_with_nextjs_page_router.md +2 -2
- package/docs/ko/intlayer_with_nuxt.md +2 -2
- package/docs/ko/intlayer_with_react_native+expo.md +19 -28
- package/docs/ko/intlayer_with_react_router_v7.md +190 -244
- package/docs/ko/intlayer_with_tanstack.md +200 -270
- package/docs/ko/intlayer_with_vite+preact.md +9 -9
- package/docs/ko/intlayer_with_vite+react.md +9 -9
- package/docs/ko/intlayer_with_vite+vue.md +11 -11
- package/docs/ko/vs_code_extension.md +48 -109
- package/docs/pt/component_i18n.md +186 -0
- package/docs/pt/intlayer_with_angular.md +2 -2
- package/docs/pt/intlayer_with_astro.md +246 -0
- package/docs/pt/intlayer_with_create_react_app.md +3 -2
- package/docs/pt/intlayer_with_express.md +2 -2
- package/docs/pt/intlayer_with_nestjs.md +2 -2
- package/docs/pt/intlayer_with_nextjs_14.md +2 -2
- package/docs/pt/intlayer_with_nextjs_15.md +2 -2
- package/docs/pt/intlayer_with_nextjs_page_router.md +2 -2
- package/docs/pt/intlayer_with_nuxt.md +2 -2
- package/docs/pt/intlayer_with_react_native+expo.md +11 -20
- package/docs/pt/intlayer_with_react_router_v7.md +7 -13
- package/docs/pt/intlayer_with_tanstack.md +183 -258
- package/docs/pt/intlayer_with_vite+preact.md +9 -9
- package/docs/pt/intlayer_with_vite+react.md +9 -9
- package/docs/pt/intlayer_with_vite+vue.md +9 -9
- package/docs/pt/vs_code_extension.md +46 -107
- package/docs/ru/component_i18n.md +186 -0
- package/docs/ru/intlayer_with_angular.md +2 -2
- package/docs/ru/intlayer_with_astro.md +246 -0
- package/docs/ru/intlayer_with_create_react_app.md +3 -2
- package/docs/ru/intlayer_with_express.md +2 -2
- package/docs/ru/intlayer_with_nestjs.md +2 -2
- package/docs/ru/intlayer_with_nextjs_14.md +2 -2
- package/docs/ru/intlayer_with_nextjs_15.md +2 -2
- package/docs/ru/intlayer_with_nextjs_page_router.md +2 -2
- package/docs/ru/intlayer_with_nuxt.md +2 -2
- package/docs/ru/intlayer_with_react_native+expo.md +11 -20
- package/docs/ru/intlayer_with_react_router_v7.md +192 -238
- package/docs/ru/intlayer_with_tanstack.md +197 -269
- package/docs/ru/intlayer_with_vite+preact.md +9 -9
- package/docs/ru/intlayer_with_vite+react.md +9 -9
- package/docs/ru/intlayer_with_vite+vue.md +11 -11
- package/docs/ru/vs_code_extension.md +48 -109
- package/docs/tr/component_i18n.md +186 -0
- package/docs/tr/how_works_intlayer.md +1 -1
- package/docs/tr/index.md +1 -1
- package/docs/tr/intlayer_cli.md +1 -1
- package/docs/tr/intlayer_with_angular.md +4 -4
- package/docs/tr/intlayer_with_astro.md +246 -0
- package/docs/tr/intlayer_with_create_react_app.md +4 -4
- package/docs/tr/intlayer_with_express.md +3 -3
- package/docs/tr/intlayer_with_lynx+react.md +1 -1
- package/docs/tr/intlayer_with_nestjs.md +2 -2
- package/docs/tr/intlayer_with_nextjs_14.md +2 -2
- package/docs/tr/intlayer_with_nextjs_15.md +4 -4
- package/docs/tr/intlayer_with_nextjs_page_router.md +5 -5
- package/docs/tr/intlayer_with_nuxt.md +4 -4
- package/docs/tr/intlayer_with_react_native+expo.md +12 -21
- package/docs/tr/intlayer_with_react_router_v7.md +222 -267
- package/docs/tr/intlayer_with_tanstack.md +400 -303
- package/docs/tr/intlayer_with_vite+preact.md +12 -12
- package/docs/tr/intlayer_with_vite+react.md +12 -12
- package/docs/tr/intlayer_with_vite+solid.md +2 -2
- package/docs/tr/intlayer_with_vite+svelte.md +2 -2
- package/docs/tr/intlayer_with_vite+vue.md +12 -12
- package/docs/tr/introduction.md +1 -1
- package/docs/tr/packages/react-intlayer/useDictionary.md +1 -1
- package/docs/tr/packages/react-intlayer/useI18n.md +1 -1
- package/docs/tr/roadmap.md +1 -1
- package/docs/tr/vs_code_extension.md +54 -115
- package/docs/zh/component_i18n.md +186 -0
- package/docs/zh/intlayer_with_angular.md +2 -2
- package/docs/zh/intlayer_with_astro.md +246 -0
- package/docs/zh/intlayer_with_create_react_app.md +3 -2
- package/docs/zh/intlayer_with_express.md +2 -2
- package/docs/zh/intlayer_with_nestjs.md +2 -2
- package/docs/zh/intlayer_with_nextjs_14.md +2 -2
- package/docs/zh/intlayer_with_nextjs_15.md +2 -2
- package/docs/zh/intlayer_with_nextjs_page_router.md +2 -2
- package/docs/zh/intlayer_with_nuxt.md +2 -2
- package/docs/zh/intlayer_with_react_native+expo.md +19 -28
- package/docs/zh/intlayer_with_react_router_v7.md +200 -248
- package/docs/zh/intlayer_with_tanstack.md +208 -283
- package/docs/zh/intlayer_with_vite+preact.md +9 -9
- package/docs/zh/intlayer_with_vite+react.md +9 -9
- package/docs/zh/intlayer_with_vite+vue.md +9 -9
- package/docs/zh/vs_code_extension.md +51 -105
- package/package.json +10 -10
- package/src/generated/docs.entry.ts +32 -0
|
@@ -19,6 +19,8 @@ slugs:
|
|
|
19
19
|
|
|
20
20
|
# next-i18next VS next-intl VS intlayer | Next.js Internationalisation (i18n)
|
|
21
21
|
|
|
22
|
+

|
|
23
|
+
|
|
22
24
|
Let’s take a look into the similarities and differences between three i18n options for Next.js: next-i18next, next-intl, and Intlayer.
|
|
23
25
|
|
|
24
26
|
This is not a full tutorial. It’s a comparison to help you pick.
|
|
@@ -165,9 +167,9 @@ In the case of `next-intl` and `next-i18next`, the library requires loading the
|
|
|
165
167
|
|
|
166
168
|
Here is an example of the impact of bundle size optimisation using `intlayer` in a vite + react application:
|
|
167
169
|
|
|
168
|
-
| Optimised bundle
|
|
169
|
-
|
|
|
170
|
-
|  |  |
|
|
170
|
+
| Optimised bundle | Bundle not optimised |
|
|
171
|
+
| ----------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------ |
|
|
172
|
+
|  |  |
|
|
171
173
|
|
|
172
174
|
---
|
|
173
175
|
|
|
@@ -369,25 +371,25 @@ The app structure is important to ensure good maintainability of your codebase.
|
|
|
369
371
|
|
|
370
372
|
```bash
|
|
371
373
|
.
|
|
372
|
-
├──
|
|
373
|
-
│ └── locales
|
|
374
|
-
│ ├── en
|
|
375
|
-
│ │ ├── home.json
|
|
376
|
-
│ │ └── navbar.json
|
|
377
|
-
│ ├── fr
|
|
378
|
-
│ │ ├── home.json
|
|
379
|
-
│ │ └── navbar.json
|
|
380
|
-
│ └── es
|
|
381
|
-
│ ├── home.json
|
|
382
|
-
│ └── navbar.json
|
|
383
|
-
├── next-i18next.config.js
|
|
374
|
+
├── i18n.config.ts
|
|
384
375
|
└── src
|
|
385
|
-
├──
|
|
376
|
+
├── locales
|
|
377
|
+
│ ├── en
|
|
378
|
+
│ │ ├── common.json
|
|
379
|
+
│ │ └── about.json
|
|
380
|
+
│ └── fr
|
|
381
|
+
│ ├── common.json
|
|
382
|
+
│ └── about.json
|
|
386
383
|
├── app
|
|
387
|
-
│
|
|
384
|
+
│ ├── i18n
|
|
385
|
+
│ │ └── server.ts
|
|
386
|
+
│ └── [locale]
|
|
387
|
+
│ ├── layout.tsx
|
|
388
|
+
│ └── about.tsx
|
|
388
389
|
└── components
|
|
389
|
-
|
|
390
|
-
|
|
390
|
+
├── I18nProvider.tsx
|
|
391
|
+
├── ClientComponent.tsx
|
|
392
|
+
└── ServerComponent.tsx
|
|
391
393
|
```
|
|
392
394
|
|
|
393
395
|
</TabItem>
|
|
@@ -395,6 +397,7 @@ The app structure is important to ensure good maintainability of your codebase.
|
|
|
395
397
|
|
|
396
398
|
```bash
|
|
397
399
|
.
|
|
400
|
+
├── i18n.ts
|
|
398
401
|
├── locales
|
|
399
402
|
│ ├── en
|
|
400
403
|
│ │ ├── home.json
|
|
@@ -405,11 +408,13 @@ The app structure is important to ensure good maintainability of your codebase.
|
|
|
405
408
|
│ └── es
|
|
406
409
|
│ ├── home.json
|
|
407
410
|
│ └── navbar.json
|
|
408
|
-
├── i18n.ts
|
|
409
411
|
└── src
|
|
410
412
|
├── middleware.ts
|
|
411
413
|
├── app
|
|
412
|
-
│
|
|
414
|
+
│ ├── i18n
|
|
415
|
+
│ │ └── server.ts
|
|
416
|
+
│ └── [locale]
|
|
417
|
+
│ └── home.tsx
|
|
413
418
|
└── components
|
|
414
419
|
└── Navbar
|
|
415
420
|
└── index.tsx
|
|
@@ -424,9 +429,11 @@ The app structure is important to ensure good maintainability of your codebase.
|
|
|
424
429
|
└── src
|
|
425
430
|
├── middleware.ts
|
|
426
431
|
├── app
|
|
427
|
-
│ └──
|
|
428
|
-
│
|
|
429
|
-
│ └──
|
|
432
|
+
│ └── [locale]
|
|
433
|
+
│ ├── layout.tsx
|
|
434
|
+
│ └── home
|
|
435
|
+
│ ├── index.tsx
|
|
436
|
+
│ └── index.content.ts
|
|
430
437
|
└── components
|
|
431
438
|
└── Navbar
|
|
432
439
|
├── index.tsx
|
|
@@ -554,8 +561,10 @@ export default async function LocaleLayout({
|
|
|
554
561
|
const messages = await getMessages();
|
|
555
562
|
const clientMessages = pick(messages, ["common", "about"]);
|
|
556
563
|
|
|
564
|
+
const rtlLocales = ["ar", "he", "fa", "ur"];
|
|
565
|
+
|
|
557
566
|
return (
|
|
558
|
-
<html lang={locale}>
|
|
567
|
+
<html lang={locale} dir={rtlLocales.includes(locale) ? "rtl" : "ltr"}>
|
|
559
568
|
<body>
|
|
560
569
|
<NextIntlClientProvider locale={locale} messages={clientMessages}>
|
|
561
570
|
{children}
|
|
@@ -872,10 +881,11 @@ const ServerComponent = ({ count }: ServerComponentProps) => {
|
|
|
872
881
|
type ServerComponentProps = {
|
|
873
882
|
count: number;
|
|
874
883
|
t: (key: string) => string;
|
|
884
|
+
formatter: Intl.NumberFormat;
|
|
875
885
|
};
|
|
876
886
|
|
|
877
|
-
const ServerComponent = ({ t, count }: ServerComponentProps) => {
|
|
878
|
-
const formatted =
|
|
887
|
+
const ServerComponent = ({ t, count, formatter }: ServerComponentProps) => {
|
|
888
|
+
const formatted = formatter.format(count);
|
|
879
889
|
|
|
880
890
|
return (
|
|
881
891
|
<div>
|
|
@@ -889,7 +899,7 @@ const ServerComponent = ({ t, count }: ServerComponentProps) => {
|
|
|
889
899
|
> As the server component cannot be async, you need to pass the translations and formatter function as props.
|
|
890
900
|
>
|
|
891
901
|
> - `const t = await getTranslations("about.counter");`
|
|
892
|
-
> - `const
|
|
902
|
+
> - `const formatter = await getFormatter().then((formatter) => formatter.number());`
|
|
893
903
|
|
|
894
904
|
</TabItem>
|
|
895
905
|
<TabItem label="intlayer" value="intlayer">
|
|
@@ -19,6 +19,8 @@ slugs:
|
|
|
19
19
|
|
|
20
20
|
# next-i18next VS next-intl VS intlayer | Internacionalización (i18n) en Next.js
|
|
21
21
|
|
|
22
|
+

|
|
23
|
+
|
|
22
24
|
Veamos las similitudes y diferencias entre tres opciones de i18n para Next.js: next-i18next, next-intl e Intlayer.
|
|
23
25
|
|
|
24
26
|
Esto no es un tutorial completo. Es una comparación para ayudarte a elegir.
|
|
@@ -165,9 +167,9 @@ En el caso de `next-intl` y `next-i18next`, la biblioteca requiere cargar el JSO
|
|
|
165
167
|
|
|
166
168
|
Aquí un ejemplo del impacto de la optimización del tamaño del paquete usando `intlayer` en una aplicación vite + react:
|
|
167
169
|
|
|
168
|
-
| Paquete optimizado
|
|
169
|
-
|
|
|
170
|
-
|  |  |
|
|
170
|
+
| Paquete optimizado | Paquete no optimizado |
|
|
171
|
+
| ------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------- |
|
|
172
|
+
|  |  |
|
|
171
173
|
|
|
172
174
|
---
|
|
173
175
|
|
|
@@ -340,25 +342,25 @@ La estructura de la aplicación es importante para asegurar un buen mantenimient
|
|
|
340
342
|
|
|
341
343
|
```bash
|
|
342
344
|
.
|
|
343
|
-
├──
|
|
344
|
-
│ └── locales
|
|
345
|
-
│ ├── en
|
|
346
|
-
│ │ ├── home.json
|
|
347
|
-
│ │ └── navbar.json
|
|
348
|
-
│ ├── fr
|
|
349
|
-
│ │ ├── home.json
|
|
350
|
-
│ │ └── navbar.json
|
|
351
|
-
│ └── es
|
|
352
|
-
│ ├── home.json
|
|
353
|
-
│ └── navbar.json
|
|
354
|
-
├── next-i18next.config.js
|
|
345
|
+
├── i18n.config.ts
|
|
355
346
|
└── src
|
|
356
|
-
├──
|
|
347
|
+
├── locales
|
|
348
|
+
│ ├── en
|
|
349
|
+
│ │ ├── common.json
|
|
350
|
+
│ │ └── about.json
|
|
351
|
+
│ └── fr
|
|
352
|
+
│ ├── common.json
|
|
353
|
+
│ └── about.json
|
|
357
354
|
├── app
|
|
358
|
-
│
|
|
355
|
+
│ ├── i18n
|
|
356
|
+
│ │ └── server.ts
|
|
357
|
+
│ └── [locale]
|
|
358
|
+
│ ├── layout.tsx
|
|
359
|
+
│ └── about.tsx
|
|
359
360
|
└── components
|
|
360
|
-
|
|
361
|
-
|
|
361
|
+
├── I18nProvider.tsx
|
|
362
|
+
├── ClientComponent.tsx
|
|
363
|
+
└── ServerComponent.tsx
|
|
362
364
|
```
|
|
363
365
|
|
|
364
366
|
</TabItem>
|
|
@@ -366,6 +368,7 @@ La estructura de la aplicación es importante para asegurar un buen mantenimient
|
|
|
366
368
|
|
|
367
369
|
```bash
|
|
368
370
|
.
|
|
371
|
+
├── i18n.ts
|
|
369
372
|
├── locales
|
|
370
373
|
│ ├── en
|
|
371
374
|
│ │ ├── home.json
|
|
@@ -376,11 +379,13 @@ La estructura de la aplicación es importante para asegurar un buen mantenimient
|
|
|
376
379
|
│ └── es
|
|
377
380
|
│ ├── home.json
|
|
378
381
|
│ └── navbar.json
|
|
379
|
-
├── i18n.ts
|
|
380
382
|
└── src
|
|
381
383
|
├── middleware.ts
|
|
382
384
|
├── app
|
|
383
|
-
│
|
|
385
|
+
│ ├── i18n
|
|
386
|
+
│ │ └── server.ts
|
|
387
|
+
│ └── [locale]
|
|
388
|
+
│ └── home.tsx
|
|
384
389
|
└── components
|
|
385
390
|
└── Navbar
|
|
386
391
|
└── index.tsx
|
|
@@ -395,9 +400,11 @@ La estructura de la aplicación es importante para asegurar un buen mantenimient
|
|
|
395
400
|
└── src
|
|
396
401
|
├── middleware.ts
|
|
397
402
|
├── app
|
|
398
|
-
│ └──
|
|
399
|
-
│
|
|
400
|
-
│ └──
|
|
403
|
+
│ └── [locale]
|
|
404
|
+
│ ├── layout.tsx
|
|
405
|
+
│ └── home
|
|
406
|
+
│ ├── index.tsx
|
|
407
|
+
│ └── index.content.ts
|
|
401
408
|
└── components
|
|
402
409
|
└── Navbar
|
|
403
410
|
├── index.tsx
|
|
@@ -420,66 +427,170 @@ Cómo la biblioteca maneja la carga de contenido es importante.
|
|
|
420
427
|
<Tab defaultTab="next-intl" group='techno'>
|
|
421
428
|
<TabItem label="next-i18next" value="next-i18next">
|
|
422
429
|
|
|
423
|
-
```
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
locales: ["en", "fr", "es"],
|
|
427
|
-
defaultLocale: "en",
|
|
428
|
-
},
|
|
429
|
-
};
|
|
430
|
-
```
|
|
430
|
+
```ts fileName="i18n.config.ts"
|
|
431
|
+
export const locales = ["en", "fr"] as const;
|
|
432
|
+
export type Locale = (typeof locales)[number];
|
|
431
433
|
|
|
432
|
-
|
|
433
|
-
import { appWithTranslation } from "next-i18next";
|
|
434
|
+
export const defaultLocale: Locale = "en";
|
|
434
435
|
|
|
435
|
-
const
|
|
436
|
+
export const rtlLocales = ["ar", "he", "fa", "ur"] as const;
|
|
437
|
+
export const isRtl = (locale: string) =>
|
|
438
|
+
(rtlLocales as readonly string[]).includes(locale);
|
|
439
|
+
|
|
440
|
+
export function localizedPath(locale: string, path: string) {
|
|
441
|
+
return locale === defaultLocale ? path : "/" + locale + path;
|
|
442
|
+
}
|
|
436
443
|
|
|
437
|
-
|
|
444
|
+
const ORIGIN = "https://example.com";
|
|
445
|
+
export function abs(locale: string, path: string) {
|
|
446
|
+
return ORIGIN + localizedPath(locale, path);
|
|
447
|
+
}
|
|
438
448
|
```
|
|
439
449
|
|
|
440
|
-
```
|
|
441
|
-
import type { GetStaticProps } from "next";
|
|
442
|
-
import { serverSideTranslations } from "next-i18next/serverSideTranslations";
|
|
443
|
-
import { useTranslation } from "next-i18next";
|
|
444
|
-
import { I18nextProvider, initReactI18next } from "react-i18next";
|
|
450
|
+
```ts fileName="src/app/i18n/server.ts"
|
|
445
451
|
import { createInstance } from "i18next";
|
|
446
|
-
import {
|
|
452
|
+
import { initReactI18next } from "react-i18next/initReactI18next";
|
|
453
|
+
import resourcesToBackend from "i18next-resources-to-backend";
|
|
454
|
+
import { defaultLocale } from "@/i18n.config";
|
|
455
|
+
|
|
456
|
+
// Load JSON resources from src/locales/<locale>/<namespace>.json
|
|
457
|
+
const backend = resourcesToBackend(
|
|
458
|
+
(locale: string, namespace: string) =>
|
|
459
|
+
import(`../../locales/${locale}/${namespace}.json`)
|
|
460
|
+
);
|
|
461
|
+
|
|
462
|
+
export async function initI18next(
|
|
463
|
+
locale: string,
|
|
464
|
+
namespaces: string[] = ["common"]
|
|
465
|
+
) {
|
|
466
|
+
const i18n = createInstance();
|
|
467
|
+
await i18n
|
|
468
|
+
.use(initReactI18next)
|
|
469
|
+
.use(backend)
|
|
470
|
+
.init({
|
|
471
|
+
lng: locale,
|
|
472
|
+
fallbackLng: defaultLocale,
|
|
473
|
+
ns: namespaces,
|
|
474
|
+
defaultNS: "common",
|
|
475
|
+
interpolation: { escapeValue: false },
|
|
476
|
+
react: { useSuspense: false },
|
|
477
|
+
});
|
|
478
|
+
return i18n;
|
|
479
|
+
}
|
|
480
|
+
```
|
|
447
481
|
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
const resources = await loadMessagesFor(locale); // tu cargador (JSON, etc.)
|
|
482
|
+
```tsx fileName="src/components/I18nProvider.tsx"
|
|
483
|
+
"use client";
|
|
451
484
|
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
485
|
+
import * as React from "react";
|
|
486
|
+
import { I18nextProvider } from "react-i18next";
|
|
487
|
+
import { createInstance } from "i18next";
|
|
488
|
+
import { initReactI18next } from "react-i18next/initReactI18next";
|
|
489
|
+
import resourcesToBackend from "i18next-resources-to-backend";
|
|
490
|
+
import { defaultLocale } from "@/i18n.config";
|
|
491
|
+
|
|
492
|
+
const backend = resourcesToBackend(
|
|
493
|
+
(locale: string, namespace: string) =>
|
|
494
|
+
import(`../../locales/${locale}/${namespace}.json`)
|
|
495
|
+
);
|
|
496
|
+
|
|
497
|
+
type Props = {
|
|
498
|
+
locale: string;
|
|
499
|
+
namespaces?: string[];
|
|
500
|
+
resources?: Record<string, any>; // { ns: bundle }
|
|
501
|
+
children: React.ReactNode;
|
|
502
|
+
};
|
|
503
|
+
|
|
504
|
+
export default function I18nProvider({
|
|
505
|
+
locale,
|
|
506
|
+
namespaces = ["common"],
|
|
507
|
+
resources,
|
|
508
|
+
children,
|
|
509
|
+
}: Props) {
|
|
510
|
+
const [i18n] = React.useState(() => {
|
|
511
|
+
const i = createInstance();
|
|
512
|
+
|
|
513
|
+
i.use(initReactI18next)
|
|
514
|
+
.use(backend)
|
|
515
|
+
.init({
|
|
516
|
+
lng: locale,
|
|
517
|
+
fallbackLng: defaultLocale,
|
|
518
|
+
ns: namespaces,
|
|
519
|
+
resources: resources ? { [locale]: resources } : undefined,
|
|
520
|
+
defaultNS: "common",
|
|
521
|
+
interpolation: { escapeValue: false },
|
|
522
|
+
react: { useSuspense: false },
|
|
523
|
+
});
|
|
524
|
+
|
|
525
|
+
return i;
|
|
460
526
|
});
|
|
461
527
|
|
|
462
|
-
|
|
528
|
+
return <I18nextProvider i18n={i18n}>{children}</I18nextProvider>;
|
|
529
|
+
}
|
|
530
|
+
```
|
|
531
|
+
|
|
532
|
+
```tsx fileName="src/app/[locale]/layout.tsx"
|
|
533
|
+
import type { ReactNode } from "react";
|
|
534
|
+
import { locales, defaultLocale, isRtl, type Locale } from "@/i18n.config";
|
|
535
|
+
|
|
536
|
+
export const dynamicParams = false;
|
|
537
|
+
|
|
538
|
+
export function generateStaticParams() {
|
|
539
|
+
return locales.map((locale) => ({ locale }));
|
|
540
|
+
}
|
|
541
|
+
|
|
542
|
+
export default function LocaleLayout({
|
|
543
|
+
children,
|
|
544
|
+
params,
|
|
545
|
+
}: {
|
|
546
|
+
children: ReactNode;
|
|
547
|
+
params: { locale: string };
|
|
548
|
+
}) {
|
|
549
|
+
const locale: Locale = (locales as readonly string[]).includes(params.locale)
|
|
550
|
+
? (params.locale as any)
|
|
551
|
+
: defaultLocale;
|
|
552
|
+
|
|
553
|
+
const dir = isRtl(locale) ? "rtl" : "ltr";
|
|
554
|
+
|
|
555
|
+
return (
|
|
556
|
+
<html lang={locale} dir={dir}>
|
|
557
|
+
<body>{children}</body>
|
|
558
|
+
</html>
|
|
559
|
+
);
|
|
560
|
+
}
|
|
561
|
+
```
|
|
562
|
+
|
|
563
|
+
```tsx fileName="src/app/[locale]/about.tsx"
|
|
564
|
+
import I18nProvider from "@/components/I18nProvider";
|
|
565
|
+
import { initI18next } from "@/app/i18n/server";
|
|
566
|
+
import type { Locale } from "@/i18n.config";
|
|
567
|
+
import ClientComponent from "@/components/ClientComponent";
|
|
568
|
+
import ServerComponent from "@/components/ServerComponent";
|
|
569
|
+
|
|
570
|
+
// Force static rendering for the page
|
|
571
|
+
export const dynamic = "force-static";
|
|
572
|
+
|
|
573
|
+
export default async function AboutPage({
|
|
574
|
+
params: { locale },
|
|
575
|
+
}: {
|
|
576
|
+
params: { locale: Locale };
|
|
577
|
+
}) {
|
|
578
|
+
const namespaces = ["common", "about"] as const;
|
|
579
|
+
|
|
580
|
+
const i18n = await initI18next(locale, [...namespaces]);
|
|
581
|
+
const tAbout = i18n.getFixedT(locale, "about");
|
|
463
582
|
|
|
464
583
|
return (
|
|
465
|
-
<
|
|
584
|
+
<I18nProvider locale={locale} namespaces={[...namespaces]}>
|
|
466
585
|
<main>
|
|
467
|
-
<h1>{
|
|
586
|
+
<h1>{tAbout("title")}</h1>
|
|
587
|
+
|
|
468
588
|
<ClientComponent />
|
|
469
|
-
<ServerComponent />
|
|
589
|
+
<ServerComponent t={tAbout} locale={locale} count={0} />
|
|
470
590
|
</main>
|
|
471
|
-
</
|
|
591
|
+
</I18nProvider>
|
|
472
592
|
);
|
|
473
593
|
}
|
|
474
|
-
|
|
475
|
-
export const getStaticProps: GetStaticProps = async ({ locale }) => {
|
|
476
|
-
// Solo precargar los namespaces necesarios para ESTA página
|
|
477
|
-
return {
|
|
478
|
-
props: {
|
|
479
|
-
...(await serverSideTranslations(locale ?? "en", ["common", "about"])),
|
|
480
|
-
},
|
|
481
|
-
};
|
|
482
|
-
};
|
|
483
594
|
```
|
|
484
595
|
|
|
485
596
|
</TabItem>
|
|
@@ -525,8 +636,10 @@ export default async function LocaleLayout({
|
|
|
525
636
|
const messages = await getMessages();
|
|
526
637
|
const clientMessages = pick(messages, ["common", "about"]);
|
|
527
638
|
|
|
639
|
+
const rtlLocales = ["ar", "he", "fa", "ur"];
|
|
640
|
+
|
|
528
641
|
return (
|
|
529
|
-
<html lang={locale}>
|
|
642
|
+
<html lang={locale} dir={rtlLocales.includes(locale) ? "rtl" : "ltr"}>
|
|
530
643
|
<body>
|
|
531
644
|
<NextIntlClientProvider locale={locale} messages={clientMessages}>
|
|
532
645
|
{children}
|
|
@@ -843,10 +956,11 @@ const ServerComponent = ({ count }: ServerComponentProps) => {
|
|
|
843
956
|
type ServerComponentProps = {
|
|
844
957
|
count: number;
|
|
845
958
|
t: (key: string) => string;
|
|
959
|
+
formatter: Intl.NumberFormat;
|
|
846
960
|
};
|
|
847
961
|
|
|
848
|
-
const ServerComponent = ({ t, count }: ServerComponentProps) => {
|
|
849
|
-
const formatted =
|
|
962
|
+
const ServerComponent = ({ t, count, formatter }: ServerComponentProps) => {
|
|
963
|
+
const formatted = formatter.format(count);
|
|
850
964
|
|
|
851
965
|
return (
|
|
852
966
|
<div>
|
|
@@ -860,7 +974,7 @@ const ServerComponent = ({ t, count }: ServerComponentProps) => {
|
|
|
860
974
|
> Como el componente del servidor no puede ser async, necesitas pasar las traducciones y la función formateadora como props.
|
|
861
975
|
>
|
|
862
976
|
> - `const t = await getTranslations("about.counter");`
|
|
863
|
-
> - `const
|
|
977
|
+
> - `const formatter = await getFormatter().then((formatter) => formatter.number());`
|
|
864
978
|
|
|
865
979
|
</TabItem>
|
|
866
980
|
<TabItem label="intlayer" value="intlayer">
|
|
@@ -19,6 +19,8 @@ slugs:
|
|
|
19
19
|
|
|
20
20
|
# next-i18next VS next-intl VS intlayer | Internationalisation (i18n) Next.js
|
|
21
21
|
|
|
22
|
+

|
|
23
|
+
|
|
22
24
|
Examinons les similitudes et différences entre trois options i18n pour Next.js : next-i18next, next-intl, et Intlayer.
|
|
23
25
|
|
|
24
26
|
Ce n’est pas un tutoriel complet. C’est une comparaison pour vous aider à choisir.
|
|
@@ -165,9 +167,9 @@ Dans le cas de `next-intl` et `next-i18next`, la bibliothèque nécessite de cha
|
|
|
165
167
|
|
|
166
168
|
Voici un exemple de l'impact de l'optimisation de la taille du bundle en utilisant `intlayer` dans une application vite + react :
|
|
167
169
|
|
|
168
|
-
| Bundle optimisé
|
|
169
|
-
|
|
|
170
|
-
|  |  |
|
|
170
|
+
| Bundle optimisé | Bundle non optimisé |
|
|
171
|
+
| ---------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------ |
|
|
172
|
+
|  |  |
|
|
171
173
|
|
|
172
174
|
---
|
|
173
175
|
|
|
@@ -340,25 +342,25 @@ La structure de l'application est importante pour assurer une bonne maintenabili
|
|
|
340
342
|
|
|
341
343
|
```bash
|
|
342
344
|
.
|
|
343
|
-
├──
|
|
344
|
-
│ └── locales
|
|
345
|
-
│ ├── en
|
|
346
|
-
│ │ ├── home.json
|
|
347
|
-
│ │ └── navbar.json
|
|
348
|
-
│ ├── fr
|
|
349
|
-
│ │ ├── home.json
|
|
350
|
-
│ │ └── navbar.json
|
|
351
|
-
│ └── es
|
|
352
|
-
│ ├── home.json
|
|
353
|
-
│ └── navbar.json
|
|
354
|
-
├── next-i18next.config.js
|
|
345
|
+
├── i18n.config.ts
|
|
355
346
|
└── src
|
|
356
|
-
├──
|
|
347
|
+
├── locales
|
|
348
|
+
│ ├── en
|
|
349
|
+
│ │ ├── common.json
|
|
350
|
+
│ │ └── about.json
|
|
351
|
+
│ └── fr
|
|
352
|
+
│ ├── common.json
|
|
353
|
+
│ └── about.json
|
|
357
354
|
├── app
|
|
358
|
-
│
|
|
355
|
+
│ ├── i18n
|
|
356
|
+
│ │ └── server.ts
|
|
357
|
+
│ └── [locale]
|
|
358
|
+
│ ├── layout.tsx
|
|
359
|
+
│ └── about.tsx
|
|
359
360
|
└── components
|
|
360
|
-
|
|
361
|
-
|
|
361
|
+
├── I18nProvider.tsx
|
|
362
|
+
├── ClientComponent.tsx
|
|
363
|
+
└── ServerComponent.tsx
|
|
362
364
|
```
|
|
363
365
|
|
|
364
366
|
</TabItem>
|
|
@@ -366,6 +368,7 @@ La structure de l'application est importante pour assurer une bonne maintenabili
|
|
|
366
368
|
|
|
367
369
|
```bash
|
|
368
370
|
.
|
|
371
|
+
├── i18n.ts
|
|
369
372
|
├── locales
|
|
370
373
|
│ ├── en
|
|
371
374
|
│ │ ├── home.json
|
|
@@ -376,11 +379,13 @@ La structure de l'application est importante pour assurer une bonne maintenabili
|
|
|
376
379
|
│ └── es
|
|
377
380
|
│ ├── home.json
|
|
378
381
|
│ └── navbar.json
|
|
379
|
-
├── i18n.ts
|
|
380
382
|
└── src
|
|
381
383
|
├── middleware.ts
|
|
382
384
|
├── app
|
|
383
|
-
│
|
|
385
|
+
│ ├── i18n
|
|
386
|
+
│ │ └── server.ts
|
|
387
|
+
│ └── [locale]
|
|
388
|
+
│ └── home.tsx
|
|
384
389
|
└── components
|
|
385
390
|
└── Navbar
|
|
386
391
|
└── index.tsx
|
|
@@ -395,9 +400,11 @@ La structure de l'application est importante pour assurer une bonne maintenabili
|
|
|
395
400
|
└── src
|
|
396
401
|
├── middleware.ts
|
|
397
402
|
├── app
|
|
398
|
-
│ └──
|
|
399
|
-
│
|
|
400
|
-
│ └──
|
|
403
|
+
│ └── [locale]
|
|
404
|
+
│ ├── layout.tsx
|
|
405
|
+
│ └── home
|
|
406
|
+
│ ├── index.tsx
|
|
407
|
+
│ └── index.content.ts
|
|
401
408
|
└── components
|
|
402
409
|
└── Navbar
|
|
403
410
|
├── index.tsx
|
|
@@ -525,8 +532,10 @@ export default async function LocaleLayout({
|
|
|
525
532
|
const messages = await getMessages();
|
|
526
533
|
const clientMessages = pick(messages, ["common", "about"]);
|
|
527
534
|
|
|
535
|
+
const rtlLocales = ["ar", "he", "fa", "ur"];
|
|
536
|
+
|
|
528
537
|
return (
|
|
529
|
-
<html lang={locale}>
|
|
538
|
+
<html lang={locale} dir={rtlLocales.includes(locale) ? "rtl" : "ltr"}>
|
|
530
539
|
<body>
|
|
531
540
|
<NextIntlClientProvider locale={locale} messages={clientMessages}>
|
|
532
541
|
{children}
|
|
@@ -843,10 +852,11 @@ const ServerComponent = ({ count }: ServerComponentProps) => {
|
|
|
843
852
|
type ServerComponentProps = {
|
|
844
853
|
count: number;
|
|
845
854
|
t: (key: string) => string;
|
|
855
|
+
formatter: Intl.NumberFormat;
|
|
846
856
|
};
|
|
847
857
|
|
|
848
|
-
const ServerComponent = ({ t, count }: ServerComponentProps) => {
|
|
849
|
-
const formatted =
|
|
858
|
+
const ServerComponent = ({ t, count, formatter }: ServerComponentProps) => {
|
|
859
|
+
const formatted = formatter.format(count);
|
|
850
860
|
|
|
851
861
|
return (
|
|
852
862
|
<div>
|
|
@@ -860,7 +870,7 @@ const ServerComponent = ({ t, count }: ServerComponentProps) => {
|
|
|
860
870
|
> Comme le composant serveur ne peut pas être asynchrone, vous devez passer les traductions et la fonction de formatage en tant que props.
|
|
861
871
|
>
|
|
862
872
|
> - `const t = await getTranslations("about.counter");`
|
|
863
|
-
> - `const
|
|
873
|
+
> - `const formatter = await getFormatter().then((formatter) => formatter.number());`
|
|
864
874
|
|
|
865
875
|
</TabItem>
|
|
866
876
|
<TabItem label="intlayer" value="intlayer">
|