@intlayer/docs 7.2.2 → 7.3.0-canary.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -0
- package/blog/ar/compiler_vs_declarative_i18n.md +138 -0
- package/blog/ar/intlayer_with_next-i18next.md +0 -1
- package/blog/ar/intlayer_with_vue-i18n.md +0 -1
- package/blog/de/compiler_vs_declarative_i18n.md +138 -0
- package/blog/de/intlayer_with_next-i18next.md +0 -1
- package/blog/de/intlayer_with_vue-i18n.md +0 -1
- package/blog/en/compiler_vs_declarative_i18n.md +138 -0
- package/blog/en/i18n_using_next-i18next.md +1 -1
- package/blog/en/i18n_using_next-intl.md +1 -1
- package/blog/en/intlayer_with_i18next.md +1 -1
- package/blog/en/intlayer_with_next-i18next.md +1 -2
- package/blog/en/intlayer_with_next-intl.md +1 -1
- package/blog/en/intlayer_with_react-i18next.md +1 -1
- package/blog/en/intlayer_with_react-intl.md +1 -1
- package/blog/en/intlayer_with_vue-i18n.md +1 -2
- package/blog/en-GB/compiler_vs_declarative_i18n.md +138 -0
- package/blog/en-GB/intlayer_with_next-i18next.md +0 -1
- package/blog/en-GB/intlayer_with_vue-i18n.md +0 -1
- package/blog/es/compiler_vs_declarative_i18n.md +138 -0
- package/blog/es/intlayer_with_next-i18next.md +0 -1
- package/blog/es/intlayer_with_vue-i18n.md +0 -1
- package/blog/fr/compiler_vs_declarative_i18n.md +138 -0
- package/blog/fr/intlayer_with_next-i18next.md +0 -1
- package/blog/fr/intlayer_with_vue-i18n.md +0 -1
- package/blog/hi/compiler_vs_declarative_i18n.md +138 -0
- package/blog/hi/intlayer_with_next-i18next.md +0 -1
- package/blog/hi/intlayer_with_vue-i18n.md +0 -1
- package/blog/id/compiler_vs_declarative_i18n.md +138 -0
- package/blog/id/intlayer_with_next-i18next.md +0 -1
- package/blog/id/intlayer_with_vue-i18n.md +0 -1
- package/blog/it/compiler_vs_declarative_i18n.md +138 -0
- package/blog/it/intlayer_with_next-i18next.md +0 -1
- package/blog/it/intlayer_with_vue-i18n.md +0 -1
- package/blog/ja/compiler_vs_declarative_i18n.md +138 -0
- package/blog/ja/intlayer_with_next-i18next.md +0 -1
- package/blog/ja/intlayer_with_vue-i18n.md +0 -1
- package/blog/ko/compiler_vs_declarative_i18n.md +138 -0
- package/blog/ko/intlayer_with_next-i18next.md +0 -1
- package/blog/ko/intlayer_with_vue-i18n.md +0 -1
- package/blog/pl/compiler_vs_declarative_i18n.md +138 -0
- package/blog/pl/intlayer_with_next-i18next.md +0 -1
- package/blog/pl/intlayer_with_vue-i18n.md +0 -1
- package/blog/pt/compiler_vs_declarative_i18n.md +138 -0
- package/blog/pt/intlayer_with_next-i18next.md +0 -1
- package/blog/pt/intlayer_with_vue-i18n.md +0 -1
- package/blog/ru/compiler_vs_declarative_i18n.md +138 -0
- package/blog/ru/intlayer_with_next-i18next.md +0 -1
- package/blog/ru/intlayer_with_vue-i18n.md +0 -1
- package/blog/tr/compiler_vs_declarative_i18n.md +138 -0
- package/blog/tr/intlayer_with_next-i18next.md +0 -1
- package/blog/tr/intlayer_with_vue-i18n.md +0 -1
- package/blog/vi/compiler_vs_declarative_i18n.md +138 -0
- package/blog/vi/intlayer_with_next-i18next.md +0 -1
- package/blog/vi/intlayer_with_vue-i18n.md +0 -1
- package/blog/zh/compiler_vs_declarative_i18n.md +138 -0
- package/blog/zh/intlayer_with_next-i18next.md +0 -1
- package/blog/zh/intlayer_with_vue-i18n.md +0 -1
- package/dist/cjs/generated/blog.entry.cjs +19 -0
- package/dist/cjs/generated/blog.entry.cjs.map +1 -1
- package/dist/cjs/generated/docs.entry.cjs +323 -19
- package/dist/cjs/generated/docs.entry.cjs.map +1 -1
- package/dist/esm/generated/blog.entry.mjs +19 -0
- package/dist/esm/generated/blog.entry.mjs.map +1 -1
- package/dist/esm/generated/docs.entry.mjs +323 -19
- package/dist/esm/generated/docs.entry.mjs.map +1 -1
- package/dist/types/generated/blog.entry.d.ts +1 -0
- package/dist/types/generated/blog.entry.d.ts.map +1 -1
- package/dist/types/generated/docs.entry.d.ts +17 -1
- package/dist/types/generated/docs.entry.d.ts.map +1 -1
- package/docs/ar/cli/build.md +64 -0
- package/docs/ar/cli/configuration.md +63 -0
- package/docs/ar/cli/debug.md +46 -0
- package/docs/ar/cli/doc-review.md +43 -0
- package/docs/ar/cli/doc-translate.md +132 -0
- package/docs/ar/cli/editor.md +28 -0
- package/docs/ar/cli/fill.md +130 -0
- package/docs/ar/cli/index.md +163 -0
- package/docs/ar/cli/list.md +53 -0
- package/docs/ar/cli/live.md +41 -0
- package/docs/ar/cli/pull.md +78 -0
- package/docs/ar/cli/push.md +98 -0
- package/docs/ar/cli/sdk.md +67 -0
- package/docs/ar/cli/test.md +76 -0
- package/docs/ar/cli/transform.md +65 -0
- package/docs/ar/cli/version.md +24 -0
- package/docs/ar/cli/watch.md +37 -0
- package/docs/ar/intlayer_with_svelte_kit.md +3 -2
- package/docs/ar/packages/intlayer/getPrefix.md +210 -0
- package/docs/de/cli/build.md +64 -0
- package/docs/de/cli/configuration.md +63 -0
- package/docs/de/cli/debug.md +46 -0
- package/docs/de/cli/doc-review.md +43 -0
- package/docs/de/cli/doc-translate.md +132 -0
- package/docs/de/cli/editor.md +28 -0
- package/docs/de/cli/fill.md +130 -0
- package/docs/de/cli/index.md +163 -0
- package/docs/de/cli/list.md +53 -0
- package/docs/de/cli/live.md +41 -0
- package/docs/de/cli/pull.md +78 -0
- package/docs/de/cli/push.md +98 -0
- package/docs/de/cli/sdk.md +67 -0
- package/docs/de/cli/test.md +76 -0
- package/docs/de/cli/transform.md +65 -0
- package/docs/de/cli/version.md +24 -0
- package/docs/de/cli/watch.md +37 -0
- package/docs/de/intlayer_with_svelte_kit.md +3 -2
- package/docs/de/packages/intlayer/getPrefix.md +213 -0
- package/docs/en/CI_CD.md +2 -2
- package/docs/en/autoFill.md +24 -2
- package/docs/en/cli/build.md +64 -0
- package/docs/en/cli/configuration.md +63 -0
- package/docs/en/cli/debug.md +46 -0
- package/docs/en/cli/doc-review.md +43 -0
- package/docs/en/cli/doc-translate.md +132 -0
- package/docs/en/cli/editor.md +28 -0
- package/docs/en/cli/fill.md +130 -0
- package/docs/en/cli/index.md +163 -0
- package/docs/en/cli/list.md +53 -0
- package/docs/en/cli/live.md +41 -0
- package/docs/en/cli/pull.md +78 -0
- package/docs/en/cli/push.md +98 -0
- package/docs/en/cli/sdk.md +67 -0
- package/docs/en/cli/test.md +76 -0
- package/docs/en/cli/transform.md +65 -0
- package/docs/en/cli/version.md +24 -0
- package/docs/en/cli/watch.md +37 -0
- package/docs/en/dictionary/condition.md +1 -1
- package/docs/en/dictionary/enumeration.md +1 -1
- package/docs/en/dictionary/file.md +1 -1
- package/docs/en/dictionary/gender.md +1 -1
- package/docs/en/dictionary/insertion.md +1 -1
- package/docs/en/dictionary/markdown.md +1 -1
- package/docs/en/dictionary/nesting.md +1 -1
- package/docs/en/index.md +1 -1
- package/docs/en/intlayer_with_angular.md +1 -1
- package/docs/en/intlayer_with_astro.md +1 -1
- package/docs/en/intlayer_with_create_react_app.md +1 -1
- package/docs/en/intlayer_with_lynx+react.md +1 -1
- package/docs/en/intlayer_with_next-i18next.md +1 -1
- package/docs/en/intlayer_with_next-intl.md +1 -1
- package/docs/en/intlayer_with_nextjs_14.md +1 -1
- package/docs/en/intlayer_with_nextjs_15.md +1 -1
- package/docs/en/intlayer_with_nextjs_16.md +1 -1
- package/docs/en/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/en/intlayer_with_nuxt.md +1 -1
- package/docs/en/intlayer_with_react_native+expo.md +1 -1
- package/docs/en/intlayer_with_react_router_v7.md +1 -1
- package/docs/en/intlayer_with_svelte_kit.md +3 -2
- package/docs/en/intlayer_with_tanstack.md +1 -1
- package/docs/en/intlayer_with_vite+preact.md +1 -1
- package/docs/en/intlayer_with_vite+react.md +1 -1
- package/docs/en/intlayer_with_vite+solid.md +1 -1
- package/docs/en/intlayer_with_vite+svelte.md +1 -1
- package/docs/en/intlayer_with_vite+vue.md +1 -1
- package/docs/en/introduction.md +1 -1
- package/docs/en/mcp_server.md +1 -2
- package/docs/en/per_locale_file.md +1 -1
- package/docs/en/plugins/sync-json.md +1 -1
- package/docs/en/releases/v6.md +2 -2
- package/docs/en/roadmap.md +1 -1
- package/docs/en-GB/cli/build.md +64 -0
- package/docs/en-GB/cli/configuration.md +63 -0
- package/docs/en-GB/cli/debug.md +46 -0
- package/docs/en-GB/cli/doc-review.md +43 -0
- package/docs/en-GB/cli/doc-translate.md +132 -0
- package/docs/en-GB/cli/editor.md +28 -0
- package/docs/en-GB/cli/fill.md +130 -0
- package/docs/en-GB/cli/index.md +163 -0
- package/docs/en-GB/cli/list.md +53 -0
- package/docs/en-GB/cli/live.md +41 -0
- package/docs/en-GB/cli/pull.md +78 -0
- package/docs/en-GB/cli/push.md +98 -0
- package/docs/en-GB/cli/sdk.md +67 -0
- package/docs/en-GB/cli/test.md +100 -0
- package/docs/en-GB/cli/transform.md +65 -0
- package/docs/en-GB/cli/version.md +24 -0
- package/docs/en-GB/cli/watch.md +37 -0
- package/docs/en-GB/dictionary/condition.md +1 -1
- package/docs/en-GB/dictionary/markdown.md +1 -1
- package/docs/en-GB/dictionary/nesting.md +1 -1
- package/docs/en-GB/intlayer_with_nextjs_14.md +1 -1
- package/docs/en-GB/intlayer_with_react_native+expo.md +1 -1
- package/docs/en-GB/intlayer_with_svelte_kit.md +3 -2
- package/docs/en-GB/packages/intlayer/getPrefix.md +213 -0
- package/docs/es/cli/build.md +64 -0
- package/docs/es/cli/configuration.md +63 -0
- package/docs/es/cli/debug.md +46 -0
- package/docs/es/cli/doc-review.md +43 -0
- package/docs/es/cli/doc-translate.md +132 -0
- package/docs/es/cli/editor.md +28 -0
- package/docs/es/cli/fill.md +130 -0
- package/docs/es/cli/index.md +163 -0
- package/docs/es/cli/list.md +53 -0
- package/docs/es/cli/live.md +41 -0
- package/docs/es/cli/pull.md +78 -0
- package/docs/es/cli/push.md +98 -0
- package/docs/es/cli/sdk.md +67 -0
- package/docs/es/cli/test.md +76 -0
- package/docs/es/cli/transform.md +65 -0
- package/docs/es/cli/version.md +24 -0
- package/docs/es/cli/watch.md +37 -0
- package/docs/es/intlayer_with_svelte_kit.md +3 -2
- package/docs/es/packages/intlayer/getPrefix.md +213 -0
- package/docs/fr/cli/build.md +64 -0
- package/docs/fr/cli/configuration.md +63 -0
- package/docs/fr/cli/debug.md +46 -0
- package/docs/fr/cli/doc-review.md +43 -0
- package/docs/fr/cli/doc-translate.md +132 -0
- package/docs/fr/cli/editor.md +28 -0
- package/docs/fr/cli/fill.md +130 -0
- package/docs/fr/cli/index.md +163 -0
- package/docs/fr/cli/list.md +53 -0
- package/docs/fr/cli/live.md +41 -0
- package/docs/fr/cli/pull.md +78 -0
- package/docs/fr/cli/push.md +98 -0
- package/docs/fr/cli/sdk.md +67 -0
- package/docs/fr/cli/test.md +76 -0
- package/docs/fr/cli/transform.md +65 -0
- package/docs/fr/cli/version.md +24 -0
- package/docs/fr/cli/watch.md +37 -0
- package/docs/fr/intlayer_with_svelte_kit.md +3 -2
- package/docs/fr/packages/intlayer/getPrefix.md +213 -0
- package/docs/hi/cli/build.md +64 -0
- package/docs/hi/cli/configuration.md +63 -0
- package/docs/hi/cli/debug.md +46 -0
- package/docs/hi/cli/doc-review.md +43 -0
- package/docs/hi/cli/doc-translate.md +132 -0
- package/docs/hi/cli/editor.md +28 -0
- package/docs/hi/cli/fill.md +130 -0
- package/docs/hi/cli/index.md +163 -0
- package/docs/hi/cli/list.md +53 -0
- package/docs/hi/cli/live.md +41 -0
- package/docs/hi/cli/pull.md +78 -0
- package/docs/hi/cli/push.md +98 -0
- package/docs/hi/cli/sdk.md +67 -0
- package/docs/hi/cli/test.md +76 -0
- package/docs/hi/cli/transform.md +65 -0
- package/docs/hi/cli/version.md +24 -0
- package/docs/hi/cli/watch.md +37 -0
- package/docs/hi/intlayer_with_svelte_kit.md +3 -2
- package/docs/hi/intlayer_with_tanstack.md +1 -1
- package/docs/hi/intlayer_with_vite+solid.md +1 -1
- package/docs/hi/packages/intlayer/getPrefix.md +217 -0
- package/docs/id/cli/build.md +64 -0
- package/docs/id/cli/configuration.md +62 -0
- package/docs/id/cli/debug.md +46 -0
- package/docs/id/cli/doc-review.md +43 -0
- package/docs/id/cli/doc-translate.md +132 -0
- package/docs/id/cli/editor.md +28 -0
- package/docs/id/cli/fill.md +130 -0
- package/docs/id/cli/index.md +163 -0
- package/docs/id/cli/list.md +53 -0
- package/docs/id/cli/live.md +41 -0
- package/docs/id/cli/pull.md +78 -0
- package/docs/id/cli/push.md +98 -0
- package/docs/id/cli/sdk.md +67 -0
- package/docs/id/cli/test.md +76 -0
- package/docs/id/cli/transform.md +65 -0
- package/docs/id/cli/version.md +24 -0
- package/docs/id/cli/watch.md +37 -0
- package/docs/id/intlayer_with_svelte_kit.md +3 -2
- package/docs/id/packages/intlayer/getPrefix.md +210 -0
- package/docs/it/cli/build.md +64 -0
- package/docs/it/cli/configuration.md +63 -0
- package/docs/it/cli/debug.md +46 -0
- package/docs/it/cli/doc-review.md +43 -0
- package/docs/it/cli/doc-translate.md +132 -0
- package/docs/it/cli/editor.md +28 -0
- package/docs/it/cli/fill.md +130 -0
- package/docs/it/cli/index.md +158 -0
- package/docs/it/cli/list.md +53 -0
- package/docs/it/cli/live.md +41 -0
- package/docs/it/cli/pull.md +78 -0
- package/docs/it/cli/push.md +98 -0
- package/docs/it/cli/sdk.md +67 -0
- package/docs/it/cli/test.md +76 -0
- package/docs/it/cli/transform.md +65 -0
- package/docs/it/cli/version.md +24 -0
- package/docs/it/cli/watch.md +39 -0
- package/docs/it/intlayer_with_svelte_kit.md +3 -2
- package/docs/it/packages/intlayer/getPrefix.md +211 -0
- package/docs/ja/cli/build.md +78 -0
- package/docs/ja/cli/configuration.md +63 -0
- package/docs/ja/cli/debug.md +46 -0
- package/docs/ja/cli/doc-review.md +43 -0
- package/docs/ja/cli/doc-translate.md +132 -0
- package/docs/ja/cli/editor.md +28 -0
- package/docs/ja/cli/fill.md +130 -0
- package/docs/ja/cli/index.md +163 -0
- package/docs/ja/cli/list.md +53 -0
- package/docs/ja/cli/live.md +41 -0
- package/docs/ja/cli/pull.md +78 -0
- package/docs/ja/cli/push.md +113 -0
- package/docs/ja/cli/sdk.md +67 -0
- package/docs/ja/cli/test.md +76 -0
- package/docs/ja/cli/transform.md +65 -0
- package/docs/ja/cli/version.md +24 -0
- package/docs/ja/cli/watch.md +37 -0
- package/docs/ja/intlayer_with_svelte_kit.md +3 -2
- package/docs/ja/packages/intlayer/getPrefix.md +212 -0
- package/docs/ko/cli/build.md +64 -0
- package/docs/ko/cli/configuration.md +63 -0
- package/docs/ko/cli/debug.md +46 -0
- package/docs/ko/cli/doc-review.md +43 -0
- package/docs/ko/cli/doc-translate.md +132 -0
- package/docs/ko/cli/editor.md +28 -0
- package/docs/ko/cli/fill.md +130 -0
- package/docs/ko/cli/index.md +163 -0
- package/docs/ko/cli/list.md +53 -0
- package/docs/ko/cli/live.md +41 -0
- package/docs/ko/cli/pull.md +78 -0
- package/docs/ko/cli/push.md +113 -0
- package/docs/ko/cli/sdk.md +67 -0
- package/docs/ko/cli/test.md +76 -0
- package/docs/ko/cli/transform.md +65 -0
- package/docs/ko/cli/version.md +24 -0
- package/docs/ko/cli/watch.md +37 -0
- package/docs/ko/intlayer_with_svelte_kit.md +3 -2
- package/docs/ko/packages/intlayer/getPrefix.md +213 -0
- package/docs/pl/cli/build.md +64 -0
- package/docs/pl/cli/configuration.md +63 -0
- package/docs/pl/cli/debug.md +46 -0
- package/docs/pl/cli/doc-review.md +43 -0
- package/docs/pl/cli/doc-translate.md +132 -0
- package/docs/pl/cli/editor.md +28 -0
- package/docs/pl/cli/fill.md +130 -0
- package/docs/pl/cli/index.md +163 -0
- package/docs/pl/cli/list.md +53 -0
- package/docs/pl/cli/live.md +41 -0
- package/docs/pl/cli/pull.md +78 -0
- package/docs/pl/cli/push.md +98 -0
- package/docs/pl/cli/sdk.md +67 -0
- package/docs/pl/cli/test.md +76 -0
- package/docs/pl/cli/transform.md +65 -0
- package/docs/pl/cli/version.md +24 -0
- package/docs/pl/cli/watch.md +39 -0
- package/docs/pl/intlayer_with_svelte_kit.md +3 -2
- package/docs/pl/packages/intlayer/getPrefix.md +217 -0
- package/docs/pt/cli/build.md +64 -0
- package/docs/pt/cli/configuration.md +63 -0
- package/docs/pt/cli/debug.md +46 -0
- package/docs/pt/cli/doc-review.md +43 -0
- package/docs/pt/cli/doc-translate.md +132 -0
- package/docs/pt/cli/editor.md +28 -0
- package/docs/pt/cli/fill.md +130 -0
- package/docs/pt/cli/index.md +163 -0
- package/docs/pt/cli/list.md +53 -0
- package/docs/pt/cli/live.md +41 -0
- package/docs/pt/cli/pull.md +78 -0
- package/docs/pt/cli/push.md +98 -0
- package/docs/pt/cli/sdk.md +67 -0
- package/docs/pt/cli/test.md +76 -0
- package/docs/pt/cli/transform.md +65 -0
- package/docs/pt/cli/version.md +24 -0
- package/docs/pt/cli/watch.md +39 -0
- package/docs/pt/intlayer_with_svelte_kit.md +3 -2
- package/docs/pt/packages/intlayer/getPrefix.md +217 -0
- package/docs/ru/cli/build.md +64 -0
- package/docs/ru/cli/configuration.md +63 -0
- package/docs/ru/cli/debug.md +46 -0
- package/docs/ru/cli/doc-review.md +43 -0
- package/docs/ru/cli/doc-translate.md +132 -0
- package/docs/ru/cli/editor.md +28 -0
- package/docs/ru/cli/fill.md +130 -0
- package/docs/ru/cli/index.md +163 -0
- package/docs/ru/cli/list.md +53 -0
- package/docs/ru/cli/live.md +41 -0
- package/docs/ru/cli/pull.md +78 -0
- package/docs/ru/cli/push.md +98 -0
- package/docs/ru/cli/sdk.md +67 -0
- package/docs/ru/cli/test.md +76 -0
- package/docs/ru/cli/transform.md +65 -0
- package/docs/ru/cli/version.md +24 -0
- package/docs/ru/cli/watch.md +39 -0
- package/docs/ru/intlayer_with_svelte_kit.md +3 -2
- package/docs/ru/packages/intlayer/getPrefix.md +213 -0
- package/docs/tr/CI_CD.md +2 -2
- package/docs/tr/cli/build.md +64 -0
- package/docs/tr/cli/configuration.md +63 -0
- package/docs/tr/cli/debug.md +46 -0
- package/docs/tr/cli/doc-review.md +43 -0
- package/docs/tr/cli/doc-translate.md +132 -0
- package/docs/tr/cli/editor.md +28 -0
- package/docs/tr/cli/fill.md +130 -0
- package/docs/tr/cli/index.md +163 -0
- package/docs/tr/cli/list.md +53 -0
- package/docs/tr/cli/live.md +41 -0
- package/docs/tr/cli/pull.md +78 -0
- package/docs/tr/cli/push.md +98 -0
- package/docs/tr/cli/sdk.md +67 -0
- package/docs/tr/cli/test.md +76 -0
- package/docs/tr/cli/transform.md +65 -0
- package/docs/tr/cli/version.md +24 -0
- package/docs/tr/cli/watch.md +39 -0
- package/docs/tr/dictionary/condition.md +1 -1
- package/docs/tr/dictionary/enumeration.md +1 -1
- package/docs/tr/dictionary/file.md +1 -1
- package/docs/tr/dictionary/gender.md +1 -1
- package/docs/tr/dictionary/insertion.md +1 -1
- package/docs/tr/dictionary/markdown.md +1 -1
- package/docs/tr/dictionary/nesting.md +1 -1
- package/docs/tr/index.md +1 -1
- package/docs/tr/intlayer_with_angular.md +1 -1
- package/docs/tr/intlayer_with_create_react_app.md +1 -1
- package/docs/tr/intlayer_with_lynx+react.md +1 -1
- package/docs/tr/intlayer_with_nextjs_15.md +1 -1
- package/docs/tr/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/tr/intlayer_with_nuxt.md +1 -1
- package/docs/tr/intlayer_with_react_native+expo.md +1 -1
- package/docs/tr/intlayer_with_svelte_kit.md +3 -2
- package/docs/tr/intlayer_with_vite+preact.md +1 -1
- package/docs/tr/intlayer_with_vite+react.md +1 -1
- package/docs/tr/intlayer_with_vite+solid.md +1 -1
- package/docs/tr/intlayer_with_vite+vue.md +1 -1
- package/docs/tr/introduction.md +1 -1
- package/docs/tr/mcp_server.md +1 -1
- package/docs/tr/packages/intlayer/getPrefix.md +213 -0
- package/docs/tr/per_locale_file.md +1 -1
- package/docs/tr/roadmap.md +1 -1
- package/docs/vi/cli/build.md +64 -0
- package/docs/vi/cli/configuration.md +63 -0
- package/docs/vi/cli/debug.md +46 -0
- package/docs/vi/cli/doc-review.md +43 -0
- package/docs/vi/cli/doc-translate.md +132 -0
- package/docs/vi/cli/editor.md +28 -0
- package/docs/vi/cli/fill.md +130 -0
- package/docs/vi/cli/index.md +163 -0
- package/docs/vi/cli/list.md +53 -0
- package/docs/vi/cli/live.md +41 -0
- package/docs/vi/cli/pull.md +78 -0
- package/docs/vi/cli/push.md +98 -0
- package/docs/vi/cli/sdk.md +67 -0
- package/docs/vi/cli/test.md +76 -0
- package/docs/vi/cli/transform.md +65 -0
- package/docs/vi/cli/version.md +24 -0
- package/docs/vi/cli/watch.md +37 -0
- package/docs/vi/intlayer_with_svelte_kit.md +3 -2
- package/docs/vi/packages/intlayer/getPrefix.md +213 -0
- package/docs/zh/cli/build.md +64 -0
- package/docs/zh/cli/configuration.md +63 -0
- package/docs/zh/cli/debug.md +46 -0
- package/docs/zh/cli/doc-review.md +43 -0
- package/docs/zh/cli/doc-translate.md +132 -0
- package/docs/zh/cli/editor.md +28 -0
- package/docs/zh/cli/fill.md +130 -0
- package/docs/zh/cli/index.md +168 -0
- package/docs/zh/cli/list.md +53 -0
- package/docs/zh/cli/live.md +41 -0
- package/docs/zh/cli/pull.md +78 -0
- package/docs/zh/cli/push.md +113 -0
- package/docs/zh/cli/sdk.md +67 -0
- package/docs/zh/cli/test.md +76 -0
- package/docs/zh/cli/transform.md +65 -0
- package/docs/zh/cli/version.md +24 -0
- package/docs/zh/cli/watch.md +37 -0
- package/docs/zh/intlayer_with_svelte_kit.md +3 -2
- package/docs/zh/packages/intlayer/getPrefix.md +213 -0
- package/package.json +7 -7
- package/src/generated/blog.entry.ts +19 -0
- package/src/generated/docs.entry.ts +323 -19
- package/docs/ar/intlayer_cli.md +0 -578
- package/docs/de/intlayer_cli.md +0 -579
- package/docs/en/intlayer_cli.md +0 -857
- package/docs/en-GB/intlayer_cli.md +0 -579
- package/docs/es/intlayer_cli.md +0 -578
- package/docs/fr/intlayer_cli.md +0 -578
- package/docs/hi/intlayer_cli.md +0 -580
- package/docs/id/intlayer_cli.md +0 -850
- package/docs/it/intlayer_cli.md +0 -574
- package/docs/ja/intlayer_cli.md +0 -580
- package/docs/ko/intlayer_cli.md +0 -578
- package/docs/pl/intlayer_cli.md +0 -857
- package/docs/pt/intlayer_cli.md +0 -579
- package/docs/ru/intlayer_cli.md +0 -849
- package/docs/tr/intlayer_cli.md +0 -578
- package/docs/vi/intlayer_cli.md +0 -850
- package/docs/zh/intlayer_cli.md +0 -577
|
@@ -187,7 +187,6 @@ Oluşturulan dosyaları sürüm kontrolünden hariç tutun:
|
|
|
187
187
|
```plaintext fileName=".gitignore"
|
|
188
188
|
# Intlayer tarafından oluşturulan dosyaları yoksay
|
|
189
189
|
.intlayer
|
|
190
|
-
intl
|
|
191
190
|
```
|
|
192
191
|
|
|
193
192
|
Bu dosyalar derleme sürecinde otomatik olarak yeniden oluşturulur ve depoza gönderilmesine gerek yoktur.
|
|
@@ -166,7 +166,6 @@ Oluşturulan dosyaları sürüm kontrolünden hariç tutun:
|
|
|
166
166
|
```plaintext fileName=".gitignore"
|
|
167
167
|
# Intlayer tarafından oluşturulan dosyaları yoksay
|
|
168
168
|
.intlayer
|
|
169
|
-
intl
|
|
170
169
|
```
|
|
171
170
|
|
|
172
171
|
Bu dosyalar derleme sürecinde otomatik olarak yeniden oluşturulur ve depoza gönderilmesine gerek yoktur.
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
---
|
|
2
|
+
createdAt: 2025-11-24
|
|
3
|
+
updatedAt: 2025-11-24
|
|
4
|
+
title: Trình Biên Dịch so với i18n Khai Báo
|
|
5
|
+
description: Khám phá các đánh đổi kiến trúc giữa quốc tế hóa dựa trên trình biên dịch "ma thuật" và quản lý nội dung khai báo rõ ràng.
|
|
6
|
+
keywords:
|
|
7
|
+
- Intlayer
|
|
8
|
+
- Quốc tế hóa
|
|
9
|
+
- Blog
|
|
10
|
+
- Next.js
|
|
11
|
+
- JavaScript
|
|
12
|
+
- React
|
|
13
|
+
- i18n
|
|
14
|
+
- Trình Biên Dịch
|
|
15
|
+
- Khai Báo
|
|
16
|
+
slugs:
|
|
17
|
+
- compiler-vs-declarative-i18n
|
|
18
|
+
- blog
|
|
19
|
+
- i18n
|
|
20
|
+
---
|
|
21
|
+
|
|
22
|
+
# Lập Luận Ủng Hộ và Phản Đối i18n Dựa Trên Trình Biên Dịch
|
|
23
|
+
|
|
24
|
+
Nếu bạn đã xây dựng các ứng dụng web hơn một thập kỷ, bạn sẽ biết rằng Quốc tế hóa (i18n) luôn là một điểm gây khó khăn. Đây thường là công việc không ai muốn làm — trích xuất chuỗi, quản lý các tệp JSON, và lo lắng về các quy tắc số nhiều.
|
|
25
|
+
|
|
26
|
+
Gần đây, một làn sóng mới các công cụ i18n "dựa trên trình biên dịch" đã xuất hiện, hứa hẹn sẽ làm biến mất những khó khăn này. Lời mời gọi thật hấp dẫn: **Chỉ cần viết văn bản trong các component của bạn, và để công cụ build lo phần còn lại.** Không cần khóa, không cần import, chỉ đơn giản là ma thuật.
|
|
27
|
+
|
|
28
|
+
Nhưng như với tất cả các trừu tượng trong kỹ thuật phần mềm, ma thuật luôn đi kèm với một cái giá.
|
|
29
|
+
|
|
30
|
+
Trong bài blog này, chúng ta sẽ khám phá sự chuyển dịch từ các thư viện khai báo sang các phương pháp dựa trên trình biên dịch, những khoản nợ kiến trúc ẩn mà chúng mang lại, và lý do tại sao cách "nhàm chán" có thể vẫn là cách tốt nhất cho các ứng dụng chuyên nghiệp.
|
|
31
|
+
|
|
32
|
+
## Lịch Sử Ngắn Gọn về Dịch Thuật
|
|
33
|
+
|
|
34
|
+
Để hiểu chúng ta đang ở đâu, chúng ta phải nhìn lại nơi chúng ta đã bắt đầu.
|
|
35
|
+
|
|
36
|
+
Khoảng năm 2011–2012, cảnh quan JavaScript rất khác biệt. Các bundler như chúng ta biết ngày nay (Webpack, Vite) chưa tồn tại hoặc còn trong giai đoạn sơ khai. Chúng ta phải dán các script lại với nhau ngay trong trình duyệt. Trong thời kỳ này, các thư viện như **i18next** đã ra đời.
|
|
37
|
+
|
|
38
|
+
Chúng giải quyết vấn đề theo cách duy nhất có thể vào thời điểm đó: **Từ điển thời gian chạy (Runtime Dictionaries)**. Bạn tải một đối tượng JSON khổng lồ vào bộ nhớ, và một hàm sẽ tra cứu các khóa ngay lập tức. Cách này đáng tin cậy, rõ ràng và hoạt động ở mọi nơi.
|
|
39
|
+
|
|
40
|
+
Tiến tới ngày nay. Chúng ta có các trình biên dịch mạnh mẽ (SWC, các bundler dựa trên Rust) có thể phân tích Cây Cú Pháp Trừu Tượng (AST) trong vài mili giây. Sức mạnh này đã sinh ra một ý tưởng mới: _Tại sao chúng ta phải quản lý khóa thủ công? Tại sao trình biên dịch không thể nhìn thấy đoạn văn bản "Hello World" và thay thế nó cho chúng ta?_
|
|
41
|
+
|
|
42
|
+
Và thế là i18n dựa trên trình biên dịch ra đời.
|
|
43
|
+
|
|
44
|
+
## Sức Hấp Dẫn của Trình Biên Dịch (Cách Tiếp Cận "Phép Thuật")
|
|
45
|
+
|
|
46
|
+
Có một lý do khiến cách tiếp cận mới này đang trở thành xu hướng. Đối với một nhà phát triển, trải nghiệm này thật tuyệt vời.
|
|
47
|
+
|
|
48
|
+
### 1. Tốc Độ và "Dòng Chảy"
|
|
49
|
+
|
|
50
|
+
Khi bạn đang tập trung, việc dừng lại để nghĩ tên biến (`home_hero_title_v2`) sẽ làm gián đoạn dòng chảy công việc của bạn. Với cách tiếp cận trình biên dịch, bạn chỉ cần gõ `<p>Welcome back</p>` và tiếp tục. Không có sự cản trở nào.
|
|
51
|
+
|
|
52
|
+
### 2. Nhiệm Vụ Cứu Hộ Di Sản
|
|
53
|
+
|
|
54
|
+
Hãy tưởng tượng bạn thừa kế một codebase khổng lồ với 5.000 component và không có bản dịch nào. Việc bổ sung hệ thống dựa trên khóa thủ công sẽ là một cơn ác mộng kéo dài hàng tháng. Công cụ dựa trên trình biên dịch hoạt động như một chiến lược cứu hộ, ngay lập tức trích xuất hàng ngàn chuỗi mà bạn không cần phải chạm vào bất kỳ file nào thủ công.
|
|
55
|
+
|
|
56
|
+
### 3. Thời Đại AI
|
|
57
|
+
|
|
58
|
+
Đây là một lợi ích hiện đại mà chúng ta không nên bỏ qua. Các trợ lý lập trình AI (như Copilot hoặc ChatGPT) tự nhiên tạo ra JSX/HTML tiêu chuẩn. Chúng không biết sơ đồ khóa dịch thuật cụ thể của bạn.
|
|
59
|
+
|
|
60
|
+
- **Khai báo:** Bạn phải viết lại đầu ra của AI để thay thế văn bản bằng các khóa.
|
|
61
|
+
- **Trình biên dịch:** Bạn chỉ cần sao chép-dán mã của AI, và nó hoạt động ngay.
|
|
62
|
+
|
|
63
|
+
## Kiểm Tra Thực Tế: Tại Sao "Phép Thuật" Lại Nguy Hiểm
|
|
64
|
+
|
|
65
|
+
Mặc dù "phép thuật" rất hấp dẫn, nhưng sự trừu tượng này lại bị rò rỉ. Dựa vào công cụ xây dựng để hiểu ý định của con người sẽ tạo ra sự mong manh về kiến trúc.
|
|
66
|
+
|
|
67
|
+
### 1. Sự Mong Manh Dựa Trên Phán Đoán (Trò Chơi Đoán)
|
|
68
|
+
|
|
69
|
+
Trình biên dịch phải đoán đâu là nội dung và đâu là mã.
|
|
70
|
+
|
|
71
|
+
- `className="active"` có được dịch không? Nó là một chuỗi.
|
|
72
|
+
- `status="pending"` có được dịch không?
|
|
73
|
+
- Có phải `<MyComponent errorMessage="An error occurred" />` được dịch không?
|
|
74
|
+
- Có phải một ID sản phẩm như `"AX-99"` được dịch không?
|
|
75
|
+
|
|
76
|
+
Bạn không thể tránh khỏi việc "đấu tranh" với trình biên dịch, thêm các chú thích cụ thể (như `// ignore-translation`) để ngăn nó phá vỡ logic ứng dụng của bạn.
|
|
77
|
+
|
|
78
|
+
### 2. Giới Hạn Cứng của Dữ Liệu Động
|
|
79
|
+
|
|
80
|
+
Việc trích xuất của trình biên dịch dựa trên **phân tích tĩnh**. Nó phải nhìn thấy chuỗi ký tự nguyên văn trong mã của bạn để tạo ra một ID ổn định.
|
|
81
|
+
Nếu API của bạn trả về một chuỗi mã lỗi như `server_error`, bạn không thể dịch nó bằng trình biên dịch vì trình biên dịch không biết chuỗi đó tồn tại tại thời điểm xây dựng. Bạn buộc phải xây dựng một hệ thống "chỉ chạy thời gian thực" phụ trợ chỉ dành cho dữ liệu động.
|
|
82
|
+
|
|
83
|
+
### 3. "Bùng Nổ Chunk" và Hiện Tượng Thác Nước Mạng
|
|
84
|
+
|
|
85
|
+
Để cho phép tree-shaking, các công cụ trình biên dịch thường chia nhỏ bản dịch theo từng component.
|
|
86
|
+
|
|
87
|
+
- **Hệ quả:** Một trang hiển thị với 50 component nhỏ có thể kích hoạt **50 yêu cầu HTTP riêng biệt** cho các đoạn dịch nhỏ. Ngay cả với HTTP/2, điều này tạo ra một chuỗi yêu cầu mạng khiến ứng dụng của bạn cảm thấy chậm chạp so với việc tải một gói ngôn ngữ duy nhất được tối ưu hóa.
|
|
88
|
+
|
|
89
|
+
### 4. Chi phí hiệu năng khi chạy
|
|
90
|
+
|
|
91
|
+
Để làm cho bản dịch phản ứng (để chúng cập nhật ngay lập tức khi bạn chuyển đổi ngôn ngữ), trình biên dịch thường chèn các hook quản lý trạng thái vào _mọi_ component.
|
|
92
|
+
|
|
93
|
+
- **Chi phí:** Nếu bạn render một danh sách gồm 5.000 mục, bạn sẽ khởi tạo 5.000 hook `useState` và `useEffect` chỉ để xử lý văn bản. Điều này tiêu tốn bộ nhớ và chu kỳ CPU mà các thư viện khai báo (thường sử dụng một Context provider duy nhất) có thể tiết kiệm được.
|
|
94
|
+
|
|
95
|
+
## Cái bẫy: Bị khóa nhà cung cấp
|
|
96
|
+
|
|
97
|
+
Đây có thể coi là khía cạnh nguy hiểm nhất của i18n dựa trên trình biên dịch.
|
|
98
|
+
|
|
99
|
+
Trong một thư viện khai báo, mã nguồn của bạn chứa ý định rõ ràng. Bạn sở hữu các khóa. Nếu bạn chuyển đổi thư viện, bạn chỉ cần thay đổi phần import.
|
|
100
|
+
|
|
101
|
+
Trong cách tiếp cận dựa trên trình biên dịch, **mã nguồn của bạn chỉ là văn bản tiếng Anh.** "Logic dịch thuật" chỉ tồn tại bên trong cấu hình plugin xây dựng.
|
|
102
|
+
Nếu thư viện đó ngừng được duy trì, hoặc nếu bạn vượt quá khả năng của nó, bạn sẽ bị mắc kẹt. Bạn không thể dễ dàng "eject" vì bạn không có bất kỳ khóa dịch nào trong mã nguồn của mình. Bạn sẽ phải tự tay viết lại toàn bộ ứng dụng để di chuyển sang giải pháp khác.
|
|
103
|
+
|
|
104
|
+
## Mặt khác: Rủi ro của phương pháp khai báo
|
|
105
|
+
|
|
106
|
+
Công bằng mà nói, cách khai báo truyền thống cũng không hoàn hảo. Nó có những "cạm bẫy" riêng.
|
|
107
|
+
|
|
108
|
+
1. **Địa ngục Namespace:** Bạn thường phải quản lý thủ công các tệp JSON nào sẽ được tải (`common.json`, `dashboard.json`, `footer.json`). Nếu bạn quên một tệp, người dùng sẽ thấy các khóa thô.
|
|
109
|
+
2. **Tải quá mức:** Nếu không cấu hình cẩn thận, rất dễ vô tình tải _tất cả_ các khóa dịch của bạn cho _tất cả_ các trang ngay lần tải đầu tiên, làm phình to kích thước gói của bạn.
|
|
110
|
+
3. **Trôi đồng bộ:** Thông thường các khóa vẫn còn trong file JSON dù component sử dụng chúng đã bị xóa. Các file dịch của bạn sẽ ngày càng phình to, chứa đầy các "khóa ma."
|
|
111
|
+
|
|
112
|
+
## Giải pháp Trung gian của Intlayer
|
|
113
|
+
|
|
114
|
+
Đây là nơi các công cụ như **Intlayer** cố gắng đổi mới. Intlayer hiểu rằng dù compiler rất mạnh mẽ, nhưng phép thuật ngầm lại nguy hiểm.
|
|
115
|
+
|
|
116
|
+
Intlayer cung cấp một **lệnh `transform`** độc đáo. Thay vì chỉ làm phép thuật trong bước build ẩn, nó thực sự có thể **viết lại mã component của bạn**. Nó quét văn bản và thay thế bằng các khai báo nội dung rõ ràng trong codebase của bạn.
|
|
117
|
+
|
|
118
|
+
Điều này mang lại cho bạn lợi ích của cả hai thế giới:
|
|
119
|
+
|
|
120
|
+
1. **Độ chi tiết:** Bạn giữ bản dịch gần với các component của mình (cải thiện tính mô-đun và tree-shaking).
|
|
121
|
+
2. **An toàn:** Bản dịch trở thành mã rõ ràng, không phải là phép thuật ẩn trong thời gian build.
|
|
122
|
+
3. **Không bị khóa:** Vì mã được chuyển đổi thành cấu trúc khai báo tiêu chuẩn trong repo của bạn, bạn không giấu logic trong một plugin webpack.
|
|
123
|
+
|
|
124
|
+
## Kết luận
|
|
125
|
+
|
|
126
|
+
Vậy, bạn nên chọn gì?
|
|
127
|
+
|
|
128
|
+
**Nếu bạn là một Junior Developer, một Nhà sáng lập đơn lẻ, hoặc đang xây dựng MVP:**
|
|
129
|
+
Phương pháp dựa trên compiler là một lựa chọn hợp lệ. Nó cho phép bạn di chuyển cực kỳ nhanh. Bạn không cần phải lo lắng về cấu trúc file hay các khóa. Bạn chỉ cần xây dựng. Nợ kỹ thuật là vấn đề của "Bạn trong tương lai."
|
|
130
|
+
|
|
131
|
+
**Nếu bạn đang xây dựng một Ứng dụng Chuyên nghiệp, Cấp Doanh nghiệp:**
|
|
132
|
+
Phép thuật thường là một ý tưởng tồi. Bạn cần kiểm soát.
|
|
133
|
+
|
|
134
|
+
- Bạn cần xử lý dữ liệu động từ backend.
|
|
135
|
+
- Bạn cần đảm bảo hiệu suất trên các thiết bị cấu hình thấp (tránh hiện tượng hook bị quá tải).
|
|
136
|
+
- Bạn cần đảm bảo rằng bạn không bị khóa vào một công cụ build cụ thể mãi mãi.
|
|
137
|
+
|
|
138
|
+
Đối với các ứng dụng chuyên nghiệp, **Quản lý Nội dung Khai báo** (như Intlayer hoặc các thư viện đã được thiết lập) vẫn là tiêu chuẩn vàng. Nó tách biệt các mối quan tâm của bạn, giữ cho kiến trúc của bạn sạch sẽ, và đảm bảo rằng khả năng đa ngôn ngữ của ứng dụng không phụ thuộc vào một trình biên dịch "hộp đen" đoán ý định của bạn.
|
|
@@ -176,7 +176,6 @@ Loại trừ các file được tạo tự động khỏi việc kiểm soát ph
|
|
|
176
176
|
```plaintext fileName=".gitignore"
|
|
177
177
|
# Bỏ qua các file được tạo bởi Intlayer
|
|
178
178
|
.intlayer
|
|
179
|
-
intl
|
|
180
179
|
```
|
|
181
180
|
|
|
182
181
|
Các file này được tự động tạo lại trong quá trình build và không cần phải commit vào kho mã của bạn.
|
|
@@ -166,7 +166,6 @@ Loại trừ các tệp được tạo tự động khỏi kiểm soát phiên b
|
|
|
166
166
|
```plaintext fileName=".gitignore"
|
|
167
167
|
# Bỏ qua các tệp được tạo bởi Intlayer
|
|
168
168
|
.intlayer
|
|
169
|
-
intl
|
|
170
169
|
```
|
|
171
170
|
|
|
172
171
|
Các tệp này được tạo lại tự động trong quá trình xây dựng và không cần phải cam kết vào kho lưu trữ của bạn.
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
---
|
|
2
|
+
createdAt: 2025-11-24
|
|
3
|
+
updatedAt: 2025-11-24
|
|
4
|
+
title: 编译器与声明式国际化的对比
|
|
5
|
+
description: 探讨“魔法”编译器驱动国际化与显式声明式内容管理之间的架构权衡。
|
|
6
|
+
keywords:
|
|
7
|
+
- Intlayer
|
|
8
|
+
- 国际化
|
|
9
|
+
- 博客
|
|
10
|
+
- Next.js
|
|
11
|
+
- JavaScript
|
|
12
|
+
- React
|
|
13
|
+
- i18n
|
|
14
|
+
- 编译器
|
|
15
|
+
- 声明式
|
|
16
|
+
slugs:
|
|
17
|
+
- compiler-vs-declarative-i18n
|
|
18
|
+
- blog
|
|
19
|
+
- i18n
|
|
20
|
+
---
|
|
21
|
+
|
|
22
|
+
# 支持与反对编译器驱动国际化的观点
|
|
23
|
+
|
|
24
|
+
如果你从事网页应用开发超过十年,你会知道国际化(i18n)一直是一个难点。它通常是没人愿意做的任务——提取字符串、管理 JSON 文件,以及处理复数规则。
|
|
25
|
+
|
|
26
|
+
最近,一波新的“编译器驱动”国际化工具出现了,承诺让这份痛苦消失。它们的卖点很诱人:**只需在组件中编写文本,构建工具会处理剩下的一切。**无需键名,无需导入,纯粹是魔法。
|
|
27
|
+
|
|
28
|
+
但正如软件工程中的所有抽象一样,魔法是有代价的。
|
|
29
|
+
|
|
30
|
+
在这篇博客文章中,我们将探讨从声明式库向编译器驱动方法的转变,它们引入的隐藏架构债务,以及为什么“无聊”的方式可能仍然是专业应用的最佳选择。
|
|
31
|
+
|
|
32
|
+
## 翻译的简史
|
|
33
|
+
|
|
34
|
+
要理解我们现在的位置,必须回顾我们从哪里开始。
|
|
35
|
+
|
|
36
|
+
大约在2011年至2012年,JavaScript的生态环境截然不同。我们现在熟知的打包工具(如Webpack、Vite)当时还不存在或处于初期阶段。那时,我们是在浏览器中将脚本拼接在一起。在那个时代,像**i18next**这样的库诞生了。
|
|
37
|
+
|
|
38
|
+
它们以当时唯一可行的方式解决了问题:**运行时字典**。你将一个庞大的JSON对象加载到内存中,然后通过函数动态查找键。它可靠、明确,并且在任何地方都能工作。
|
|
39
|
+
|
|
40
|
+
快进到今天。我们拥有强大的编译器(如SWC、基于Rust的打包工具),能够在毫秒级别解析抽象语法树(AST)。这种能力催生了一个新想法:_为什么我们还要手动管理键?为什么编译器不能直接看到文本“Hello World”并替我们替换它?_
|
|
41
|
+
|
|
42
|
+
于是,基于编译器的i18n诞生了。
|
|
43
|
+
|
|
44
|
+
## 编译器的魅力(“魔法”方法)
|
|
45
|
+
|
|
46
|
+
这种新方法之所以流行是有原因的。对于开发者来说,这种体验令人难以置信。
|
|
47
|
+
|
|
48
|
+
### 1. 速度与“流畅感”
|
|
49
|
+
|
|
50
|
+
当你进入状态时,停下来思考一个变量名(如 `home_hero_title_v2`)会打断你的思路。使用编译器方法时,你只需输入 `<p>Welcome back</p>`,然后继续前进。摩擦为零。
|
|
51
|
+
|
|
52
|
+
### 2. 旧代码救援任务
|
|
53
|
+
|
|
54
|
+
想象一下,继承了一个拥有5000个组件且没有任何翻译的大型代码库。用手动基于键的系统来改造它,将是一场持续数月的噩梦。基于编译器的工具则像一场救援行动,能够瞬间提取成千上万的字符串,而你无需手动触碰任何文件。
|
|
55
|
+
|
|
56
|
+
### 3. AI 时代
|
|
57
|
+
|
|
58
|
+
这是一个我们不应忽视的现代优势。AI 编码助手(如 Copilot 或 ChatGPT)自然生成标准的 JSX/HTML。它们并不知道你特定的翻译键方案。
|
|
59
|
+
|
|
60
|
+
- **声明式(Declarative):** 你必须重写 AI 的输出,将文本替换为键。
|
|
61
|
+
- **编译器(Compiler):** 你只需复制粘贴 AI 的代码,它就能直接工作。
|
|
62
|
+
|
|
63
|
+
## 现实检验:为什么“魔法”是危险的
|
|
64
|
+
|
|
65
|
+
虽然“魔法”很吸引人,但抽象层会泄漏。依赖构建工具去理解人类意图会引入架构上的脆弱性。
|
|
66
|
+
|
|
67
|
+
### 1. 启发式脆弱性(猜测游戏)
|
|
68
|
+
|
|
69
|
+
编译器必须猜测什么是内容,什么是代码。
|
|
70
|
+
|
|
71
|
+
- `className="active"` 会被翻译吗?它是一个字符串。
|
|
72
|
+
- `status="pending"` 会被翻译吗?
|
|
73
|
+
- `<MyComponent errorMessage="An error occurred" />` 会被翻译吗?
|
|
74
|
+
- 像 `"AX-99"` 这样的产品 ID 会被翻译吗?
|
|
75
|
+
|
|
76
|
+
你不可避免地会与编译器“斗争”,添加特定注释(如 `// ignore-translation`)以防止它破坏你的应用逻辑。
|
|
77
|
+
|
|
78
|
+
### 2. 动态数据的硬性限制
|
|
79
|
+
|
|
80
|
+
编译器提取依赖于**静态分析**。它必须在代码中看到字面字符串才能生成稳定的 ID。
|
|
81
|
+
如果你的 API 返回一个错误代码字符串,比如 `server_error`,你无法用编译器翻译它,因为编译器在构建时并不知道该字符串的存在。你被迫为动态数据构建一个次级的“仅运行时”系统。
|
|
82
|
+
|
|
83
|
+
### 3. “块爆炸”和网络瀑布效应
|
|
84
|
+
|
|
85
|
+
为了支持 tree-shaking,编译器工具通常会按组件拆分翻译内容。
|
|
86
|
+
|
|
87
|
+
- **后果:** 一个页面视图中如果有 50 个小组件,可能会触发 **50 个独立的 HTTP 请求** 来获取微小的翻译片段。即使使用 HTTP/2,这也会造成网络瀑布效应,使你的应用相比加载单个优化语言包时显得响应迟缓。
|
|
88
|
+
|
|
89
|
+
### 4. 运行时性能开销
|
|
90
|
+
|
|
91
|
+
为了让翻译具有响应性(以便切换语言时能即时更新),编译器通常会在 _每个_ 组件中注入状态管理钩子。
|
|
92
|
+
|
|
93
|
+
- **代价:** 如果你渲染一个包含5000个条目的列表,你实际上是在为文本初始化5000个 `useState` 和 `useEffect` 钩子。这会消耗大量内存和CPU周期,而声明式库(通常只使用一个 Context 提供者)则能节省这些资源。
|
|
94
|
+
|
|
95
|
+
## 陷阱:供应商锁定
|
|
96
|
+
|
|
97
|
+
这可以说是基于编译器的国际化中最危险的方面。
|
|
98
|
+
|
|
99
|
+
在声明式库中,你的源代码包含明确的意图。你拥有翻译键。如果你切换库,只需更改导入即可。
|
|
100
|
+
|
|
101
|
+
而在基于编译器的方法中,**你的源代码只是英文文本。** “翻译逻辑”仅存在于构建插件的配置中。
|
|
102
|
+
如果该库停止维护,或者你超出了它的能力范围,你就会陷入困境。你无法轻易“弹出”,因为你的源代码中没有任何翻译键。你必须手动重写整个应用程序才能迁移。
|
|
103
|
+
|
|
104
|
+
## 另一面:声明式方法的风险
|
|
105
|
+
|
|
106
|
+
公平地说,传统的声明式方法也并不完美。它有自己的一些“坑”。
|
|
107
|
+
|
|
108
|
+
1. **命名空间地狱:** 你经常需要手动管理加载哪些 JSON 文件(如 `common.json`、`dashboard.json`、`footer.json`)。如果忘记加载其中一个,用户就会看到原始的键名。
|
|
109
|
+
2. **过度获取:** 如果配置不当,很容易在初始加载时意外加载所有页面的所有翻译键,导致包体积膨胀。
|
|
110
|
+
3. **同步漂移(Sync Drift):** 通常情况下,某些键会在对应组件被删除很久之后仍然保留在 JSON 文件中。你的翻译文件会无限增长,充满了“僵尸键”。
|
|
111
|
+
|
|
112
|
+
## Intlayer 的折中方案
|
|
113
|
+
|
|
114
|
+
这正是像 **Intlayer** 这样的工具试图创新的地方。Intlayer 理解编译器虽然强大,但隐式的魔法是危险的。
|
|
115
|
+
|
|
116
|
+
Intlayer 提供了一个独特的 **`transform` 命令**。它不仅仅是在隐藏的构建步骤中做魔法,而是可以实际**重写你的组件代码**。它扫描你的文本,并用显式的内容声明替换代码库中的文本。
|
|
117
|
+
|
|
118
|
+
这让你同时拥有两者的优点:
|
|
119
|
+
|
|
120
|
+
1. **粒度控制(Granularity):** 你可以将翻译内容保持在组件附近(提升模块化和 tree-shaking 效果)。
|
|
121
|
+
2. **安全性:** 翻译变成了显式代码,而不是隐藏的构建时魔法。
|
|
122
|
+
3. **无锁定:** 由于代码被转换为仓库内的标准声明式结构,你不会将逻辑隐藏在 webpack 插件中。
|
|
123
|
+
|
|
124
|
+
## 结论
|
|
125
|
+
|
|
126
|
+
那么,你应该选择哪种方案?
|
|
127
|
+
|
|
128
|
+
**如果你是初级开发者、独立创始人,或者正在构建 MVP:**
|
|
129
|
+
基于编译器的方法是一个有效的选择。它允许你非常快速地开发。你无需担心文件结构或键值。你只需构建。技术债务是“未来的你”的问题。
|
|
130
|
+
|
|
131
|
+
**如果你正在构建专业的企业级应用:**
|
|
132
|
+
魔法通常不是一个好主意。你需要掌控。
|
|
133
|
+
|
|
134
|
+
- 你需要处理来自后端的动态数据。
|
|
135
|
+
- 您需要确保在低端设备上的性能(避免钩子爆炸)。
|
|
136
|
+
- 您需要确保不会永远被锁定在特定的构建工具中。
|
|
137
|
+
|
|
138
|
+
对于专业应用,**声明式内容管理**(如 Intlayer 或成熟的库)仍然是黄金标准。它将关注点分离,保持架构清晰,并确保您的应用多语言能力不依赖于“黑盒”编译器去猜测您的意图。
|
|
@@ -24,6 +24,25 @@ const readLocale = (relativeAfterLocale, locale) => {
|
|
|
24
24
|
return Promise.reject(/* @__PURE__ */ new Error(`[docs] File not found: ${relativeAfterLocale} - locale: ${locale} - path: ${target1} - path: ${target2}`));
|
|
25
25
|
};
|
|
26
26
|
const blogEntry = {
|
|
27
|
+
"./blog/en/compiler_vs_declarative_i18n.md": {
|
|
28
|
+
en: readLocale("compiler_vs_declarative_i18n.md", "en"),
|
|
29
|
+
ru: readLocale("compiler_vs_declarative_i18n.md", "ru"),
|
|
30
|
+
ja: readLocale("compiler_vs_declarative_i18n.md", "ja"),
|
|
31
|
+
fr: readLocale("compiler_vs_declarative_i18n.md", "fr"),
|
|
32
|
+
ko: readLocale("compiler_vs_declarative_i18n.md", "ko"),
|
|
33
|
+
zh: readLocale("compiler_vs_declarative_i18n.md", "zh"),
|
|
34
|
+
es: readLocale("compiler_vs_declarative_i18n.md", "es"),
|
|
35
|
+
de: readLocale("compiler_vs_declarative_i18n.md", "de"),
|
|
36
|
+
ar: readLocale("compiler_vs_declarative_i18n.md", "ar"),
|
|
37
|
+
it: readLocale("compiler_vs_declarative_i18n.md", "it"),
|
|
38
|
+
"en-GB": readLocale("compiler_vs_declarative_i18n.md", "en-GB"),
|
|
39
|
+
pt: readLocale("compiler_vs_declarative_i18n.md", "pt"),
|
|
40
|
+
hi: readLocale("compiler_vs_declarative_i18n.md", "hi"),
|
|
41
|
+
tr: readLocale("compiler_vs_declarative_i18n.md", "tr"),
|
|
42
|
+
pl: readLocale("compiler_vs_declarative_i18n.md", "pl"),
|
|
43
|
+
id: readLocale("compiler_vs_declarative_i18n.md", "id"),
|
|
44
|
+
vi: readLocale("compiler_vs_declarative_i18n.md", "vi")
|
|
45
|
+
},
|
|
27
46
|
"./blog/en/i18n_using_next-i18next.md": {
|
|
28
47
|
en: readLocale("i18n_using_next-i18next.md", "en"),
|
|
29
48
|
ru: readLocale("i18n_using_next-i18next.md", "ru"),
|