@intlayer/docs 9.5.2 → 9.5.4-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 +9 -9
- package/blog/ar/history_of_i18n.md +54 -54
- package/blog/ar/how_to_pick_react_i18n_library.md +548 -0
- package/blog/ar/how_to_pick_solid_i18n_library.md +438 -0
- package/blog/ar/how_to_pick_svelte_i18n_library.md +454 -0
- package/blog/ar/how_to_pick_vue_i18n_library.md +442 -0
- package/blog/ar/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/ar/i18next_vs_intlayer.md +445 -0
- package/blog/ar/is_i18next_outdated.md +6 -2
- package/blog/ar/is_next-intl_outdated.md +6 -2
- package/blog/ar/is_vue-i18n_outdated.md +8 -2
- package/blog/ar/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/ar/lingui_vs_intlayer.md +381 -0
- package/blog/ar/next-i18next_vs_next-intl_vs_intlayer.md +9 -5
- package/blog/ar/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/ar/next-intl_vs_intlayer.md +397 -0
- package/blog/ar/per-component_vs_centralized_i18n.md +9 -4
- package/blog/ar/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/ar/vue-i18n_vs_intlayer-vue-i18n.md +286 -0
- package/blog/ar/vue-i18n_vs_intlayer_benchmark.md +0 -0
- package/blog/de/history_of_i18n.md +54 -54
- package/blog/de/how_to_pick_react_i18n_library.md +548 -0
- package/blog/de/how_to_pick_solid_i18n_library.md +451 -0
- package/blog/de/how_to_pick_svelte_i18n_library.md +454 -0
- package/blog/de/how_to_pick_vue_i18n_library.md +448 -0
- package/blog/de/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/de/i18next_vs_intlayer.md +445 -0
- package/blog/de/is_i18next_outdated.md +6 -2
- package/blog/de/is_next-intl_outdated.md +6 -2
- package/blog/de/is_vue-i18n_outdated.md +8 -2
- package/blog/de/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/de/lingui_vs_intlayer.md +381 -0
- package/blog/de/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/de/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/de/next-intl_vs_intlayer.md +415 -0
- package/blog/de/per-component_vs_centralized_i18n.md +9 -4
- package/blog/de/react-i18next_vs_react-intl_vs_intlayer.md +5 -1
- package/blog/de/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/de/vue-i18n_vs_intlayer_benchmark.md +355 -0
- package/blog/en/history_of_i18n.md +54 -54
- package/blog/en/how_to_pick_react_i18n_library.md +542 -0
- package/blog/en/how_to_pick_solid_i18n_library.md +438 -0
- package/blog/en/how_to_pick_svelte_i18n_library.md +448 -0
- package/blog/en/how_to_pick_vue_i18n_library.md +442 -0
- package/blog/en/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/en/i18next_vs_intlayer.md +445 -0
- package/blog/en/is_i18next_outdated.md +6 -2
- package/blog/en/is_next-intl_outdated.md +6 -2
- package/blog/en/is_vue-i18n_outdated.md +8 -2
- package/blog/en/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/en/lingui_vs_intlayer.md +381 -0
- package/blog/en/list_i18n_technologies/frameworks/react-router.md +2 -3
- package/blog/en/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/en/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/en/next-intl_vs_intlayer.md +415 -0
- package/blog/en/per-component_vs_centralized_i18n.md +9 -4
- package/blog/en/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/en/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/en/vue-i18n_vs_intlayer.md +1 -1
- package/blog/en/vue-i18n_vs_intlayer_benchmark.md +361 -0
- package/blog/en-GB/history_of_i18n.md +54 -54
- package/blog/en-GB/how_to_pick_react_i18n_library.md +542 -0
- package/blog/en-GB/how_to_pick_solid_i18n_library.md +438 -0
- package/blog/en-GB/how_to_pick_svelte_i18n_library.md +448 -0
- package/blog/en-GB/how_to_pick_vue_i18n_library.md +448 -0
- package/blog/en-GB/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/en-GB/i18next_vs_intlayer.md +445 -0
- package/blog/en-GB/is_i18next_outdated.md +6 -2
- package/blog/en-GB/is_next-intl_outdated.md +6 -2
- package/blog/en-GB/is_vue-i18n_outdated.md +8 -2
- package/blog/en-GB/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/en-GB/lingui_vs_intlayer.md +381 -0
- package/blog/en-GB/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/en-GB/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/en-GB/next-intl_vs_intlayer.md +415 -0
- package/blog/en-GB/per-component_vs_centralized_i18n.md +9 -4
- package/blog/en-GB/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/en-GB/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/en-GB/vue-i18n_vs_intlayer.md +1 -1
- package/blog/en-GB/vue-i18n_vs_intlayer_benchmark.md +245 -0
- package/blog/es/history_of_i18n.md +54 -54
- package/blog/es/how_to_pick_react_i18n_library.md +542 -0
- package/blog/es/how_to_pick_solid_i18n_library.md +446 -0
- package/blog/es/how_to_pick_svelte_i18n_library.md +448 -0
- package/blog/es/how_to_pick_vue_i18n_library.md +442 -0
- package/blog/es/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/es/i18next_vs_intlayer.md +445 -0
- package/blog/es/is_i18next_outdated.md +6 -2
- package/blog/es/is_next-intl_outdated.md +6 -2
- package/blog/es/is_vue-i18n_outdated.md +8 -2
- package/blog/es/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/es/lingui_vs_intlayer.md +381 -0
- package/blog/es/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/es/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/es/next-intl_vs_intlayer.md +417 -0
- package/blog/es/per-component_vs_centralized_i18n.md +9 -4
- package/blog/es/react-i18next_vs_react-intl_vs_intlayer.md +5 -1
- package/blog/es/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/es/vue-i18n_vs_intlayer_benchmark.md +363 -0
- package/blog/fr/history_of_i18n.md +54 -54
- package/blog/fr/how_to_pick_react_i18n_library.md +542 -0
- package/blog/fr/how_to_pick_solid_i18n_library.md +438 -0
- package/blog/fr/how_to_pick_svelte_i18n_library.md +448 -0
- package/blog/fr/how_to_pick_vue_i18n_library.md +442 -0
- package/blog/fr/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/fr/i18next_vs_intlayer.md +445 -0
- package/blog/fr/is_i18next_outdated.md +6 -2
- package/blog/fr/is_next-intl_outdated.md +6 -2
- package/blog/fr/is_vue-i18n_outdated.md +8 -2
- package/blog/fr/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/fr/lingui_vs_intlayer.md +381 -0
- package/blog/fr/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/fr/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/fr/next-intl_vs_intlayer.md +417 -0
- package/blog/fr/per-component_vs_centralized_i18n.md +9 -4
- package/blog/fr/react-i18next_vs_react-intl_vs_intlayer.md +5 -1
- package/blog/fr/vue-i18n_vs_intlayer-vue-i18n.md +287 -0
- package/blog/fr/vue-i18n_vs_intlayer_benchmark.md +39 -0
- package/blog/hi/history_of_i18n.md +54 -54
- package/blog/hi/how_to_pick_react_i18n_library.md +548 -0
- package/blog/hi/how_to_pick_solid_i18n_library.md +451 -0
- package/blog/hi/how_to_pick_svelte_i18n_library.md +448 -0
- package/blog/hi/how_to_pick_vue_i18n_library.md +442 -0
- package/blog/hi/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/hi/i18next_vs_intlayer.md +445 -0
- package/blog/hi/is_i18next_outdated.md +6 -2
- package/blog/hi/is_next-intl_outdated.md +6 -2
- package/blog/hi/is_vue-i18n_outdated.md +8 -2
- package/blog/hi/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/hi/lingui_vs_intlayer.md +381 -0
- package/blog/hi/next-i18next_vs_next-intl_vs_intlayer.md +8 -4
- package/blog/hi/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/hi/next-intl_vs_intlayer.md +397 -0
- package/blog/hi/per-component_vs_centralized_i18n.md +9 -4
- package/blog/hi/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/hi/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/hi/vue-i18n_vs_intlayer_benchmark.md +0 -0
- package/blog/id/history_of_i18n.md +54 -54
- package/blog/id/how_to_pick_react_i18n_library.md +548 -0
- package/blog/id/how_to_pick_solid_i18n_library.md +451 -0
- package/blog/id/how_to_pick_svelte_i18n_library.md +454 -0
- package/blog/id/how_to_pick_vue_i18n_library.md +442 -0
- package/blog/id/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/id/i18next_vs_intlayer.md +445 -0
- package/blog/id/is_i18next_outdated.md +6 -2
- package/blog/id/is_next-intl_outdated.md +6 -2
- package/blog/id/is_vue-i18n_outdated.md +8 -2
- package/blog/id/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/id/lingui_vs_intlayer.md +381 -0
- package/blog/id/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/id/next-intl_vs_intlayer-next-intl.md +310 -0
- package/blog/id/next-intl_vs_intlayer.md +397 -0
- package/blog/id/per-component_vs_centralized_i18n.md +9 -4
- package/blog/id/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/id/vue-i18n_vs_intlayer-vue-i18n.md +36 -0
- package/blog/id/vue-i18n_vs_intlayer.md +1 -1
- package/blog/id/vue-i18n_vs_intlayer_benchmark.md +41 -0
- package/blog/it/history_of_i18n.md +54 -54
- package/blog/it/how_to_pick_react_i18n_library.md +549 -0
- package/blog/it/how_to_pick_solid_i18n_library.md +451 -0
- package/blog/it/how_to_pick_svelte_i18n_library.md +455 -0
- package/blog/it/how_to_pick_vue_i18n_library.md +449 -0
- package/blog/it/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/it/i18next_vs_intlayer.md +445 -0
- package/blog/it/is_i18next_outdated.md +6 -2
- package/blog/it/is_next-intl_outdated.md +6 -2
- package/blog/it/is_vue-i18n_outdated.md +8 -2
- package/blog/it/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/it/lingui_vs_intlayer.md +381 -0
- package/blog/it/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/it/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/it/next-intl_vs_intlayer.md +418 -0
- package/blog/it/per-component_vs_centralized_i18n.md +9 -4
- package/blog/it/react-i18next_vs_react-intl_vs_intlayer.md +5 -1
- package/blog/it/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/it/vue-i18n_vs_intlayer_benchmark.md +34 -0
- package/blog/ja/history_of_i18n.md +54 -54
- package/blog/ja/how_to_pick_react_i18n_library.md +542 -0
- package/blog/ja/how_to_pick_solid_i18n_library.md +451 -0
- package/blog/ja/how_to_pick_svelte_i18n_library.md +457 -0
- package/blog/ja/how_to_pick_vue_i18n_library.md +442 -0
- package/blog/ja/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/ja/i18next_vs_intlayer.md +447 -0
- package/blog/ja/is_i18next_outdated.md +6 -2
- package/blog/ja/is_next-intl_outdated.md +6 -2
- package/blog/ja/is_vue-i18n_outdated.md +8 -2
- package/blog/ja/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/ja/lingui_vs_intlayer.md +381 -0
- package/blog/ja/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/ja/next-intl_vs_intlayer-next-intl.md +310 -0
- package/blog/ja/next-intl_vs_intlayer.md +422 -0
- package/blog/ja/per-component_vs_centralized_i18n.md +9 -4
- package/blog/ja/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/ja/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/ja/vue-i18n_vs_intlayer.md +1 -1
- package/blog/ja/vue-i18n_vs_intlayer_benchmark.md +0 -0
- package/blog/ko/history_of_i18n.md +54 -54
- package/blog/ko/how_to_pick_react_i18n_library.md +548 -0
- package/blog/ko/how_to_pick_solid_i18n_library.md +451 -0
- package/blog/ko/how_to_pick_svelte_i18n_library.md +454 -0
- package/blog/ko/how_to_pick_vue_i18n_library.md +448 -0
- package/blog/ko/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/ko/i18next_vs_intlayer.md +447 -0
- package/blog/ko/is_i18next_outdated.md +6 -2
- package/blog/ko/is_next-intl_outdated.md +6 -2
- package/blog/ko/is_vue-i18n_outdated.md +8 -2
- package/blog/ko/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/ko/lingui_vs_intlayer.md +381 -0
- package/blog/ko/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/ko/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/ko/next-intl_vs_intlayer.md +397 -0
- package/blog/ko/per-component_vs_centralized_i18n.md +9 -4
- package/blog/ko/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/ko/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/ko/vue-i18n_vs_intlayer.md +1 -1
- package/blog/ko/vue-i18n_vs_intlayer_benchmark.md +366 -0
- package/blog/pl/history_of_i18n.md +54 -54
- package/blog/pl/how_to_pick_react_i18n_library.md +549 -0
- package/blog/pl/how_to_pick_solid_i18n_library.md +438 -0
- package/blog/pl/how_to_pick_svelte_i18n_library.md +460 -0
- package/blog/pl/how_to_pick_vue_i18n_library.md +442 -0
- package/blog/pl/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/pl/i18next_vs_intlayer.md +445 -0
- package/blog/pl/is_i18next_outdated.md +6 -2
- package/blog/pl/is_next-intl_outdated.md +6 -2
- package/blog/pl/is_vue-i18n_outdated.md +8 -2
- package/blog/pl/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/pl/lingui_vs_intlayer.md +381 -0
- package/blog/pl/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/pl/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/pl/next-intl_vs_intlayer.md +397 -0
- package/blog/pl/per-component_vs_centralized_i18n.md +9 -4
- package/blog/pl/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/pl/vue-i18n_vs_intlayer-vue-i18n.md +289 -0
- package/blog/pl/vue-i18n_vs_intlayer.md +1 -1
- package/blog/pl/vue-i18n_vs_intlayer_benchmark.md +0 -0
- package/blog/pt/history_of_i18n.md +54 -54
- package/blog/pt/how_to_pick_react_i18n_library.md +549 -0
- package/blog/pt/how_to_pick_solid_i18n_library.md +451 -0
- package/blog/pt/how_to_pick_svelte_i18n_library.md +454 -0
- package/blog/pt/how_to_pick_vue_i18n_library.md +448 -0
- package/blog/pt/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/pt/i18next_vs_intlayer.md +445 -0
- package/blog/pt/is_i18next_outdated.md +6 -2
- package/blog/pt/is_next-intl_outdated.md +6 -2
- package/blog/pt/is_vue-i18n_outdated.md +8 -2
- package/blog/pt/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/pt/lingui_vs_intlayer.md +381 -0
- package/blog/pt/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/pt/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/pt/next-intl_vs_intlayer.md +411 -0
- package/blog/pt/per-component_vs_centralized_i18n.md +9 -4
- package/blog/pt/react-i18next_vs_react-intl_vs_intlayer.md +5 -1
- package/blog/pt/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/pt/vue-i18n_vs_intlayer_benchmark.md +0 -0
- package/blog/ru/history_of_i18n.md +54 -54
- package/blog/ru/how_to_pick_react_i18n_library.md +553 -0
- package/blog/ru/how_to_pick_solid_i18n_library.md +451 -0
- package/blog/ru/how_to_pick_svelte_i18n_library.md +459 -0
- package/blog/ru/how_to_pick_vue_i18n_library.md +453 -0
- package/blog/ru/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/ru/i18next_vs_intlayer.md +445 -0
- package/blog/ru/is_i18next_outdated.md +6 -2
- package/blog/ru/is_next-intl_outdated.md +6 -2
- package/blog/ru/is_vue-i18n_outdated.md +8 -2
- package/blog/ru/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/ru/lingui_vs_intlayer.md +381 -0
- package/blog/ru/next-i18next_vs_next-intl_vs_intlayer.md +9 -5
- package/blog/ru/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/ru/next-intl_vs_intlayer.md +417 -0
- package/blog/ru/per-component_vs_centralized_i18n.md +9 -4
- package/blog/ru/react-i18next_vs_react-intl_vs_intlayer.md +5 -1
- package/blog/ru/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/ru/vue-i18n_vs_intlayer_benchmark.md +54 -0
- package/blog/tr/history_of_i18n.md +54 -54
- package/blog/tr/how_to_pick_react_i18n_library.md +548 -0
- package/blog/tr/how_to_pick_solid_i18n_library.md +451 -0
- package/blog/tr/how_to_pick_svelte_i18n_library.md +454 -0
- package/blog/tr/how_to_pick_vue_i18n_library.md +448 -0
- package/blog/tr/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/tr/i18next_vs_intlayer.md +445 -0
- package/blog/tr/is_i18next_outdated.md +6 -2
- package/blog/tr/is_next-intl_outdated.md +6 -2
- package/blog/tr/is_vue-i18n_outdated.md +8 -2
- package/blog/tr/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/tr/lingui_vs_intlayer.md +381 -0
- package/blog/tr/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/tr/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/tr/next-intl_vs_intlayer.md +397 -0
- package/blog/tr/per-component_vs_centralized_i18n.md +9 -4
- package/blog/tr/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/tr/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/tr/vue-i18n_vs_intlayer.md +1 -1
- package/blog/tr/vue-i18n_vs_intlayer_benchmark.md +0 -0
- package/blog/uk/history_of_i18n.md +54 -54
- package/blog/uk/how_to_pick_react_i18n_library.md +542 -0
- package/blog/uk/how_to_pick_solid_i18n_library.md +451 -0
- package/blog/uk/how_to_pick_svelte_i18n_library.md +448 -0
- package/blog/uk/how_to_pick_vue_i18n_library.md +443 -0
- package/blog/uk/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/uk/i18next_vs_intlayer.md +445 -0
- package/blog/uk/is_i18next_outdated.md +6 -2
- package/blog/uk/is_next-intl_outdated.md +6 -2
- package/blog/uk/is_vue-i18n_outdated.md +8 -2
- package/blog/uk/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/uk/lingui_vs_intlayer.md +381 -0
- package/blog/uk/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/uk/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/uk/next-intl_vs_intlayer.md +397 -0
- package/blog/uk/per-component_vs_centralized_i18n.md +9 -4
- package/blog/uk/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/uk/vue-i18n_vs_intlayer-vue-i18n.md +270 -0
- package/blog/uk/vue-i18n_vs_intlayer.md +1 -1
- package/blog/uk/vue-i18n_vs_intlayer_benchmark.md +0 -0
- package/blog/vi/history_of_i18n.md +54 -54
- package/blog/vi/how_to_pick_react_i18n_library.md +548 -0
- package/blog/vi/how_to_pick_solid_i18n_library.md +438 -0
- package/blog/vi/how_to_pick_svelte_i18n_library.md +448 -0
- package/blog/vi/how_to_pick_vue_i18n_library.md +442 -0
- package/blog/vi/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/vi/i18next_vs_intlayer.md +445 -0
- package/blog/vi/is_i18next_outdated.md +6 -2
- package/blog/vi/is_next-intl_outdated.md +6 -2
- package/blog/vi/is_vue-i18n_outdated.md +8 -2
- package/blog/vi/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/vi/lingui_vs_intlayer.md +381 -0
- package/blog/vi/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/vi/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/vi/next-intl_vs_intlayer.md +397 -0
- package/blog/vi/per-component_vs_centralized_i18n.md +9 -4
- package/blog/vi/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/vi/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/vi/vue-i18n_vs_intlayer.md +1 -1
- package/blog/vi/vue-i18n_vs_intlayer_benchmark.md +0 -0
- package/blog/zh/history_of_i18n.md +54 -54
- package/blog/zh/how_to_pick_react_i18n_library.md +548 -0
- package/blog/zh/how_to_pick_solid_i18n_library.md +451 -0
- package/blog/zh/how_to_pick_svelte_i18n_library.md +454 -0
- package/blog/zh/how_to_pick_vue_i18n_library.md +448 -0
- package/blog/zh/i18next_vs_intlayer-i18next.md +327 -0
- package/blog/zh/i18next_vs_intlayer.md +445 -0
- package/blog/zh/is_i18next_outdated.md +6 -2
- package/blog/zh/is_next-intl_outdated.md +6 -2
- package/blog/zh/is_vue-i18n_outdated.md +8 -2
- package/blog/zh/lingui_vs_intlayer-lingui.md +304 -0
- package/blog/zh/lingui_vs_intlayer.md +381 -0
- package/blog/zh/next-i18next_vs_next-intl_vs_intlayer.md +10 -6
- package/blog/zh/next-intl_vs_intlayer-next-intl.md +309 -0
- package/blog/zh/next-intl_vs_intlayer.md +422 -0
- package/blog/zh/per-component_vs_centralized_i18n.md +9 -4
- package/blog/zh/react-i18next_vs_react-intl_vs_intlayer.md +6 -2
- package/blog/zh/vue-i18n_vs_intlayer-vue-i18n.md +288 -0
- package/blog/zh/vue-i18n_vs_intlayer.md +1 -1
- package/blog/zh/vue-i18n_vs_intlayer_benchmark.md +30 -0
- package/dist/cjs/generated/blog.entry.cjs +240 -0
- package/dist/cjs/generated/blog.entry.cjs.map +1 -1
- package/dist/cjs/generated/frequentQuestions.entry.cjs +20 -0
- package/dist/cjs/generated/frequentQuestions.entry.cjs.map +1 -1
- package/dist/cjs/index.cjs +1 -1
- package/dist/esm/generated/blog.entry.mjs +240 -0
- package/dist/esm/generated/blog.entry.mjs.map +1 -1
- package/dist/esm/generated/frequentQuestions.entry.mjs +20 -0
- package/dist/esm/generated/frequentQuestions.entry.mjs.map +1 -1
- package/dist/esm/index.mjs +1 -1
- package/dist/types/generated/blog.entry.d.ts +12 -0
- package/dist/types/generated/blog.entry.d.ts.map +1 -1
- package/dist/types/generated/frequentQuestions.entry.d.ts +1 -0
- package/dist/types/generated/frequentQuestions.entry.d.ts.map +1 -1
- package/docs/ar/benchmark/nextjs.md +1 -1
- package/docs/ar/benchmark/solid.md +1 -1
- package/docs/ar/benchmark/svelte.md +1 -1
- package/docs/ar/benchmark/tanstack.md +1 -1
- package/docs/ar/benchmark/vue.md +1 -1
- package/docs/ar/bundle_optimization.md +5 -1
- package/docs/ar/how_works_intlayer.md +2 -2
- package/docs/ar/interest_of_intlayer.md +7 -7
- package/docs/ar/intlayer_CMS.md +1 -1
- package/docs/ar/intlayer_with_adonisjs.md +1 -1
- package/docs/ar/intlayer_with_analog.md +1 -1
- package/docs/ar/intlayer_with_angular_19.md +1 -1
- package/docs/ar/intlayer_with_angular_21.md +1 -1
- package/docs/ar/intlayer_with_astro.md +1 -1
- package/docs/ar/intlayer_with_astro_lit.md +1 -1
- package/docs/ar/intlayer_with_astro_preact.md +1 -1
- package/docs/ar/intlayer_with_astro_react.md +1 -1
- package/docs/ar/intlayer_with_astro_solid.md +1 -1
- package/docs/ar/intlayer_with_astro_svelte.md +1 -1
- package/docs/ar/intlayer_with_astro_vanilla.md +1 -1
- package/docs/ar/intlayer_with_astro_vue.md +1 -1
- package/docs/ar/intlayer_with_create_react_app.md +1 -1
- package/docs/ar/intlayer_with_express.md +1 -1
- package/docs/ar/intlayer_with_hono.md +1 -1
- package/docs/ar/intlayer_with_nestjs.md +1 -1
- package/docs/ar/intlayer_with_nextjs_14.md +1 -1
- package/docs/ar/intlayer_with_nextjs_15.md +1 -1
- package/docs/ar/intlayer_with_nextjs_16.md +1 -1
- package/docs/ar/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/ar/intlayer_with_react_router_v7.md +1 -1
- package/docs/ar/intlayer_with_vite+preact.md +1 -1
- package/docs/ar/intlayer_with_vite+react.md +1 -1
- package/docs/ar/intlayer_with_vite+vue.md +1 -1
- package/docs/ar/introduction.md +0 -1
- package/docs/ar/readme.md +8 -8
- package/docs/bn/bundle_optimization.md +5 -1
- package/docs/bn/interest_of_intlayer.md +22 -22
- package/docs/bn/intlayer_CMS.md +1 -1
- package/docs/bn/intlayer_with_angular_21.md +1 -1
- package/docs/bn/intlayer_with_hono.md +1 -1
- package/docs/bn/introduction.md +0 -1
- package/docs/cs/bundle_optimization.md +5 -1
- package/docs/cs/interest_of_intlayer.md +7 -7
- package/docs/cs/intlayer_with_angular_21.md +1 -1
- package/docs/cs/intlayer_with_hono.md +1 -1
- package/docs/cs/introduction.md +0 -1
- package/docs/de/benchmark/nextjs.md +1 -1
- package/docs/de/benchmark/solid.md +1 -1
- package/docs/de/benchmark/svelte.md +1 -1
- package/docs/de/benchmark/tanstack.md +1 -1
- package/docs/de/benchmark/vue.md +1 -1
- package/docs/de/bundle_optimization.md +5 -1
- package/docs/de/how_works_intlayer.md +2 -2
- package/docs/de/interest_of_intlayer.md +7 -7
- package/docs/de/intlayer_CMS.md +1 -1
- package/docs/de/intlayer_with_adonisjs.md +1 -1
- package/docs/de/intlayer_with_analog.md +1 -1
- package/docs/de/intlayer_with_angular_19.md +1 -1
- package/docs/de/intlayer_with_angular_21.md +1 -1
- package/docs/de/intlayer_with_astro.md +1 -1
- package/docs/de/intlayer_with_astro_lit.md +1 -1
- package/docs/de/intlayer_with_astro_preact.md +1 -1
- package/docs/de/intlayer_with_astro_react.md +1 -1
- package/docs/de/intlayer_with_astro_solid.md +1 -1
- package/docs/de/intlayer_with_astro_svelte.md +1 -1
- package/docs/de/intlayer_with_astro_vanilla.md +1 -1
- package/docs/de/intlayer_with_astro_vue.md +1 -1
- package/docs/de/intlayer_with_create_react_app.md +1 -1
- package/docs/de/intlayer_with_express.md +1 -1
- package/docs/de/intlayer_with_hono.md +1 -1
- package/docs/de/intlayer_with_nestjs.md +1 -1
- package/docs/de/intlayer_with_nextjs_14.md +1 -1
- package/docs/de/intlayer_with_nextjs_15.md +1 -1
- package/docs/de/intlayer_with_nextjs_16.md +1 -1
- package/docs/de/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/de/intlayer_with_vite+preact.md +1 -1
- package/docs/de/intlayer_with_vite+react.md +1 -1
- package/docs/de/intlayer_with_vite+vue.md +1 -1
- package/docs/de/introduction.md +0 -1
- package/docs/de/readme.md +8 -8
- package/docs/en/benchmark/nextjs.md +1 -1
- package/docs/en/benchmark/solid.md +1 -1
- package/docs/en/benchmark/svelte.md +1 -1
- package/docs/en/benchmark/tanstack.md +1 -1
- package/docs/en/benchmark/vue.md +1 -1
- package/docs/en/bundle_optimization.md +5 -1
- package/docs/en/how_works_intlayer.md +2 -2
- package/docs/en/interest_of_intlayer.md +7 -7
- package/docs/en/intlayer_CMS.md +1 -1
- package/docs/en/intlayer_with_adonisjs.md +1 -1
- package/docs/en/intlayer_with_analog.md +1 -1
- package/docs/en/intlayer_with_angular_19.md +1 -1
- package/docs/en/intlayer_with_angular_21.md +1 -1
- package/docs/en/intlayer_with_astro.md +1 -1
- package/docs/en/intlayer_with_astro_lit.md +1 -1
- package/docs/en/intlayer_with_astro_preact.md +1 -1
- package/docs/en/intlayer_with_astro_react.md +1 -1
- package/docs/en/intlayer_with_astro_solid.md +1 -1
- package/docs/en/intlayer_with_astro_svelte.md +1 -1
- package/docs/en/intlayer_with_astro_vanilla.md +1 -1
- package/docs/en/intlayer_with_astro_vue.md +1 -1
- package/docs/en/intlayer_with_create_react_app.md +1 -1
- package/docs/en/intlayer_with_express.md +1 -1
- package/docs/en/intlayer_with_hono.md +1 -1
- package/docs/en/intlayer_with_nestjs.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_vite+preact.md +1 -1
- package/docs/en/intlayer_with_vite+react.md +1 -1
- package/docs/en/intlayer_with_vite+vue.md +1 -1
- package/docs/en/introduction.md +0 -1
- package/docs/en/readme.md +8 -8
- package/docs/en-GB/benchmark/nextjs.md +1 -1
- package/docs/en-GB/benchmark/solid.md +1 -1
- package/docs/en-GB/benchmark/svelte.md +1 -1
- package/docs/en-GB/benchmark/tanstack.md +1 -1
- package/docs/en-GB/benchmark/vue.md +1 -1
- package/docs/en-GB/bundle_optimization.md +5 -1
- package/docs/en-GB/how_works_intlayer.md +2 -2
- package/docs/en-GB/interest_of_intlayer.md +7 -7
- package/docs/en-GB/intlayer_CMS.md +1 -1
- package/docs/en-GB/intlayer_with_adonisjs.md +1 -1
- package/docs/en-GB/intlayer_with_analog.md +1 -1
- package/docs/en-GB/intlayer_with_angular_19.md +1 -1
- package/docs/en-GB/intlayer_with_angular_21.md +1 -1
- package/docs/en-GB/intlayer_with_astro.md +1 -1
- package/docs/en-GB/intlayer_with_astro_lit.md +1 -1
- package/docs/en-GB/intlayer_with_astro_preact.md +1 -1
- package/docs/en-GB/intlayer_with_astro_react.md +1 -1
- package/docs/en-GB/intlayer_with_astro_solid.md +1 -1
- package/docs/en-GB/intlayer_with_astro_svelte.md +1 -1
- package/docs/en-GB/intlayer_with_astro_vanilla.md +1 -1
- package/docs/en-GB/intlayer_with_astro_vue.md +1 -1
- package/docs/en-GB/intlayer_with_create_react_app.md +1 -1
- package/docs/en-GB/intlayer_with_express.md +1 -1
- package/docs/en-GB/intlayer_with_hono.md +1 -1
- package/docs/en-GB/intlayer_with_nestjs.md +1 -1
- package/docs/en-GB/intlayer_with_nextjs_14.md +1 -1
- package/docs/en-GB/intlayer_with_nextjs_15.md +1 -1
- package/docs/en-GB/intlayer_with_nextjs_16.md +1 -1
- package/docs/en-GB/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/en-GB/intlayer_with_vite+preact.md +1 -1
- package/docs/en-GB/intlayer_with_vite+react.md +1 -1
- package/docs/en-GB/intlayer_with_vite+vue.md +1 -1
- package/docs/en-GB/introduction.md +0 -1
- package/docs/en-GB/readme.md +8 -8
- package/docs/es/benchmark/nextjs.md +1 -1
- package/docs/es/benchmark/solid.md +1 -1
- package/docs/es/benchmark/svelte.md +1 -1
- package/docs/es/benchmark/tanstack.md +1 -1
- package/docs/es/benchmark/vue.md +1 -1
- package/docs/es/bundle_optimization.md +5 -1
- package/docs/es/how_works_intlayer.md +2 -2
- package/docs/es/interest_of_intlayer.md +7 -7
- package/docs/es/intlayer_CMS.md +1 -1
- package/docs/es/intlayer_with_adonisjs.md +1 -1
- package/docs/es/intlayer_with_analog.md +1 -1
- package/docs/es/intlayer_with_angular_19.md +1 -1
- package/docs/es/intlayer_with_angular_21.md +1 -1
- package/docs/es/intlayer_with_astro.md +1 -1
- package/docs/es/intlayer_with_astro_lit.md +1 -1
- package/docs/es/intlayer_with_astro_preact.md +1 -1
- package/docs/es/intlayer_with_astro_react.md +1 -1
- package/docs/es/intlayer_with_astro_solid.md +1 -1
- package/docs/es/intlayer_with_astro_svelte.md +1 -1
- package/docs/es/intlayer_with_astro_vanilla.md +1 -1
- package/docs/es/intlayer_with_astro_vue.md +1 -1
- package/docs/es/intlayer_with_create_react_app.md +1 -1
- package/docs/es/intlayer_with_express.md +1 -1
- package/docs/es/intlayer_with_hono.md +1 -1
- package/docs/es/intlayer_with_nestjs.md +1 -1
- package/docs/es/intlayer_with_nextjs_14.md +1 -1
- package/docs/es/intlayer_with_nextjs_15.md +1 -1
- package/docs/es/intlayer_with_nextjs_16.md +1 -1
- package/docs/es/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/es/intlayer_with_vite+preact.md +1 -1
- package/docs/es/intlayer_with_vite+react.md +1 -1
- package/docs/es/intlayer_with_vite+vue.md +1 -1
- package/docs/es/introduction.md +0 -1
- package/docs/es/readme.md +8 -8
- package/docs/fr/benchmark/nextjs.md +1 -1
- package/docs/fr/benchmark/solid.md +1 -1
- package/docs/fr/benchmark/svelte.md +1 -1
- package/docs/fr/benchmark/tanstack.md +1 -1
- package/docs/fr/benchmark/vue.md +1 -1
- package/docs/fr/bundle_optimization.md +5 -1
- package/docs/fr/how_works_intlayer.md +2 -2
- package/docs/fr/interest_of_intlayer.md +7 -7
- package/docs/fr/intlayer_CMS.md +1 -1
- package/docs/fr/intlayer_with_adonisjs.md +1 -1
- package/docs/fr/intlayer_with_analog.md +1 -1
- package/docs/fr/intlayer_with_angular_19.md +1 -1
- package/docs/fr/intlayer_with_angular_21.md +1 -1
- package/docs/fr/intlayer_with_astro.md +1 -1
- package/docs/fr/intlayer_with_astro_lit.md +1 -1
- package/docs/fr/intlayer_with_astro_preact.md +1 -1
- package/docs/fr/intlayer_with_astro_react.md +1 -1
- package/docs/fr/intlayer_with_astro_solid.md +1 -1
- package/docs/fr/intlayer_with_astro_svelte.md +1 -1
- package/docs/fr/intlayer_with_astro_vanilla.md +1 -1
- package/docs/fr/intlayer_with_astro_vue.md +1 -1
- package/docs/fr/intlayer_with_create_react_app.md +1 -1
- package/docs/fr/intlayer_with_express.md +1 -1
- package/docs/fr/intlayer_with_hono.md +1 -1
- package/docs/fr/intlayer_with_nestjs.md +1 -1
- package/docs/fr/intlayer_with_nextjs_14.md +1 -1
- package/docs/fr/intlayer_with_nextjs_15.md +1 -1
- package/docs/fr/intlayer_with_nextjs_16.md +1 -1
- package/docs/fr/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/fr/intlayer_with_react_router_v7.md +2 -2
- package/docs/fr/intlayer_with_vite+preact.md +1 -1
- package/docs/fr/intlayer_with_vite+react.md +1 -1
- package/docs/fr/intlayer_with_vite+vue.md +1 -1
- package/docs/fr/introduction.md +0 -1
- package/docs/fr/readme.md +8 -8
- package/docs/hi/benchmark/nextjs.md +1 -1
- package/docs/hi/benchmark/solid.md +1 -1
- package/docs/hi/benchmark/svelte.md +1 -1
- package/docs/hi/benchmark/tanstack.md +1 -1
- package/docs/hi/benchmark/vue.md +1 -1
- package/docs/hi/bundle_optimization.md +5 -1
- package/docs/hi/how_works_intlayer.md +2 -2
- package/docs/hi/interest_of_intlayer.md +7 -7
- package/docs/hi/intlayer_CMS.md +1 -1
- package/docs/hi/intlayer_with_adonisjs.md +1 -1
- package/docs/hi/intlayer_with_analog.md +1 -1
- package/docs/hi/intlayer_with_angular_19.md +1 -1
- package/docs/hi/intlayer_with_angular_21.md +1 -1
- package/docs/hi/intlayer_with_astro.md +1 -1
- package/docs/hi/intlayer_with_astro_lit.md +1 -1
- package/docs/hi/intlayer_with_astro_preact.md +1 -1
- package/docs/hi/intlayer_with_astro_react.md +1 -1
- package/docs/hi/intlayer_with_astro_solid.md +1 -1
- package/docs/hi/intlayer_with_astro_svelte.md +1 -1
- package/docs/hi/intlayer_with_astro_vanilla.md +1 -1
- package/docs/hi/intlayer_with_astro_vue.md +1 -1
- package/docs/hi/intlayer_with_create_react_app.md +1 -1
- package/docs/hi/intlayer_with_express.md +1 -1
- package/docs/hi/intlayer_with_hono.md +1 -1
- package/docs/hi/intlayer_with_nestjs.md +1 -1
- package/docs/hi/intlayer_with_nextjs_14.md +1 -1
- package/docs/hi/intlayer_with_nextjs_15.md +1 -1
- package/docs/hi/intlayer_with_nextjs_16.md +1 -1
- package/docs/hi/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/hi/intlayer_with_react_router_v7.md +1 -1
- package/docs/hi/intlayer_with_vite+preact.md +1 -1
- package/docs/hi/intlayer_with_vite+react.md +1 -1
- package/docs/hi/intlayer_with_vite+vue.md +1 -1
- package/docs/hi/introduction.md +0 -1
- package/docs/hi/readme.md +8 -8
- package/docs/id/benchmark/nextjs.md +1 -1
- package/docs/id/benchmark/solid.md +1 -1
- package/docs/id/benchmark/svelte.md +1 -1
- package/docs/id/benchmark/tanstack.md +1 -1
- package/docs/id/benchmark/vue.md +1 -1
- package/docs/id/bundle_optimization.md +5 -1
- package/docs/id/how_works_intlayer.md +2 -2
- package/docs/id/interest_of_intlayer.md +7 -7
- package/docs/id/intlayer_CMS.md +1 -1
- package/docs/id/intlayer_with_adonisjs.md +1 -1
- package/docs/id/intlayer_with_analog.md +1 -1
- package/docs/id/intlayer_with_angular_19.md +1 -1
- package/docs/id/intlayer_with_angular_21.md +1 -1
- package/docs/id/intlayer_with_astro.md +1 -1
- package/docs/id/intlayer_with_astro_lit.md +1 -1
- package/docs/id/intlayer_with_astro_preact.md +1 -1
- package/docs/id/intlayer_with_astro_react.md +1 -1
- package/docs/id/intlayer_with_astro_solid.md +1 -1
- package/docs/id/intlayer_with_astro_svelte.md +1 -1
- package/docs/id/intlayer_with_astro_vanilla.md +1 -1
- package/docs/id/intlayer_with_astro_vue.md +1 -1
- package/docs/id/intlayer_with_create_react_app.md +1 -1
- package/docs/id/intlayer_with_express.md +1 -1
- package/docs/id/intlayer_with_hono.md +1 -1
- package/docs/id/intlayer_with_nestjs.md +1 -1
- package/docs/id/intlayer_with_nextjs_14.md +1 -1
- package/docs/id/intlayer_with_nextjs_15.md +1 -1
- package/docs/id/intlayer_with_nextjs_16.md +1 -1
- package/docs/id/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/id/intlayer_with_react_router_v7.md +1 -1
- package/docs/id/intlayer_with_vite+preact.md +1 -1
- package/docs/id/intlayer_with_vite+react.md +1 -1
- package/docs/id/intlayer_with_vite+vue.md +1 -1
- package/docs/id/introduction.md +0 -1
- package/docs/id/readme.md +8 -8
- package/docs/it/benchmark/nextjs.md +1 -1
- package/docs/it/benchmark/solid.md +1 -1
- package/docs/it/benchmark/svelte.md +1 -1
- package/docs/it/benchmark/tanstack.md +1 -1
- package/docs/it/benchmark/vue.md +1 -1
- package/docs/it/bundle_optimization.md +5 -1
- package/docs/it/how_works_intlayer.md +2 -2
- package/docs/it/interest_of_intlayer.md +7 -7
- package/docs/it/intlayer_CMS.md +1 -1
- package/docs/it/intlayer_with_adonisjs.md +1 -1
- package/docs/it/intlayer_with_analog.md +1 -1
- package/docs/it/intlayer_with_angular_19.md +1 -1
- package/docs/it/intlayer_with_angular_21.md +1 -1
- package/docs/it/intlayer_with_astro.md +1 -1
- package/docs/it/intlayer_with_astro_lit.md +1 -1
- package/docs/it/intlayer_with_astro_preact.md +1 -1
- package/docs/it/intlayer_with_astro_react.md +1 -1
- package/docs/it/intlayer_with_astro_solid.md +1 -1
- package/docs/it/intlayer_with_astro_svelte.md +1 -1
- package/docs/it/intlayer_with_astro_vanilla.md +1 -1
- package/docs/it/intlayer_with_astro_vue.md +1 -1
- package/docs/it/intlayer_with_create_react_app.md +1 -1
- package/docs/it/intlayer_with_express.md +1 -1
- package/docs/it/intlayer_with_hono.md +1 -1
- package/docs/it/intlayer_with_nestjs.md +1 -1
- package/docs/it/intlayer_with_nextjs_14.md +1 -1
- package/docs/it/intlayer_with_nextjs_15.md +1 -1
- package/docs/it/intlayer_with_nextjs_16.md +1 -1
- package/docs/it/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/it/intlayer_with_react_router_v7.md +2 -2
- package/docs/it/intlayer_with_vite+preact.md +1 -1
- package/docs/it/intlayer_with_vite+react.md +1 -1
- package/docs/it/intlayer_with_vite+vue.md +1 -1
- package/docs/it/introduction.md +0 -1
- package/docs/it/readme.md +8 -8
- package/docs/ja/benchmark/nextjs.md +1 -1
- package/docs/ja/benchmark/solid.md +1 -1
- package/docs/ja/benchmark/svelte.md +1 -1
- package/docs/ja/benchmark/tanstack.md +1 -1
- package/docs/ja/benchmark/vue.md +1 -1
- package/docs/ja/bundle_optimization.md +5 -1
- package/docs/ja/how_works_intlayer.md +2 -2
- package/docs/ja/interest_of_intlayer.md +7 -7
- package/docs/ja/intlayer_CMS.md +1 -1
- package/docs/ja/intlayer_with_adonisjs.md +1 -1
- package/docs/ja/intlayer_with_analog.md +1 -1
- package/docs/ja/intlayer_with_angular_19.md +1 -1
- package/docs/ja/intlayer_with_angular_21.md +1 -1
- package/docs/ja/intlayer_with_astro.md +1 -1
- package/docs/ja/intlayer_with_astro_lit.md +1 -1
- package/docs/ja/intlayer_with_astro_preact.md +1 -1
- package/docs/ja/intlayer_with_astro_react.md +1 -1
- package/docs/ja/intlayer_with_astro_solid.md +1 -1
- package/docs/ja/intlayer_with_astro_svelte.md +1 -1
- package/docs/ja/intlayer_with_astro_vanilla.md +1 -1
- package/docs/ja/intlayer_with_astro_vue.md +1 -1
- package/docs/ja/intlayer_with_create_react_app.md +1 -1
- package/docs/ja/intlayer_with_express.md +1 -1
- package/docs/ja/intlayer_with_hono.md +1 -1
- package/docs/ja/intlayer_with_nestjs.md +1 -1
- package/docs/ja/intlayer_with_nextjs_14.md +1 -1
- package/docs/ja/intlayer_with_nextjs_15.md +1 -1
- package/docs/ja/intlayer_with_nextjs_16.md +1 -1
- package/docs/ja/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/ja/intlayer_with_vite+preact.md +1 -1
- package/docs/ja/intlayer_with_vite+react.md +1 -1
- package/docs/ja/intlayer_with_vite+vue.md +1 -1
- package/docs/ja/introduction.md +0 -1
- package/docs/ja/readme.md +8 -8
- package/docs/ko/benchmark/nextjs.md +1 -1
- package/docs/ko/benchmark/solid.md +1 -1
- package/docs/ko/benchmark/svelte.md +1 -1
- package/docs/ko/benchmark/tanstack.md +1 -1
- package/docs/ko/benchmark/vue.md +1 -1
- package/docs/ko/bundle_optimization.md +5 -1
- package/docs/ko/how_works_intlayer.md +2 -2
- package/docs/ko/interest_of_intlayer.md +7 -7
- package/docs/ko/intlayer_CMS.md +1 -1
- package/docs/ko/intlayer_with_adonisjs.md +1 -1
- package/docs/ko/intlayer_with_analog.md +1 -1
- package/docs/ko/intlayer_with_angular_19.md +1 -1
- package/docs/ko/intlayer_with_angular_21.md +1 -1
- package/docs/ko/intlayer_with_astro.md +1 -1
- package/docs/ko/intlayer_with_astro_lit.md +1 -1
- package/docs/ko/intlayer_with_astro_preact.md +1 -1
- package/docs/ko/intlayer_with_astro_react.md +1 -1
- package/docs/ko/intlayer_with_astro_solid.md +1 -1
- package/docs/ko/intlayer_with_astro_svelte.md +1 -1
- package/docs/ko/intlayer_with_astro_vanilla.md +1 -1
- package/docs/ko/intlayer_with_astro_vue.md +1 -1
- package/docs/ko/intlayer_with_create_react_app.md +1 -1
- package/docs/ko/intlayer_with_express.md +1 -1
- package/docs/ko/intlayer_with_hono.md +1 -1
- package/docs/ko/intlayer_with_nestjs.md +1 -1
- package/docs/ko/intlayer_with_nextjs_14.md +1 -1
- package/docs/ko/intlayer_with_nextjs_15.md +1 -1
- package/docs/ko/intlayer_with_nextjs_16.md +1 -1
- package/docs/ko/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/ko/intlayer_with_react_router_v7.md +2 -2
- package/docs/ko/intlayer_with_vite+preact.md +1 -1
- package/docs/ko/intlayer_with_vite+react.md +1 -1
- package/docs/ko/intlayer_with_vite+vue.md +1 -1
- package/docs/ko/introduction.md +0 -1
- package/docs/ko/readme.md +8 -8
- package/docs/nl/bundle_optimization.md +5 -1
- package/docs/nl/interest_of_intlayer.md +7 -7
- package/docs/nl/intlayer_with_angular_21.md +1 -1
- package/docs/nl/intlayer_with_hono.md +1 -1
- package/docs/nl/introduction.md +0 -1
- package/docs/pl/benchmark/nextjs.md +1 -1
- package/docs/pl/benchmark/solid.md +1 -1
- package/docs/pl/benchmark/svelte.md +1 -1
- package/docs/pl/benchmark/tanstack.md +1 -1
- package/docs/pl/benchmark/vue.md +1 -1
- package/docs/pl/bundle_optimization.md +5 -1
- package/docs/pl/how_works_intlayer.md +2 -2
- package/docs/pl/interest_of_intlayer.md +7 -7
- package/docs/pl/intlayer_CMS.md +1 -1
- package/docs/pl/intlayer_with_adonisjs.md +1 -1
- package/docs/pl/intlayer_with_analog.md +1 -1
- package/docs/pl/intlayer_with_angular_19.md +1 -1
- package/docs/pl/intlayer_with_angular_21.md +1 -1
- package/docs/pl/intlayer_with_astro.md +1 -1
- package/docs/pl/intlayer_with_astro_lit.md +1 -1
- package/docs/pl/intlayer_with_astro_preact.md +1 -1
- package/docs/pl/intlayer_with_astro_react.md +1 -1
- package/docs/pl/intlayer_with_astro_solid.md +1 -1
- package/docs/pl/intlayer_with_astro_svelte.md +1 -1
- package/docs/pl/intlayer_with_astro_vanilla.md +1 -1
- package/docs/pl/intlayer_with_astro_vue.md +1 -1
- package/docs/pl/intlayer_with_create_react_app.md +1 -1
- package/docs/pl/intlayer_with_express.md +1 -1
- package/docs/pl/intlayer_with_hono.md +1 -1
- package/docs/pl/intlayer_with_nestjs.md +1 -1
- package/docs/pl/intlayer_with_nextjs_14.md +1 -1
- package/docs/pl/intlayer_with_nextjs_15.md +1 -1
- package/docs/pl/intlayer_with_nextjs_16.md +1 -1
- package/docs/pl/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/pl/intlayer_with_react_router_v7.md +2 -2
- package/docs/pl/intlayer_with_vite+preact.md +1 -1
- package/docs/pl/intlayer_with_vite+react.md +1 -1
- package/docs/pl/intlayer_with_vite+vue.md +1 -1
- package/docs/pl/introduction.md +0 -1
- package/docs/pl/readme.md +8 -8
- package/docs/pt/benchmark/nextjs.md +1 -1
- package/docs/pt/benchmark/solid.md +1 -1
- package/docs/pt/benchmark/svelte.md +1 -1
- package/docs/pt/benchmark/tanstack.md +1 -1
- package/docs/pt/benchmark/vue.md +1 -1
- package/docs/pt/bundle_optimization.md +5 -1
- package/docs/pt/how_works_intlayer.md +2 -2
- package/docs/pt/interest_of_intlayer.md +7 -7
- package/docs/pt/intlayer_CMS.md +1 -1
- package/docs/pt/intlayer_with_adonisjs.md +1 -1
- package/docs/pt/intlayer_with_analog.md +1 -1
- package/docs/pt/intlayer_with_angular_19.md +1 -1
- package/docs/pt/intlayer_with_angular_21.md +1 -1
- package/docs/pt/intlayer_with_astro.md +1 -1
- package/docs/pt/intlayer_with_astro_lit.md +1 -1
- package/docs/pt/intlayer_with_astro_preact.md +1 -1
- package/docs/pt/intlayer_with_astro_react.md +1 -1
- package/docs/pt/intlayer_with_astro_solid.md +1 -1
- package/docs/pt/intlayer_with_astro_svelte.md +1 -1
- package/docs/pt/intlayer_with_astro_vanilla.md +1 -1
- package/docs/pt/intlayer_with_astro_vue.md +1 -1
- package/docs/pt/intlayer_with_create_react_app.md +1 -1
- package/docs/pt/intlayer_with_express.md +1 -1
- package/docs/pt/intlayer_with_hono.md +1 -1
- package/docs/pt/intlayer_with_nestjs.md +1 -1
- package/docs/pt/intlayer_with_nextjs_14.md +1 -1
- package/docs/pt/intlayer_with_nextjs_15.md +1 -1
- package/docs/pt/intlayer_with_nextjs_16.md +1 -1
- package/docs/pt/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/pt/intlayer_with_react_router_v7.md +2 -2
- package/docs/pt/intlayer_with_vite+preact.md +1 -1
- package/docs/pt/intlayer_with_vite+react.md +1 -1
- package/docs/pt/intlayer_with_vite+vue.md +1 -1
- package/docs/pt/introduction.md +0 -1
- package/docs/pt/readme.md +8 -8
- package/docs/ru/benchmark/nextjs.md +1 -1
- package/docs/ru/benchmark/solid.md +1 -1
- package/docs/ru/benchmark/svelte.md +1 -1
- package/docs/ru/benchmark/tanstack.md +1 -1
- package/docs/ru/benchmark/vue.md +1 -1
- package/docs/ru/bundle_optimization.md +5 -1
- package/docs/ru/how_works_intlayer.md +2 -2
- package/docs/ru/interest_of_intlayer.md +7 -7
- package/docs/ru/intlayer_CMS.md +1 -1
- package/docs/ru/intlayer_with_adonisjs.md +1 -1
- package/docs/ru/intlayer_with_analog.md +1 -1
- package/docs/ru/intlayer_with_angular_19.md +1 -1
- package/docs/ru/intlayer_with_angular_21.md +1 -1
- package/docs/ru/intlayer_with_astro.md +1 -1
- package/docs/ru/intlayer_with_astro_lit.md +1 -1
- package/docs/ru/intlayer_with_astro_preact.md +1 -1
- package/docs/ru/intlayer_with_astro_react.md +1 -1
- package/docs/ru/intlayer_with_astro_solid.md +1 -1
- package/docs/ru/intlayer_with_astro_svelte.md +1 -1
- package/docs/ru/intlayer_with_astro_vanilla.md +1 -1
- package/docs/ru/intlayer_with_astro_vue.md +1 -1
- package/docs/ru/intlayer_with_create_react_app.md +1 -1
- package/docs/ru/intlayer_with_express.md +1 -1
- package/docs/ru/intlayer_with_hono.md +1 -1
- package/docs/ru/intlayer_with_nestjs.md +1 -1
- package/docs/ru/intlayer_with_nextjs_14.md +1 -1
- package/docs/ru/intlayer_with_nextjs_15.md +1 -1
- package/docs/ru/intlayer_with_nextjs_16.md +1 -1
- package/docs/ru/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/ru/intlayer_with_react_router_v7.md +2 -2
- package/docs/ru/intlayer_with_vite+preact.md +1 -1
- package/docs/ru/intlayer_with_vite+react.md +1 -1
- package/docs/ru/intlayer_with_vite+vue.md +1 -1
- package/docs/ru/introduction.md +0 -1
- package/docs/ru/readme.md +8 -8
- package/docs/tr/benchmark/nextjs.md +1 -1
- package/docs/tr/benchmark/solid.md +1 -1
- package/docs/tr/benchmark/svelte.md +1 -1
- package/docs/tr/benchmark/tanstack.md +1 -1
- package/docs/tr/benchmark/vue.md +1 -1
- package/docs/tr/bundle_optimization.md +5 -1
- package/docs/tr/how_works_intlayer.md +2 -2
- package/docs/tr/interest_of_intlayer.md +7 -7
- package/docs/tr/intlayer_CMS.md +1 -1
- package/docs/tr/intlayer_with_adonisjs.md +1 -1
- package/docs/tr/intlayer_with_analog.md +1 -1
- package/docs/tr/intlayer_with_angular_19.md +1 -1
- package/docs/tr/intlayer_with_angular_21.md +1 -1
- package/docs/tr/intlayer_with_astro.md +1 -1
- package/docs/tr/intlayer_with_astro_lit.md +1 -1
- package/docs/tr/intlayer_with_astro_preact.md +1 -1
- package/docs/tr/intlayer_with_astro_react.md +1 -1
- package/docs/tr/intlayer_with_astro_solid.md +1 -1
- package/docs/tr/intlayer_with_astro_svelte.md +1 -1
- package/docs/tr/intlayer_with_astro_vanilla.md +1 -1
- package/docs/tr/intlayer_with_astro_vue.md +1 -1
- package/docs/tr/intlayer_with_create_react_app.md +1 -1
- package/docs/tr/intlayer_with_express.md +1 -1
- package/docs/tr/intlayer_with_hono.md +1 -1
- package/docs/tr/intlayer_with_nestjs.md +1 -1
- package/docs/tr/intlayer_with_nextjs_14.md +1 -1
- package/docs/tr/intlayer_with_nextjs_15.md +1 -1
- package/docs/tr/intlayer_with_nextjs_16.md +1 -1
- package/docs/tr/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/tr/intlayer_with_react_router_v7.md +1 -1
- 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+vue.md +1 -1
- package/docs/tr/introduction.md +0 -1
- package/docs/tr/readme.md +8 -8
- package/docs/uk/benchmark/nextjs.md +1 -1
- package/docs/uk/benchmark/solid.md +1 -1
- package/docs/uk/benchmark/svelte.md +1 -1
- package/docs/uk/benchmark/tanstack.md +1 -1
- package/docs/uk/benchmark/vue.md +1 -1
- package/docs/uk/bundle_optimization.md +5 -1
- package/docs/uk/how_works_intlayer.md +2 -2
- package/docs/uk/interest_of_intlayer.md +7 -7
- package/docs/uk/intlayer_CMS.md +1 -1
- package/docs/uk/intlayer_with_adonisjs.md +1 -1
- package/docs/uk/intlayer_with_analog.md +1 -1
- package/docs/uk/intlayer_with_angular_19.md +1 -1
- package/docs/uk/intlayer_with_angular_21.md +1 -1
- package/docs/uk/intlayer_with_astro.md +1 -1
- package/docs/uk/intlayer_with_astro_lit.md +1 -1
- package/docs/uk/intlayer_with_astro_preact.md +1 -1
- package/docs/uk/intlayer_with_astro_react.md +1 -1
- package/docs/uk/intlayer_with_astro_solid.md +1 -1
- package/docs/uk/intlayer_with_astro_svelte.md +1 -1
- package/docs/uk/intlayer_with_astro_vanilla.md +1 -1
- package/docs/uk/intlayer_with_astro_vue.md +1 -1
- package/docs/uk/intlayer_with_create_react_app.md +1 -1
- package/docs/uk/intlayer_with_express.md +1 -1
- package/docs/uk/intlayer_with_hono.md +1 -1
- package/docs/uk/intlayer_with_nestjs.md +1 -1
- package/docs/uk/intlayer_with_nextjs_14.md +1 -1
- package/docs/uk/intlayer_with_nextjs_15.md +1 -1
- package/docs/uk/intlayer_with_nextjs_16.md +1 -1
- package/docs/uk/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/uk/intlayer_with_react_router_v7.md +1 -1
- package/docs/uk/intlayer_with_vite+preact.md +1 -1
- package/docs/uk/intlayer_with_vite+react.md +1 -1
- package/docs/uk/intlayer_with_vite+vue.md +1 -1
- package/docs/uk/introduction.md +0 -1
- package/docs/uk/readme.md +8 -8
- package/docs/ur/bundle_optimization.md +5 -1
- package/docs/ur/interest_of_intlayer.md +7 -7
- package/docs/ur/intlayer_with_angular_21.md +1 -1
- package/docs/ur/intlayer_with_hono.md +1 -1
- package/docs/ur/introduction.md +0 -1
- package/docs/vi/benchmark/nextjs.md +1 -1
- package/docs/vi/benchmark/solid.md +1 -1
- package/docs/vi/benchmark/svelte.md +1 -1
- package/docs/vi/benchmark/tanstack.md +1 -1
- package/docs/vi/benchmark/vue.md +1 -1
- package/docs/vi/bundle_optimization.md +5 -1
- package/docs/vi/how_works_intlayer.md +2 -2
- package/docs/vi/interest_of_intlayer.md +7 -7
- package/docs/vi/intlayer_CMS.md +1 -1
- package/docs/vi/intlayer_with_adonisjs.md +1 -1
- package/docs/vi/intlayer_with_analog.md +1 -1
- package/docs/vi/intlayer_with_angular_19.md +1 -1
- package/docs/vi/intlayer_with_angular_21.md +1 -1
- package/docs/vi/intlayer_with_astro.md +1 -1
- package/docs/vi/intlayer_with_astro_lit.md +1 -1
- package/docs/vi/intlayer_with_astro_preact.md +1 -1
- package/docs/vi/intlayer_with_astro_react.md +1 -1
- package/docs/vi/intlayer_with_astro_solid.md +1 -1
- package/docs/vi/intlayer_with_astro_svelte.md +1 -1
- package/docs/vi/intlayer_with_astro_vanilla.md +1 -1
- package/docs/vi/intlayer_with_astro_vue.md +1 -1
- package/docs/vi/intlayer_with_create_react_app.md +1 -1
- package/docs/vi/intlayer_with_express.md +1 -1
- package/docs/vi/intlayer_with_hono.md +1 -1
- package/docs/vi/intlayer_with_nestjs.md +1 -1
- package/docs/vi/intlayer_with_nextjs_14.md +1 -1
- package/docs/vi/intlayer_with_nextjs_15.md +1 -1
- package/docs/vi/intlayer_with_nextjs_16.md +1 -1
- package/docs/vi/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/vi/intlayer_with_vite+preact.md +1 -1
- package/docs/vi/intlayer_with_vite+react.md +1 -1
- package/docs/vi/intlayer_with_vite+vue.md +1 -1
- package/docs/vi/introduction.md +0 -1
- package/docs/vi/readme.md +8 -8
- package/docs/zh/benchmark/nextjs.md +1 -1
- package/docs/zh/benchmark/solid.md +1 -1
- package/docs/zh/benchmark/svelte.md +1 -1
- package/docs/zh/benchmark/tanstack.md +1 -1
- package/docs/zh/benchmark/vue.md +1 -1
- package/docs/zh/bundle_optimization.md +5 -1
- package/docs/zh/how_works_intlayer.md +2 -2
- package/docs/zh/interest_of_intlayer.md +7 -7
- package/docs/zh/intlayer_CMS.md +1 -1
- package/docs/zh/intlayer_with_adonisjs.md +1 -1
- package/docs/zh/intlayer_with_analog.md +1 -1
- package/docs/zh/intlayer_with_angular_19.md +1 -1
- package/docs/zh/intlayer_with_angular_21.md +1 -1
- package/docs/zh/intlayer_with_astro.md +1 -1
- package/docs/zh/intlayer_with_astro_lit.md +1 -1
- package/docs/zh/intlayer_with_astro_preact.md +1 -1
- package/docs/zh/intlayer_with_astro_react.md +1 -1
- package/docs/zh/intlayer_with_astro_solid.md +1 -1
- package/docs/zh/intlayer_with_astro_svelte.md +1 -1
- package/docs/zh/intlayer_with_astro_vanilla.md +1 -1
- package/docs/zh/intlayer_with_astro_vue.md +1 -1
- package/docs/zh/intlayer_with_create_react_app.md +1 -1
- package/docs/zh/intlayer_with_express.md +1 -1
- package/docs/zh/intlayer_with_hono.md +1 -1
- package/docs/zh/intlayer_with_nestjs.md +1 -1
- package/docs/zh/intlayer_with_nextjs_14.md +1 -1
- package/docs/zh/intlayer_with_nextjs_15.md +1 -1
- package/docs/zh/intlayer_with_nextjs_16.md +1 -1
- package/docs/zh/intlayer_with_nextjs_page_router.md +1 -1
- package/docs/zh/intlayer_with_react_router_v7.md +2 -2
- package/docs/zh/intlayer_with_vite+preact.md +1 -1
- package/docs/zh/intlayer_with_vite+react.md +1 -1
- package/docs/zh/intlayer_with_vite+vue.md +1 -1
- package/docs/zh/introduction.md +0 -1
- package/docs/zh/readme.md +8 -8
- package/docs/zh-TW/bundle_optimization.md +5 -1
- package/docs/zh-TW/interest_of_intlayer.md +7 -7
- package/docs/zh-TW/intlayer_with_angular_21.md +1 -1
- package/docs/zh-TW/introduction.md +0 -1
- package/frequent_questions/ar/claude_code_token_consumption.md +152 -0
- package/frequent_questions/de/claude_code_token_consumption.md +152 -0
- package/frequent_questions/en/claude_code_token_consumption.md +152 -0
- package/frequent_questions/en-GB/claude_code_token_consumption.md +152 -0
- package/frequent_questions/es/claude_code_token_consumption.md +152 -0
- package/frequent_questions/fr/claude_code_token_consumption.md +152 -0
- package/frequent_questions/hi/claude_code_token_consumption.md +152 -0
- package/frequent_questions/id/claude_code_token_consumption.md +152 -0
- package/frequent_questions/it/claude_code_token_consumption.md +152 -0
- package/frequent_questions/ja/claude_code_token_consumption.md +152 -0
- package/frequent_questions/ko/claude_code_token_consumption.md +152 -0
- package/frequent_questions/pl/claude_code_token_consumption.md +152 -0
- package/frequent_questions/pt/claude_code_token_consumption.md +152 -0
- package/frequent_questions/ru/claude_code_token_consumption.md +152 -0
- package/frequent_questions/tr/claude_code_token_consumption.md +152 -0
- package/frequent_questions/uk/claude_code_token_consumption.md +152 -0
- package/frequent_questions/vi/claude_code_token_consumption.md +152 -0
- package/frequent_questions/zh/claude_code_token_consumption.md +152 -0
- package/package.json +8 -7
- package/src/generated/blog.entry.ts +240 -0
- package/src/generated/frequentQuestions.entry.ts +20 -0
- package/blog/en/___per-component_vs_centralized_i18n.md +0 -255
- package/blog/pl/___per-component_vs_centralized_i18n.md +0 -100
- package/docs/en/benchmark/___NOTE.md +0 -101
- package/docs/en/benchmark/___nextjs.md +0 -197
- package/docs/en/benchmark/___solid.md +0 -12
- package/docs/en/benchmark/___svelte.md +0 -16
- package/docs/en/benchmark/___tanstack.md +0 -190
- package/docs/en/benchmark/___vue.md +0 -7
- package/docs/pl/benchmark/___NOTE.md +0 -101
- package/docs/pl/benchmark/___nextjs.md +0 -198
- package/docs/pl/benchmark/___solid.md +0 -36
- package/docs/pl/benchmark/___svelte.md +0 -36
- package/docs/pl/benchmark/___tanstack.md +0 -36
- package/docs/pl/benchmark/___vue.md +0 -36
|
@@ -0,0 +1,445 @@
|
|
|
1
|
+
---
|
|
2
|
+
createdAt: 2026-09-13
|
|
3
|
+
updatedAt: 2026-09-13
|
|
4
|
+
title: "i18next vs Intlayer: Đo kiểm và So sánh chi tiết năm 2026"
|
|
5
|
+
description: "Đo lường react-i18next và next-i18next so với Intlayer trên Next.js và TanStack Start. Kích thước bundle, rò rỉ nội dung, tốc độ phản hồi khi chuyển ngôn ngữ và trải nghiệm lập trình viên."
|
|
6
|
+
keywords:
|
|
7
|
+
- i18next
|
|
8
|
+
- react-i18next
|
|
9
|
+
- next-i18next
|
|
10
|
+
- Intlayer
|
|
11
|
+
- Đa ngôn ngữ
|
|
12
|
+
- i18n
|
|
13
|
+
- Benchmark
|
|
14
|
+
- Kích thước bundle
|
|
15
|
+
- Blog
|
|
16
|
+
- Next.js
|
|
17
|
+
- TanStack Start
|
|
18
|
+
- JavaScript
|
|
19
|
+
- React
|
|
20
|
+
slugs:
|
|
21
|
+
- blog
|
|
22
|
+
- i18next-vs-intlayer
|
|
23
|
+
author: aymericzip
|
|
24
|
+
---
|
|
25
|
+
|
|
26
|
+
# i18next VS Intlayer | Đo kiểm đa ngôn ngữ (i18n) cho React & Next.js
|
|
27
|
+
|
|
28
|
+
`i18next` là framework i18n phổ biến nhất trong hệ sinh thái JavaScript. Thông qua `react-i18next` và `next-i18next`, nó đang vận hành phần lớn các ứng dụng React và Next.js. Intlayer là một giải pháp thay thế hiện đại dựa trên trình biên dịch và cô lập phạm vi theo từng component.
|
|
29
|
+
|
|
30
|
+
Bài viết này so sánh hai giải pháp dựa trên số liệu đo lường thực tế thay vì danh sách tính năng đơn thuần. Các số liệu được trích xuất từ [Benchmark Bloom](https://github.com/intlayer-org/benchmark-bloom) - một bộ đo lường nguồn mở xây dựng cùng một ứng dụng mẫu trên từng thư viện và ghi nhận chính xác những gì trình duyệt tải về.
|
|
31
|
+
|
|
32
|
+
<TOC/>
|
|
33
|
+
|
|
34
|
+
> **Tóm tắt cốt lõi (tl;dr)**: `i18next` là runtime nặng nhất trong thử nghiệm benchmark: làm tăng thêm **+77 KB gzip mỗi trang** trên Next.js ở cấu hình cơ bản, và vẫn tăng **+22 KB** sau khi đã tối ưu hóa toàn diện namespace và lazy-loading. Ngược lại, Intlayer chỉ thêm vỏn vẹn **+0.3 KB**. Mọi cấu hình `i18next` ngoại trừ cấu hình phân tách phạm vi hoàn toàn (scoped) đều **rò rỉ khoảng 90% chuỗi ký tự của các trang khác**; trong khi Intlayer đạt **0%** rò rỉ theo mặc định. Thao tác chuyển đổi ngôn ngữ với backend tải lười (lazy load) mất **123-185 ms** với `react-i18next`, so với chỉ **3-4 ms** ở Intlayer. Bộ chuyển đổi tương thích `@intlayer/next-i18next` giữ nguyên API của `i18next` nhưng hạ kích thước trang từ **218.5 KB** xuống còn **150.7 KB**.
|
|
35
|
+
|
|
36
|
+
## Tóm tắt nhanh
|
|
37
|
+
|
|
38
|
+
- **i18next / react-i18next / next-i18next** - Lâu đời, hệ sinh thái plugin đồ sộ và độc lập với framework. Hỗ trợ namespaces, bộ nhận diện ngôn ngữ, các dạng backend, ICU qua plugin và thẻ `<Trans>` cho nội dung có cấu trúc. Dữ liệu bản dịch được tập trung tại `locales/{lng}/{ns}.json`. Rất mạnh mẽ nhưng mọi tối ưu (chia nhỏ namespace, tải theo từng trang, an toàn kiểu dữ liệu) đều đòi hỏi bạn phải tự cấu hình và bảo trì thủ công.
|
|
39
|
+
- **Intlayer** - Mô hình nội dung lấy component làm trung tâm. Các tệp từ điển `.content.ts` nằm ngay cạnh component mà chúng phục vụ, trình biên dịch tại thời điểm build sẽ tự động thực hiện tree-shaking và lazy loading theo từng component và ngôn ngữ, tự động tạo kiểu TypeScript nghiêm ngặt từ nội dung và chặn quá trình build nếu thiếu bản dịch. Tích hợp sẵn middleware, bộ hỗ trợ SEO, Visual Editor / CMS và biên dịch hỗ trợ bởi AI.
|
|
40
|
+
|
|
41
|
+
| Thư viện | Lượt gắn sao GitHub | Tổng số Commit | Commit gần nhất | Phiên bản đầu | Phiên bản NPM | Lượt tải hàng tháng NPM |
|
|
42
|
+
| ----------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------- | --------------------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------- |
|
|
43
|
+
| `aymericzip/intlayer` | [](https://github.com/aymericzip/intlayer/stargazers) | [](https://github.com/aymericzip/intlayer/commits) | [](https://github.com/aymericzip/intlayer/commits) | Tháng 4/2024 | [](https://www.npmjs.com/package/intlayer) | [](https://www.npmjs.com/package/intlayer) |
|
|
44
|
+
| `i18next/i18next` | [](https://github.com/i18next/i18next/stargazers) | [](https://github.com/i18next/i18next/commits) | [](https://github.com/i18next/i18next/commits) | Tháng 1/2012 | [](https://www.npmjs.com/package/i18next) | [](https://www.npmjs.com/package/i18next) |
|
|
45
|
+
| `i18next/react-i18next` | [](https://github.com/i18next/react-i18next/stargazers) | [](https://github.com/i18next/react-i18next/commits) | [](https://github.com/i18next/react-i18next/commits) | Tháng 12/2015 | [](https://www.npmjs.com/package/react-i18next) | [](https://www.npmjs.com/package/react-i18next) |
|
|
46
|
+
| `i18next/next-i18next` | [](https://github.com/i18next/next-i18next/stargazers) | [](https://github.com/i18next/next-i18next/commits) | [](https://github.com/i18next/next-i18next/commits) | Tháng 11/2018 | [](https://www.npmjs.com/package/next-i18next) | [](https://www.npmjs.com/package/next-i18next) |
|
|
47
|
+
|
|
48
|
+
> Các huy hiệu cập nhật tự động. Số liệu thực tế có thể biến động theo thời gian.
|
|
49
|
+
|
|
50
|
+
## So sánh tính năng chi tiết
|
|
51
|
+
|
|
52
|
+
| Tính năng | Intlayer (`react-intlayer` / `next-intlayer`) | i18next (`react-i18next` / `next-i18next`) |
|
|
53
|
+
| ------------------------------------------------- | ------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------ |
|
|
54
|
+
| **Bản dịch đặt ngay cạnh component** | ✅ Có, tệp `.content.ts` đặt cùng thư mục với component | ❌ Không, tập trung ở `locales/{lng}/{ns}.json` |
|
|
55
|
+
| **Tích hợp TypeScript** | ✅ Tự động tạo kiểu dữ liệu nghiêm ngặt từ nội dung | ⚠️ Cơ bản; các khóa nghiêm ngặt cần mở rộng `CustomTypeOptions` và gán kiểu thủ công |
|
|
56
|
+
| **Phát hiện bản dịch còn thiếu** | ✅ Báo lỗi TypeScript + lỗi/cảnh báo trong thời gian build | ⚠️ Fallback ở runtime (`saveMissing`, hiển thị lại chuỗi khóa) |
|
|
57
|
+
| **Nội dung đa dạng (JSX / Markdown / Component)** | ✅ Hỗ trợ trực tiếp tự nhiên | ⚠️ Sử dụng thẻ đánh chỉ mục `<Trans>` |
|
|
58
|
+
| **Hỗ trợ định dạng ICU** | ⚠️ Đang hoàn thiện | ⚠️ Cần bổ sung plugin (`i18next-icu`) |
|
|
59
|
+
| **Xử lý số nhiều (Pluralization)** | ✅ Định dạng dựa trên liệt kê (Enum) tường minh | ✅ Hậu tố `_one` / `_other` (dựa trên Intl.PluralRules) |
|
|
60
|
+
| **Định dạng (ngày, số, tiền tệ)** | ✅ `useNumber`, `useDate`, ... (tận dụng Intl gốc) | ⚠️ Sử dụng formatter nội suy hoặc gọi `Intl.*` thủ công |
|
|
61
|
+
| **Định tuyến bản địa hóa và middleware** | ✅ Tích hợp sẵn proxy/middleware, `getMultilingualUrls` | ⚠️ Không có sẵn trong core; cần tự tạo middleware hoặc dùng thư viện ngoài |
|
|
62
|
+
| **Bộ hỗ trợ SEO (hreflang, sitemap, robots)** | ✅ Cung cấp đầy đủ | ❌ Phải thiết lập thủ công |
|
|
63
|
+
| **Component Server đồng bộ (RSC)** | ✅ `useIntlayer` từ `next-intlayer/server` dùng được ở mọi Server Component con | ⚠️ Gọi `getFixedT` ở cấp page rồi truyền `t` qua Props xuống các component |
|
|
64
|
+
| **Tree-shaking (chỉ đóng gói nội dung dùng)** | ✅ Trình biên dịch tự động xử lý theo component và ngôn ngữ | ⚠️ Thủ công: chia namespace + liệt kê `ns` cho từng trang + cấu hình backend |
|
|
65
|
+
| **Tải lười (Lazy loading)** | ✅ `importMode: 'dynamic'` (chỉ một dòng cấu hình) | ✅ Thông qua các plugin backend (`i18next-resources-to-backend`, v.v.) |
|
|
66
|
+
| **Dọn dẹp nội dung thừa (Purge)** | ✅ Loại bỏ các từ điển không dùng đến khi build | ❌ Không hỗ trợ mặc định |
|
|
67
|
+
| **Kiểm thử bản dịch còn thiếu (CLI / CI)** | ✅ `npx intlayer content test` | ⚠️ Cần công cụ ngoài như `i18next-parser` |
|
|
68
|
+
| **Biên dịch bằng AI** | ✅ Tích hợp sẵn, dùng API key của riêng bạn | ❌ Không có (Locize là dịch vụ tính phí riêng) |
|
|
69
|
+
| **Visual Editor / CMS** | ✅ Visual Editor miễn phí + CMS tùy chọn | ❌ Không có (phụ thuộc vào Locize hoặc nền tảng ngoài) |
|
|
70
|
+
| **Máy chủ MCP & Kỹ năng Agent** | ✅ Hỗ trợ | ❌ Không hỗ trợ |
|
|
71
|
+
| **Hệ sinh thái & Cộng đồng** | ⚠️ Mới hơn nhưng tốc độ phát triển rất nhanh | ✅ Lớn nhất và lâu đời nhất |
|
|
72
|
+
|
|
73
|
+
## Đo kiểm Benchmark
|
|
74
|
+
|
|
75
|
+
### Những gì đã được đo lường?
|
|
76
|
+
|
|
77
|
+
Bộ công cụ [Benchmark Bloom](https://github.com/intlayer-org/benchmark-bloom) xây dựng **cùng một ứng dụng giống hệt nhau** cho từng thư viện: **10 trang** (home, about, blog, careers, contact, FAQ, pricing, products, settings, team), **10 ngôn ngữ** (`en`, `fr`, `es`, `de`, `it`, `pt`, `zh`, `ja`, `ko`, `ru`), cùng component và cùng nội dung văn bản. Dữ liệu được đo trên hai ngôn ngữ `en` và `fr`. Mỗi thư viện được đánh giá qua tối đa bốn **chiến lược tải**:
|
|
78
|
+
|
|
79
|
+
| Chiến lược | Mô tả | Trường hợp sử dụng tiêu biểu |
|
|
80
|
+
| ------------------ | ---------------------------------------------------------------------------------------- | --------------------------------------------- |
|
|
81
|
+
| **static** | Gom tất cả ngôn ngữ và trang vào một gói duy nhất (`resources` nhúng thẳng vào `init()`) | Làm bản thử nghiệm nhanh, code sinh bởi AI |
|
|
82
|
+
| **dynamic** | Chỉ tải ngôn ngữ hiện tại qua backend, nhưng tải toàn bộ các namespace cùng lúc | Đa số các ứng dụng thông thường |
|
|
83
|
+
| **scoped-static** | Mỗi route một namespace riêng, nhưng đóng gói tất cả vào bundle ban đầu | Rất hiếm khi sử dụng |
|
|
84
|
+
| **scoped-dynamic** | Namespace theo route + tải lười qua backend. Chỉ tải trang hiện tại và ngôn ngữ hiện tại | Ứng dụng có giới hạn nghiêm ngặt về hiệu năng |
|
|
85
|
+
|
|
86
|
+
Intlayer không cần biến thể "scoped": Trình biên dịch tự động giới hạn phạm vi nội dung **ở mức độ từng component**, vì vậy hai dòng `static` và `dynamic` của Intlayer đã được tối ưu hóa sẵn.
|
|
87
|
+
|
|
88
|
+
Các chỉ số đo lường:
|
|
89
|
+
|
|
90
|
+
- **Lib size**: Dung lượng gzip của một component rỗng chỉ import thư viện i18n (chi phí cố định của runtime).
|
|
91
|
+
- **Page JS**: Dung lượng gzip JavaScript trung bình tải về mỗi trang (tính chung trên mọi trang và ngôn ngữ).
|
|
92
|
+
- **Locale leak %**: Tỷ lệ chuỗi dịch trong JS tải về thuộc về các ngôn ngữ mà người dùng **không** xem.
|
|
93
|
+
- **Page leak %**: Tỷ lệ chuỗi dịch trong JS tải về thuộc về các trang mà người dùng **không** mở.
|
|
94
|
+
- **Component avg**: Kích thước gzip trung bình của từng component khi được biên dịch cô lập.
|
|
95
|
+
- **E2E reactivity**: Thời gian thực tế tính từ khi người dùng chọn ngôn ngữ mới đến khi thẻ `html[lang]` trong DOM được cập nhật xong (Playwright, trung bình 5 lần lặp).
|
|
96
|
+
- **Hydration**: Thời gian thực hiện quá trình hydrate của React.
|
|
97
|
+
|
|
98
|
+
> Số liệu bên dưới được ghi nhận vào ngày **2026-09-12** với `next-i18next` 16.3.0, `react-i18next` 17.0.13 và `intlayer` 9.5.1. Ứng dụng kiểm thử được thiết kế gọn nhẹ, nên các tỷ lệ rò rỉ thể hiện **mô hình kiến trúc**: Rò rỉ sẽ tăng theo lượng văn bản thực tế, trong khi chi phí runtime giữ nguyên.
|
|
99
|
+
|
|
100
|
+
### Kết quả trên Next.js (`next-i18next`)
|
|
101
|
+
|
|
102
|
+
| Thư viện | Chiến lược | Dung lượng Lib (gz) | JS TB mỗi trang (gz) | Rò rỉ ngôn ngữ | Rò rỉ trang | Kích thước TB Comp (gz) | Phản hồi E2E | Thời gian Hydrate |
|
|
103
|
+
| -------------------------------------- | -------------- | ------------------: | -------------------: | -------------: | ----------: | ----------------------: | -----------: | ----------------: |
|
|
104
|
+
| **base** (không i18n) | - | 0.0 KB | 141.0 KB | 0.0% | 0.0% | 0.9 KB | 13.4 ms | 11.8 ms |
|
|
105
|
+
| `next-i18next` | static | 19.7 KB | 218.5 KB | 0.0% | 89.8% | 78.5 KB | 16.4 ms | 15.6 ms |
|
|
106
|
+
| `next-i18next` | dynamic | 19.7 KB | 169.5 KB | 50.0% | 89.8% | 26.1 KB | 15.4 ms | 27.7 ms |
|
|
107
|
+
| `next-i18next` | scoped-static | 19.7 KB | 220.1 KB | 0.0% | 89.8% | 78.9 KB | 16.4 ms | 14.7 ms |
|
|
108
|
+
| `next-i18next` | scoped-dynamic | 19.7 KB | 163.4 KB | 0.0% | 0.0% | 27.1 KB | 15.9 ms | 15.1 ms |
|
|
109
|
+
| **`next-intlayer`** | static | **5.5 KB** | **141.3 KB** | **0.0%** | **0.0%** | **8.5 KB** | **15.5 ms** | 16.9 ms |
|
|
110
|
+
| **`next-intlayer`** | dynamic | **5.5 KB** | **141.3 KB** | **0.0%** | **0.0%** | **6.9 KB** | **15.3 ms** | 15.9 ms |
|
|
111
|
+
| `@intlayer/next-i18next` (tương thích) | static | 9.4 KB | 150.7 KB | 0.0% | 0.0% | 9.7 KB | 10.7 ms | 11.3 ms |
|
|
112
|
+
| `@intlayer/next-i18next` (tương thích) | dynamic | 9.4 KB | 150.7 KB | 0.0% | 0.0% | 9.7 KB | 11.9 ms | 10.6 ms |
|
|
113
|
+
|
|
114
|
+
**Phân tích kết quả**
|
|
115
|
+
|
|
116
|
+
- **Gánh nặng runtime**: Phần lõi của `i18next` kết hợp cùng `react-i18next` là runtime nặng nhất được ghi nhận: chiếm **19.7 KB gzip** cho một component rỗng, so với chỉ 5.5 KB của `next-intlayer`.
|
|
117
|
+
- **Thiết lập cơ bản rất tốn kém**: Đặt `resources` trực tiếp vào `init()` tạo ra kích thước **218.5 KB mỗi trang** (+77.5 KB so với ứng dụng gốc không i18n). Từng trang bắt buộc phải tải về toàn bộ các namespace.
|
|
118
|
+
- **Tối ưu hóa thủ công đòi hỏi nhiều công sức**: Chuyển sang dùng backend (`dynamic`) giảm được 49 KB nhưng **vẫn rò rỉ 90% chuỗi thuộc các trang khác**, và một nửa chuỗi tải về thuộc ngôn ngữ không dùng đến. Phải bổ sung cấu hình chia nhỏ namespace cho từng route (`scoped-dynamic`) mới triệt tiêu được rò rỉ ở mức **163.4 KB**, nhưng vẫn **nặng hơn +22.4 KB mỗi trang** so với Intlayer (141.3 KB) vốn không cần cấu hình phức tạp.
|
|
119
|
+
- **Kích thước từng component**: Một component gọi `useTranslation()` được đóng gói trong khoảng 26 đến 79 KB; trong khi component tương đương dùng `useIntlayer()` chỉ nặng 6.9 KB.
|
|
120
|
+
- **Độ trễ khi hydrate**: Thời gian hydrate tăng vọt lên 27.7 ms ở cấu hình `dynamic` do thực thể i18next cần khởi tạo và nạp backend tại client trước khi React có thể hoàn tất quá trình hydrate.
|
|
121
|
+
|
|
122
|
+
### Kết quả trên TanStack Start (`react-i18next`)
|
|
123
|
+
|
|
124
|
+
Cùng ứng dụng kiểm thử trên nền tảng TanStack Start sử dụng trực tiếp `react-i18next` nhằm loại bỏ các yếu tố can thiệp riêng của Next.js:
|
|
125
|
+
|
|
126
|
+
| Thư viện | Chiến lược | Dung lượng Lib (gz) | JS TB mỗi trang (gz) | Rò rỉ ngôn ngữ | Rò rỉ trang | Kích thước TB Comp (gz) | Phản hồi E2E | Thời gian Hydrate |
|
|
127
|
+
| --------------------- | -------------- | ------------------: | -------------------: | -------------: | ----------: | ----------------------: | -----------: | ----------------: |
|
|
128
|
+
| **base** (không i18n) | - | 0.0 KB | 111.0 KB | 0.0% | 0.0% | 0.7 KB | 8.1 ms | 21.6 ms |
|
|
129
|
+
| `react-i18next` | static | 18.4 KB | 180.3 KB | 50.0% | 89.8% | 24.3 KB | 12.9 ms | 85.1 ms |
|
|
130
|
+
| `react-i18next` | dynamic | 18.4 KB | 136.4 KB | 23.1% | 89.8% | 24.8 KB | 123.1 ms | 32.9 ms |
|
|
131
|
+
| `react-i18next` | scoped-static | 18.4 KB | 184.2 KB | 50.7% | 89.8% | 25.3 KB | 185.1 ms | 25.2 ms |
|
|
132
|
+
| `react-i18next` | scoped-dynamic | 18.4 KB | 127.2 KB | 0.0% | 0.0% | 26.7 KB | 17.6 ms | 11.3 ms |
|
|
133
|
+
| **`intlayer`** | static | **5.0 KB** | **125.8 KB** | 50.0% | **0.0%** | **8.1 KB** | **3.2 ms** | 11.5 ms |
|
|
134
|
+
| **`intlayer`** | dynamic | **5.0 KB** | **118.6 KB** | **0.0%** | **0.0%** | **6.3 KB** | **3.6 ms** | 14.1 ms |
|
|
135
|
+
|
|
136
|
+
**Phân tích kết quả**
|
|
137
|
+
|
|
138
|
+
- Ứng dụng `react-i18next` cơ bản tải về **nhiều hơn +69 KB mỗi trang** so với bản không có i18n, và quá trình hydrate kéo dài tới **85 ms** (gấp 4 lần chuẩn) do toàn bộ cây dữ liệu dịch thuật phải được xử lý và đăng ký trên client trước lần render đầu tiên.
|
|
139
|
+
- **Độ trễ mạng khi đổi ngôn ngữ**: Khi nạp tài nguyên theo yêu cầu qua backend, việc chuyển đổi ngôn ngữ phải chờ phản hồi mạng trước khi thẻ `html[lang]` kịp cập nhật: **123 ms** ở `dynamic` và **185 ms** ở `scoped-static`. Trong khi đó, Intlayer cập nhật DOM chỉ trong **3-4 ms** ở cả hai chế độ mà không bao giờ bị nghẽn mạng.
|
|
140
|
+
- Cấu hình tối ưu cao `scoped-dynamic` đạt mức 127.2 KB, vẫn **nặng hơn +8.6 KB** so với cấu hình `dynamic` của Intlayer, dù đã phải tốn rất nhiều công sức tạo ánh xạ route-namespace, backend và các biên Suspense.
|
|
141
|
+
- Chế độ `static` của Intlayer đã mặc định đạt **0% rò rỉ trang** vì nó chỉ đóng gói các từ điển được import bởi component của trang đó. Bật `importMode: 'dynamic'` sẽ triệt tiêu hoàn toàn rò rỉ ngôn ngữ.
|
|
142
|
+
- **Kích thước component**: 24-27 KB ở `react-i18next` so với 6-8 KB ở Intlayer. `useTranslation()` luôn gắn chặt từng component với instance i18next toàn cục.
|
|
143
|
+
|
|
144
|
+
## Nguyên nhân của sự chênh lệch: Global Instance vs Từ điển biên dịch
|
|
145
|
+
|
|
146
|
+
`i18next` được xây dựng từ năm 2012 theo hướng runtime: một instance toàn cục nắm giữ kho tài nguyên, các plugin mở rộng nó và hàm `t()` tìm khóa khi render. Thiết kế này đem lại tính linh hoạt cao nhưng tạo ra gánh nặng lớn về dung lượng:
|
|
147
|
+
|
|
148
|
+
```bash
|
|
149
|
+
.
|
|
150
|
+
├── i18n.ts # createInstance().use(...).use(...).init({...})
|
|
151
|
+
└── src
|
|
152
|
+
├── locales
|
|
153
|
+
│ ├── en
|
|
154
|
+
│ │ ├── common.json
|
|
155
|
+
│ │ ├── home.json
|
|
156
|
+
│ │ └── about.json
|
|
157
|
+
│ └── fr
|
|
158
|
+
│ ├── common.json
|
|
159
|
+
│ ├── home.json
|
|
160
|
+
│ └── about.json
|
|
161
|
+
├── components
|
|
162
|
+
│ └── Counter.tsx # useTranslation("about") + t("counter.label")
|
|
163
|
+
└── app
|
|
164
|
+
└── [locale]
|
|
165
|
+
└── about
|
|
166
|
+
└── page.tsx # phải tự biết rằng trang này cần ["common", "about"]
|
|
167
|
+
```
|
|
168
|
+
|
|
169
|
+
Instance toàn cục không thể biết trước component sẽ gọi những khóa nào; vì vậy nó buộc phải lưu trữ toàn bộ các namespace được chỉ định nạp. Muốn tối ưu, **bạn** phải chia nhỏ danh mục, **bạn** phải liệt kê các namespace cần thiết cho từng trang, và **bạn** phải duy trì danh sách này khi component di chuyển. Đúng như [ghi chú benchmark](https://github.com/intlayer-org/benchmark-bloom/blob/main/report/NOTE.md) đã chỉ ra: "Vừa duy trì an toàn kiểu dữ liệu vừa quản lý đúng namespace cho từng trang thực sự là một cơn ác mộng".
|
|
170
|
+
|
|
171
|
+
Intlayer loại bỏ hoàn toàn instance toàn cục. Nội dung được khai báo ngay cạnh component và trình biên dịch sẽ giải quyết cây phụ thuộc vào lúc build:
|
|
172
|
+
|
|
173
|
+
```bash
|
|
174
|
+
.
|
|
175
|
+
├── intlayer.config.ts
|
|
176
|
+
└── src
|
|
177
|
+
├── components
|
|
178
|
+
│ └── Counter
|
|
179
|
+
│ ├── index.tsx # useIntlayer("counter")
|
|
180
|
+
│ └── index.content.ts
|
|
181
|
+
└── app
|
|
182
|
+
└── [locale]
|
|
183
|
+
└── about
|
|
184
|
+
├── page.tsx
|
|
185
|
+
└── page.content.ts
|
|
186
|
+
```
|
|
187
|
+
|
|
188
|
+
`@intlayer/swc` / `@intlayer/babel` biết chính xác component nào cần từ điển nào, chỉ đóng gói đúng phần đó cho ngôn ngữ đang kích hoạt và loại bỏ nội dung thừa. Mô hình "scoped-dynamic" trở thành kết quả mặc định của quá trình build mà nhóm phát triển không phải bận tâm quản lý thủ công.
|
|
189
|
+
|
|
190
|
+
> Để đạt được các thông số của dòng `dynamic`, bạn chỉ cần khai báo `dictionary.importMode: 'dynamic'` trong `intlayer.config.ts`. Chi tiết xem thêm tại [tài liệu tối ưu bundle](https://intlayer.org/vi/doc/concept/bundle-optimization).
|
|
191
|
+
|
|
192
|
+
## Trải nghiệm lập trình viên (DX)
|
|
193
|
+
|
|
194
|
+
### Khởi tạo cấu hình
|
|
195
|
+
|
|
196
|
+
**next-i18next (App Router)**
|
|
197
|
+
|
|
198
|
+
```ts fileName="src/app/i18n/server.ts"
|
|
199
|
+
import { createInstance } from "i18next";
|
|
200
|
+
import { initReactI18next } from "react-i18next/initReactI18next";
|
|
201
|
+
import resourcesToBackend from "i18next-resources-to-backend";
|
|
202
|
+
import { defaultLocale } from "@/i18n.config";
|
|
203
|
+
|
|
204
|
+
const backend = resourcesToBackend(
|
|
205
|
+
(locale: string, namespace: string) =>
|
|
206
|
+
import(`../../locales/${locale}/${namespace}.json`)
|
|
207
|
+
);
|
|
208
|
+
|
|
209
|
+
export const initI18next = async (
|
|
210
|
+
locale: string,
|
|
211
|
+
namespaces: string[] = ["common"]
|
|
212
|
+
) => {
|
|
213
|
+
const i18n = createInstance();
|
|
214
|
+
await i18n
|
|
215
|
+
.use(initReactI18next)
|
|
216
|
+
.use(backend)
|
|
217
|
+
.init({
|
|
218
|
+
lng: locale,
|
|
219
|
+
fallbackLng: defaultLocale,
|
|
220
|
+
ns: namespaces,
|
|
221
|
+
defaultNS: "common",
|
|
222
|
+
interpolation: { escapeValue: false },
|
|
223
|
+
react: { useSuspense: false },
|
|
224
|
+
});
|
|
225
|
+
return i18n;
|
|
226
|
+
};
|
|
227
|
+
```
|
|
228
|
+
|
|
229
|
+
Bên cạnh đó, bạn phải viết thêm `I18nProvider` ở phía client, khai báo `generateStaticParams` và quản lý mảng `namespaces` trên từng trang.
|
|
230
|
+
|
|
231
|
+
**Intlayer**
|
|
232
|
+
|
|
233
|
+
```ts fileName="intlayer.config.ts"
|
|
234
|
+
import { type IntlayerConfig, Locales } from "intlayer";
|
|
235
|
+
|
|
236
|
+
const config: IntlayerConfig = {
|
|
237
|
+
internationalization: {
|
|
238
|
+
locales: [Locales.ENGLISH, Locales.FRENCH],
|
|
239
|
+
defaultLocale: Locales.ENGLISH,
|
|
240
|
+
},
|
|
241
|
+
};
|
|
242
|
+
|
|
243
|
+
export default config;
|
|
244
|
+
```
|
|
245
|
+
|
|
246
|
+
```tsx fileName="src/app/[locale]/layout.tsx"
|
|
247
|
+
import { getHTMLTextDir } from "intlayer";
|
|
248
|
+
import { IntlayerClientProvider, type NextLayoutIntlayer } from "next-intlayer";
|
|
249
|
+
|
|
250
|
+
const LocaleLayout: NextLayoutIntlayer = async ({ children, params }) => {
|
|
251
|
+
const { locale } = await params;
|
|
252
|
+
|
|
253
|
+
return (
|
|
254
|
+
<html lang={locale} dir={getHTMLTextDir(locale)}>
|
|
255
|
+
<body>
|
|
256
|
+
<IntlayerClientProvider locale={locale}>
|
|
257
|
+
{children}
|
|
258
|
+
</IntlayerClientProvider>
|
|
259
|
+
</body>
|
|
260
|
+
</html>
|
|
261
|
+
);
|
|
262
|
+
};
|
|
263
|
+
|
|
264
|
+
export default LocaleLayout;
|
|
265
|
+
```
|
|
266
|
+
|
|
267
|
+
### Component phía Client
|
|
268
|
+
|
|
269
|
+
**react-i18next**
|
|
270
|
+
|
|
271
|
+
```json fileName="src/locales/en/about.json"
|
|
272
|
+
{
|
|
273
|
+
"counter": {
|
|
274
|
+
"label": "Counter",
|
|
275
|
+
"increment": "Increment"
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
```
|
|
279
|
+
|
|
280
|
+
```tsx fileName="src/components/Counter.tsx"
|
|
281
|
+
"use client";
|
|
282
|
+
|
|
283
|
+
import { useState } from "react";
|
|
284
|
+
import { useTranslation } from "react-i18next";
|
|
285
|
+
|
|
286
|
+
export const Counter = () => {
|
|
287
|
+
const { t, i18n } = useTranslation("about");
|
|
288
|
+
const [count, setCount] = useState(0);
|
|
289
|
+
const numberFormat = new Intl.NumberFormat(i18n.language);
|
|
290
|
+
|
|
291
|
+
return (
|
|
292
|
+
<div>
|
|
293
|
+
<p>{numberFormat.format(count)}</p>
|
|
294
|
+
<button
|
|
295
|
+
aria-label={t("counter.label")}
|
|
296
|
+
onClick={() => setCount((c) => c + 1)}
|
|
297
|
+
>
|
|
298
|
+
{t("counter.increment")}
|
|
299
|
+
</button>
|
|
300
|
+
</div>
|
|
301
|
+
);
|
|
302
|
+
};
|
|
303
|
+
```
|
|
304
|
+
|
|
305
|
+
> Trang hiển thị component này bắt buộc phải nạp namespace `about`, và `t("counter.label")` sẽ chỉ là chuỗi thông thường nếu chưa mở rộng `CustomTypeOptions`.
|
|
306
|
+
|
|
307
|
+
**Intlayer**
|
|
308
|
+
|
|
309
|
+
```ts fileName="src/components/Counter/index.content.ts"
|
|
310
|
+
import { t, type Dictionary } from "intlayer";
|
|
311
|
+
|
|
312
|
+
const counterContent = {
|
|
313
|
+
key: "counter",
|
|
314
|
+
content: {
|
|
315
|
+
label: t({ en: "Counter", fr: "Compteur" }),
|
|
316
|
+
increment: t({ en: "Increment", fr: "Incrémenter" }),
|
|
317
|
+
},
|
|
318
|
+
} satisfies Dictionary;
|
|
319
|
+
|
|
320
|
+
export default counterContent;
|
|
321
|
+
```
|
|
322
|
+
|
|
323
|
+
```tsx fileName="src/components/Counter/index.tsx"
|
|
324
|
+
"use client";
|
|
325
|
+
|
|
326
|
+
import { useState } from "react";
|
|
327
|
+
import { useIntlayer } from "next-intlayer";
|
|
328
|
+
import { useNumber } from "next-intlayer/format";
|
|
329
|
+
|
|
330
|
+
export const Counter = () => {
|
|
331
|
+
const { label, increment } = useIntlayer("counter");
|
|
332
|
+
const number = useNumber();
|
|
333
|
+
const [count, setCount] = useState(0);
|
|
334
|
+
|
|
335
|
+
return (
|
|
336
|
+
<div>
|
|
337
|
+
<p>{number(count)}</p>
|
|
338
|
+
<button aria-label={label} onClick={() => setCount((c) => c + 1)}>
|
|
339
|
+
{increment}
|
|
340
|
+
</button>
|
|
341
|
+
</div>
|
|
342
|
+
);
|
|
343
|
+
};
|
|
344
|
+
```
|
|
345
|
+
|
|
346
|
+
`label` và `increment` đều được kiểm tra kiểu dữ liệu nghiêm ngặt; gõ sai tên sẽ báo lỗi TypeScript ngay lập tức, và nếu thiếu bản dịch tiếng Pháp thì quá trình build sẽ bị dừng lại.
|
|
347
|
+
|
|
348
|
+
### Component phía Server đồng bộ
|
|
349
|
+
|
|
350
|
+
**next-i18next**
|
|
351
|
+
|
|
352
|
+
```tsx fileName="src/components/ServerCounter.tsx"
|
|
353
|
+
type ServerCounterProps = {
|
|
354
|
+
t: (key: string) => string;
|
|
355
|
+
locale: string;
|
|
356
|
+
count: number;
|
|
357
|
+
};
|
|
358
|
+
|
|
359
|
+
export const ServerCounter = ({ t, locale, count }: ServerCounterProps) => (
|
|
360
|
+
<div>
|
|
361
|
+
<p>{new Intl.NumberFormat(locale).format(count)}</p>
|
|
362
|
+
<button aria-label={t("counter.label")}>{t("counter.increment")}</button>
|
|
363
|
+
</div>
|
|
364
|
+
);
|
|
365
|
+
```
|
|
366
|
+
|
|
367
|
+
Trang cha phải gọi `i18n.getFixedT(locale, "about")` rồi truyền `t` và `locale` xuống dưới dạng props.
|
|
368
|
+
|
|
369
|
+
**Intlayer**
|
|
370
|
+
|
|
371
|
+
```tsx fileName="src/components/ServerCounter.tsx"
|
|
372
|
+
import { useIntlayer } from "next-intlayer/server";
|
|
373
|
+
import { useNumber } from "next-intlayer/server/format";
|
|
374
|
+
|
|
375
|
+
export const ServerCounter = ({ count }: { count: number }) => {
|
|
376
|
+
const { label, increment } = useIntlayer("counter");
|
|
377
|
+
const number = useNumber();
|
|
378
|
+
|
|
379
|
+
return (
|
|
380
|
+
<div>
|
|
381
|
+
<p>{number(count)}</p>
|
|
382
|
+
<button aria-label={label}>{increment}</button>
|
|
383
|
+
</div>
|
|
384
|
+
);
|
|
385
|
+
};
|
|
386
|
+
```
|
|
387
|
+
|
|
388
|
+
## Giữ nguyên API của i18next, nhận ngay hiệu năng của Intlayer
|
|
389
|
+
|
|
390
|
+
Bạn không cần phải viết lại toàn bộ component để đạt được kết quả benchmark trên. `@intlayer/i18next`, `@intlayer/react-i18next` và `@intlayer/next-i18next` đóng vai trò là các adapter tương thích trực tiếp: các lệnh gọi `useTranslation`, `t()`, `<Trans>`, xử lý số nhiều và ngữ cảnh vẫn hoạt động bình thường, được vận hành bởi các từ điển do trình biên dịch Intlayer cung cấp.
|
|
391
|
+
|
|
392
|
+
```ts fileName="next.config.ts"
|
|
393
|
+
import type { NextConfig } from "next";
|
|
394
|
+
import { createNextI18nPlugin } from "@intlayer/next-i18next/plugin";
|
|
395
|
+
|
|
396
|
+
const withIntlayer = createNextI18nPlugin();
|
|
397
|
+
|
|
398
|
+
const nextConfig: NextConfig = {};
|
|
399
|
+
|
|
400
|
+
export default withIntlayer(nextConfig);
|
|
401
|
+
```
|
|
402
|
+
|
|
403
|
+
```ts fileName="vite.config.ts"
|
|
404
|
+
import { defineConfig } from "vite";
|
|
405
|
+
import { reactI18nextVitePlugin } from "@intlayer/react-i18next/plugin";
|
|
406
|
+
|
|
407
|
+
export default defineConfig({
|
|
408
|
+
plugins: [reactI18nextVitePlugin()],
|
|
409
|
+
});
|
|
410
|
+
```
|
|
411
|
+
|
|
412
|
+
Trong bài đo kiểm, bản build tương thích của cùng ứng dụng Next.js đã giảm từ **218.5 KB xuống 150.7 KB** mỗi trang, từ **78.5 KB xuống 9.7 KB** mỗi component, tỷ lệ rò rỉ giảm từ **~90% về 0%**, và thời gian hydrate rút ngắn từ 15.6 ms xuống 11.3 ms mà không cần sửa bất kỳ dòng mã nghiệp vụ nào. Các tệp `locales/{lng}/{ns}.json` hiện tại vẫn có thể được giữ làm nguồn dữ liệu chính thông qua plugin đồng bộ JSON.
|
|
413
|
+
|
|
414
|
+
Xem hướng dẫn chuyển đổi: [i18next](https://intlayer.org/vi/doc/migration/i18next), [react-i18next](https://intlayer.org/vi/doc/migration/react-i18next), [next-i18next](https://intlayer.org/vi/doc/migration/next-i18next).
|
|
415
|
+
|
|
416
|
+
## Khi nào nên chọn giải pháp nào?
|
|
417
|
+
|
|
418
|
+
- **Chọn i18next**: Nếu bạn phụ thuộc chặt chẽ vào hệ sinh thái plugin (bộ nhận diện đặc thù, backend chuyên biệt, ICU, Locize), cần bản địa hóa ở cả ngoài React (Node services, vanilla JS, các framework khác), đội ngũ của bạn đã rất thành thạo, hoặc nền tảng dịch thuật bắt buộc định dạng `locales/{lng}/{ns}.json`. Hãy dành thời gian để quản lý namespace và bản đồ route nếu hiệu năng là ưu tiên hàng đầu.
|
|
419
|
+
- **Chọn Intlayer**: Nếu bạn muốn **nội dung đặt ngay tại component**, **an toàn kiểu dữ liệu TypeScript nghiêm ngặt**, **báo lỗi thiếu bản dịch khi build**, **tự động tree-shaking và lazy loading không tốn công**, chuyển đổi ngôn ngữ tức thì, hỗ trợ component server đồng bộ và các công cụ biên tập tích hợp sẵn (Visual Editor, CMS, dịch thuật AI, máy chủ MCP). Rất thích hợp cho dự án dạng module lớn và Design Systems.
|
|
420
|
+
- **Chọn adapter `@intlayer/*-i18next`**: Nếu bạn đã có ứng dụng chạy i18next và muốn tối ưu hóa kích thước bundle và tốc độ phản hồi ngay lập tức mà không phải refactor mã nguồn.
|
|
421
|
+
|
|
422
|
+
## Các bài so sánh liên quan
|
|
423
|
+
|
|
424
|
+
- [next-intl vs Intlayer](https://intlayer.org/vi/blog/next-intl-vs-intlayer) (cùng benchmark)
|
|
425
|
+
- [Lingui vs Intlayer](https://intlayer.org/vi/blog/lingui-vs-intlayer) (cùng benchmark)
|
|
426
|
+
- [vue-i18n vs Intlayer benchmark](https://intlayer.org/vi/blog/vue-i18n-vs-intlayer-benchmark) (cùng benchmark)
|
|
427
|
+
- [next-i18next vs next-intl vs Intlayer](https://intlayer.org/vi/blog/next-i18next-vs-next-intl-vs-intlayer)
|
|
428
|
+
- [react-i18next vs react-intl vs Intlayer](https://intlayer.org/vi/blog/react-i18next-vs-react-intl-vs-intlayer)
|
|
429
|
+
- [i18next có bị lỗi thời không?](https://intlayer.org/vi/blog/is-i18next-outdated)
|
|
430
|
+
|
|
431
|
+
## Lượt gắn sao trên GitHub
|
|
432
|
+
|
|
433
|
+
Lượt sao GitHub là thước đo tin cậy về mức độ phổ biến, niềm tin của cộng đồng và tiềm năng phát triển lâu dài. Dù không phản ánh trực tiếp chất lượng mã nguồn, nó cho thấy sự quan tâm và xu hướng đón nhận của cộng đồng phát triển phần mềm.
|
|
434
|
+
|
|
435
|
+
[](https://star-history.com/#i18next/i18next&i18next/react-i18next&i18next/next-i18next&aymericzip/intlayer)
|
|
436
|
+
|
|
437
|
+
## Kết luận
|
|
438
|
+
|
|
439
|
+
`i18next` hoàn toàn xứng đáng với vị thế của mình: hoạt động ở mọi môi trường, có plugin cho mọi bài toán và được duy trì ổn định hơn một thập kỷ qua. Tuy nhiên, benchmark này phản ánh chi phí của kiến trúc phụ thuộc vào runtime. Cách thiết lập thông thường làm tăng thêm **+70-77 KB gzip mỗi trang**, **rò rỉ ~90% dữ liệu của các trang khác**, và mất **hơn 100 ms** để đổi ngôn ngữ khi dùng lazy load. Dù có thể triệt tiêu rò rỉ nhưng đòi hỏi quản lý thủ công phức tạp và vẫn **nặng hơn Intlayer từ 9-22 KB**.
|
|
440
|
+
|
|
441
|
+
Intlayer chuyển toàn bộ gánh nặng này sang trình biên dịch. Từ điển theo component, tải lười theo ngôn ngữ và loại bỏ nội dung thừa đều là kết quả tự động của quá trình build. Trên cùng một ứng dụng: **Chỉ tăng +0.3 KB mỗi trang**, **0% rò rỉ**, component **nhỏ hơn 3-10 lần** và đổi ngôn ngữ chỉ mất **3-4 ms**.
|
|
442
|
+
|
|
443
|
+
Toàn bộ dữ liệu thô, ứng dụng mẫu và kịch bản thử nghiệm đều công khai tại [kho lưu trữ Benchmark Bloom](https://github.com/intlayer-org/benchmark-bloom). Bạn hoàn toàn có thể tự mình kiểm chứng.
|
|
444
|
+
|
|
445
|
+
Tìm hiểu thêm tại tài liệu ['Tại sao chọn Intlayer?'](https://intlayer.org/vi/doc/why).
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
createdAt: 2026-09-02
|
|
3
|
-
updatedAt: 2026-09-
|
|
3
|
+
updatedAt: 2026-09-16
|
|
4
4
|
title: Liệu i18next Đã Lỗi Thời Vào Năm 2026?
|
|
5
5
|
description: i18next đang vận hành hàng triệu trang web, nhưng kiến trúc runtime từ năm 2011 đang bộc lộ giới hạn. Phân tích về dung lượng bundle, hạn chế tree-shaking và tốc độ đổi mới.
|
|
6
6
|
keywords:
|
|
@@ -70,7 +70,7 @@ Hoạt động phát triển trong 12 tháng qua:
|
|
|
70
70
|
| `i18next` core | 2.626 | **259** | Các bản vá nhỏ |
|
|
71
71
|
| Intlayer | 7.156 | **4.343** | Trình biên dịch, công cụ IDE và AI engine |
|
|
72
72
|
|
|
73
|
-
[](https://
|
|
73
|
+
[](https://star-history.com/#i18next/i18next&i18next/react-i18next&i18next/next-i18next&aymericzip/intlayer)
|
|
74
74
|
|
|
75
75
|
Một thư viện trưởng thành mang lại sự an tâm. Tuy nhiên, các tiêu chuẩn của công cụ i18n đã thay đổi: bundler hiện đại loại bỏ nội dung không sử dụng khi build, LLM tự động dịch trên CI, và lập trình viên tận dụng Language Server (LSP) cùng AI agent. Mô hình chỉ dựa vào runtime của i18next gặp khó khăn trong việc đón nhận những tiến bộ này.
|
|
76
76
|
|
|
@@ -125,6 +125,10 @@ Trên Next.js, `next-i18next` thêm vào **76.7 KB gzipped** so với ứng dụ
|
|
|
125
125
|
|
|
126
126
|
Theo mặc định, khoảng **90% văn bản dịch** gửi tới một route thực chất thuộc về các trang khác. Việc phân chia namespace thủ công tốn nhiều công sức và rất dễ phát sinh lỗi sót từ khóa.
|
|
127
127
|
|
|
128
|
+
Biểu đồ dưới đây ước tính dung lượng nội dung cho một ứng dụng giả định gồm 1 đến 10 trang, được dịch sang 1 đến 10 ngôn ngữ, với khoảng 30 KB văn bản mỗi trang. Tải nội dung động theo locale loại bỏ trục ngôn ngữ, giới hạn nội dung theo component hoặc route loại bỏ trục trang, và chỉ khi kết hợp cả hai thì dung lượng mới giữ nguyên.
|
|
129
|
+
|
|
130
|
+

|
|
131
|
+
|
|
128
132
|
**Độ trễ hydration:**
|
|
129
133
|
|
|
130
134
|
Component sử dụng `react-i18next` mất tới **85 ms** để hoàn tất hydration, so với chỉ **24 ms** ở Intlayer. Việc chuyển giao các cây JSON khổng lồ tới component client làm chậm khả năng tương tác ban đầu.
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
createdAt: 2026-09-02
|
|
3
|
-
updatedAt: 2026-09-
|
|
3
|
+
updatedAt: 2026-09-16
|
|
4
4
|
title: Liệu next-intl Đã Lỗi Thời Vào Năm 2026?
|
|
5
5
|
description: next-intl đã trở thành lựa chọn phổ biến cho Next.js App Router. Nhưng nó vẫn mang gánh nặng bundle lúc runtime và yêu cầu quản lý namespace thủ công.
|
|
6
6
|
keywords:
|
|
@@ -66,7 +66,7 @@ Tổng kết một năm qua:
|
|
|
66
66
|
- `amannn/next-intl`: **187 commit** (chủ yếu là cập nhật phụ thuộc và vá lỗi nhỏ).
|
|
67
67
|
- `aymericzip/intlayer`: **4.343 commit** (phát triển tích cực trên trình biên dịch, tiện ích mở rộng IDE, máy chủ MCP và công cụ dịch thuật AI).
|
|
68
68
|
|
|
69
|
-
[](https://
|
|
69
|
+
[](https://star-history.com/#amannn/next-intl&aymericzip/intlayer)
|
|
70
70
|
|
|
71
71
|
Một thư viện đã ổn định mang lại cảm giác an tâm. Tuy nhiên, tiêu chuẩn công cụ i18n đã thay đổi: trình biên dịch loại bỏ văn bản không dùng khi build, LLM dịch tự động trong CI, và lập trình viên được hỗ trợ bởi Language Server (LSP) cùng AI agent. Kiến trúc phụ thuộc hoàn toàn vào runtime khó có thể tận dụng những bước tiến này.
|
|
72
72
|
|
|
@@ -127,6 +127,10 @@ Bởi vì `messages` được đưa vào client provider ở cấp cao nhất, t
|
|
|
127
127
|
|
|
128
128
|
Có thể giảm bớt điều này bằng cách chia nhỏ file JSON thành các namespace. Tuy nhiên, việc tự quản lý ánh xạ này tốn nhiều công sức và rất dễ bỏ sót.
|
|
129
129
|
|
|
130
|
+
Biểu đồ dưới đây ước tính dung lượng nội dung cho một ứng dụng giả định gồm 1 đến 10 trang, được dịch sang 1 đến 10 ngôn ngữ, với khoảng 30 KB văn bản mỗi trang. Tải nội dung động theo locale loại bỏ trục ngôn ngữ, giới hạn nội dung theo component hoặc route loại bỏ trục trang, và chỉ khi kết hợp cả hai thì dung lượng mới giữ nguyên.
|
|
131
|
+
|
|
132
|
+

|
|
133
|
+
|
|
130
134
|
Intlayer giải quyết vấn đề bằng phân tích tĩnh: [trình biên dịch Intlayer](https://intlayer.org/vi/doc/compiler) chỉ đóng gói những nội dung thực sự được gọi trên route đó, đưa tỷ lệ rò rỉ giữa các trang về mức **0.0%**.
|
|
131
135
|
|
|
132
136
|
## Tại Sao next-intl Không Thể Tree-Shaking?
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
createdAt: 2026-09-02
|
|
3
|
-
updatedAt: 2026-09-
|
|
3
|
+
updatedAt: 2026-09-16
|
|
4
4
|
title: Liệu vue-i18n Đã Lỗi Thời Vào Năm 2026?
|
|
5
5
|
description: vue-i18n là chuẩn mực cho Vue và Nuxt suốt cả thập kỷ. Nhưng trong các bài kiểm tra benchmark, nó lại là runtime i18n nặng nhất trên web. Tìm hiểu nguyên nhân tại đây.
|
|
6
6
|
keywords:
|
|
@@ -64,7 +64,7 @@ Số liệu 12 tháng qua:
|
|
|
64
64
|
- `intlify/vue-i18n`: **259 commit** (bảo trì định kỳ cho Vue 3 và Nuxt).
|
|
65
65
|
- `aymericzip/intlayer`: **4.343 commit** (liên tục cải tiến trình biên dịch, công cụ LSP và tích hợp AI agent).
|
|
66
66
|
|
|
67
|
-
[](https://
|
|
67
|
+
[](https://star-history.com/#intlify/vue-i18n&aymericzip/intlayer)
|
|
68
68
|
|
|
69
69
|
Một thư viện lâu năm luôn có tính ổn định cao. Tuy nhiên, lập trình web ngày nay dựa trên phân tích AST khi build, loại bỏ mã không dùng và dịch tự động bằng AI. Một hệ thống phụ thuộc vào việc thực thi trên trình duyệt khó lòng áp dụng hiệu quả các tiện ích này.
|
|
70
70
|
|
|
@@ -116,6 +116,12 @@ Theo mặc định, **90% dữ liệu dịch** được gửi tới một route
|
|
|
116
116
|
|
|
117
117
|
Các component có phạm vi dịch cục bộ đạt kích thước trung bình 196 KB ở `vue-i18n` do trùng lặp từ điển, so với chỉ **6.5 KB** khi dùng Intlayer.
|
|
118
118
|
|
|
119
|
+
**Rò rỉ tăng như thế nào:**
|
|
120
|
+
|
|
121
|
+
Biểu đồ dưới đây ước tính dung lượng nội dung cho một ứng dụng giả định gồm 1 đến 10 trang, được dịch sang 1 đến 10 ngôn ngữ, với khoảng 30 KB văn bản mỗi trang. Tải nội dung động theo locale loại bỏ trục ngôn ngữ, giới hạn nội dung theo component hoặc route loại bỏ trục trang, và chỉ khi kết hợp cả hai thì dung lượng mới giữ nguyên.
|
|
122
|
+
|
|
123
|
+

|
|
124
|
+
|
|
119
125
|
## Tại Sao vue-i18n Lại Nặng?
|
|
120
126
|
|
|
121
127
|
### Trình Biên Dịch AST Bị Gửi Xuống Trình Duyệt
|