@intlayer/docs 7.3.3 → 7.3.5

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.
@@ -2,7 +2,7 @@
2
2
  createdAt: 2025-11-24
3
3
  updatedAt: 2025-11-24
4
4
  title: Compilador vs. i18n Declarativo
5
- description: Explorando los compromisos arquitectónicos entre la internacionalización "mágica" basada en compiladores y la gestión explícita y declarativa de contenido.
5
+ description: Explorando las compensaciones arquitectónicas entre la internacionalización "mágica" basada en compilador y la gestión explícita y declarativa de contenido.
6
6
  keywords:
7
7
  - Intlayer
8
8
  - Internacionalización
@@ -18,35 +18,67 @@ slugs:
18
18
  - compiler-vs-declarative-i18n
19
19
  ---
20
20
 
21
- # El Caso a Favor y en Contra de la i18n Basada en Compiladores
21
+ # Argumentos a favor y en contra de la i18n basada en compilador
22
22
 
23
23
  Si has estado desarrollando aplicaciones web por más de una década, sabes que la Internacionalización (i18n) siempre ha sido un punto de fricción. A menudo es la tarea que nadie quiere hacer: extraer cadenas, gestionar archivos JSON y preocuparse por las reglas de pluralización.
24
24
 
25
- Recientemente, ha surgido una nueva ola de herramientas de i18n "basadas en compiladores", que prometen hacer desaparecer este dolor. La propuesta es seductora: **Simplemente escribe texto en tus componentes y deja que la herramienta de compilación se encargue del resto.** Sin claves, sin importaciones, solo magia.
25
+ Recientemente, ha surgido una nueva ola de herramientas de i18n **"basadas en compilador"**, que prometen hacer desaparecer este dolor. La propuesta es seductora: **Simplemente escribe texto en tus componentes y deja que la herramienta de compilación se encargue del resto.** Sin claves, sin importaciones, solo magia.
26
26
 
27
27
  Pero como con todas las abstracciones en la ingeniería de software, la magia tiene un precio.
28
28
 
29
- En esta publicación del blog, exploraremos el cambio de bibliotecas declarativas a enfoques basados en compiladores, las deudas arquitectónicas ocultas que introducen y por qué la forma "aburrida" podría seguir siendo la mejor para aplicaciones profesionales.
29
+ En esta publicación del blog, exploraremos el cambio de las bibliotecas declarativas a los enfoques basados en compiladores, las deudas arquitectónicas ocultas que introducen y por qué la forma "aburrida" podría seguir siendo la mejor para aplicaciones profesionales.
30
30
 
31
- ## Una Breve Historia de la Traducción
31
+ ## Tabla de contenidos
32
32
 
33
- Para entender dónde estamos, tenemos que mirar hacia atrás y ver dónde empezamos.
33
+ <TOC/>
34
34
 
35
- Alrededor de 2011–2012, el panorama de JavaScript era muy diferente. Los bundlers tal como los conocemos (Webpack, Vite) no existían o estaban en sus inicios. Estábamos pegando scripts directamente en el navegador. En esta era, nacieron bibliotecas como **i18next**.
35
+ ## Una breve historia de la internacionalización
36
36
 
37
- Resolvieron el problema de la única manera posible en ese momento: **Diccionarios en tiempo de ejecución**. Cargabas un objeto JSON masivo en memoria, y una función buscaba las claves al vuelo. Era confiable, explícito y funcionaba en todas partes.
37
+ Para entender dónde estamos, debemos mirar hacia atrás y ver dónde comenzamos.
38
38
 
39
- Avanzando hasta hoy. Contamos con compiladores potentes (SWC, bundlers basados en Rust) que pueden analizar Árboles de Sintaxis Abstracta (AST) en milisegundos. Este poder dio origen a una nueva idea: _¿Por qué gestionamos las claves manualmente? ¿Por qué el compilador no puede simplemente ver el texto "Hello World" y reemplazarlo por nosotros?_
39
+ Alrededor de 2011–2012, el panorama de JavaScript era muy diferente. Los bundlers tal como los conocemos (Webpack, Vite) no existían o estaban en sus inicios. Estábamos uniendo scripts directamente en el navegador. En esta época, nacieron bibliotecas como **i18next**.
40
+
41
+ Resolvieron el problema de la única manera posible en ese momento: **Diccionarios en tiempo de ejecución**. Cargabas un objeto JSON enorme en memoria, y una función buscaba las claves sobre la marcha. Era fiable, explícito y funcionaba en todas partes.
42
+
43
+ Avancemos hasta hoy. Contamos con compiladores potentes (SWC, bundlers basados en Rust) que pueden analizar Árboles de Sintaxis Abstracta (AST) en milisegundos. Este poder dio origen a una nueva idea: _¿Por qué gestionamos manualmente las claves? ¿Por qué el compilador no puede simplemente ver el texto "Hello World" y reemplazarlo por nosotros?_
40
44
 
41
45
  Así nació la i18n basada en compiladores.
42
46
 
47
+ > **Ejemplo de i18n basado en compiladores:**
48
+ >
49
+ > - Paraglide (Módulos tree-shaken que compilan cada mensaje en una pequeña función ESM para que los bundlers puedan eliminar automáticamente locales y claves no usadas. Importas los mensajes como funciones en lugar de hacer búsquedas por claves de cadena.)
50
+ > - LinguiJS (Compilador de macro a función que reescribe macros de mensajes como `<Trans>` en llamadas a funciones JS simples en tiempo de compilación. Obtienes sintaxis ICU/MessageFormat con una huella de ejecución muy pequeña.)
51
+ > - Lingo.dev (Se enfoca en automatizar la canalización de localización inyectando contenido traducido directamente durante la compilación de tu aplicación React. Puede generar traducciones automáticamente usando IA e integrarse directamente en CI/CD.)
52
+ > - Wuchale (Preprocesador orientado a Svelte que extrae texto en línea en archivos .svelte y lo compila en funciones de traducción sin envoltorios. Evita las claves de cadena y separa completamente la lógica de extracción de contenido del runtime principal de la aplicación.)
53
+ > - Intlayer (Compilador / CLI de extracción que analiza tus componentes, genera diccionarios tipados y puede opcionalmente reescribir código para usar contenido explícito de Intlayer. El objetivo es usar el compilador para velocidad manteniendo un núcleo declarativo y agnóstico al framework.)
54
+
55
+ > **Ejemplo de i18n declarativo:**
56
+ >
57
+ > - i18next / react-i18next / next-i18next (El estándar maduro de la industria que utiliza diccionarios JSON en tiempo de ejecución y un extenso ecosistema de plugins)
58
+ > - react-intl (Parte de la biblioteca FormatJS, enfocada en la sintaxis estándar de mensajes ICU y un formateo estricto de datos)
59
+ > - next-intl (Optimizado específicamente para Next.js con integración para el App Router y React Server Components)
60
+ > - vue-i18n / @nuxt/i18n (La solución estándar del ecosistema Vue que ofrece bloques de traducción a nivel de componente e integración estrecha con la reactividad)
61
+ > - svelte-i18n (Un envoltorio ligero alrededor de las stores de Svelte para traducciones reactivas en tiempo de ejecución)
62
+ > - angular-translate (La biblioteca heredada de traducción dinámica que se basa en búsquedas de claves en tiempo de ejecución en lugar de la fusión en tiempo de compilación)
63
+ > - angular-i18n (El enfoque nativo de Angular, adelantado en tiempo, que fusiona archivos XLIFF directamente en las plantillas durante la compilación)
64
+ > - Tolgee (Combina código declarativo con un SDK en contexto para edición "click-to-translate" directamente en la interfaz de usuario)
65
+ > - Intlayer (Enfoque por componente, usando archivos de declaraciones de contenido que permiten tree-shaking nativo y validación en TypeScript)
66
+
67
+ ## El Compilador de Intlayer
68
+
69
+ Aunque **Intlayer** es una solución que fundamentalmente fomenta un **enfoque declarativo** para tu contenido, incluye un compilador para ayudar a acelerar el desarrollo o facilitar la creación rápida de prototipos.
70
+
71
+ El compilador de Intlayer recorre el AST (Árbol de Sintaxis Abstracta) de tus componentes React, Vue o Svelte, así como otros archivos JavaScript/TypeScript. Su función es detectar cadenas de texto codificadas directamente y extraerlas en declaraciones dedicadas `.content`.
72
+
73
+ > Para más detalles, consulta la documentación: [Documentación del Compilador Intlayer](https://github.com/aymericzip/intlayer/blob/main/docs/docs/es/compiler.md)
74
+
43
75
  ## El Atractivo del Compilador (El Enfoque "Mágico")
44
76
 
45
77
  Hay una razón por la cual este nuevo enfoque está en tendencia. Para un desarrollador, la experiencia se siente increíble.
46
78
 
47
- ### 1. Velocidad y "Flujo"
79
+ ### 1. Velocidad y "Flow"
48
80
 
49
- Cuando estás concentrado, detenerte a pensar en un nombre de variable (`home_hero_title_v2`) rompe tu flujo. Con un enfoque basado en compilador, escribes `<p>Welcome back</p>` y sigues adelante. La fricción es cero.
81
+ Cuando estás en la zona, detenerte a pensar en un nombre de variable semántico (`home_hero_title_v2`) rompe tu flujo. Con un enfoque de compilador, escribes `<p>Welcome back</p>` y sigues adelante. La fricción es cero.
50
82
 
51
83
  ### 2. La Misión de Rescate del Legado
52
84
 
@@ -59,79 +91,130 @@ Este es un beneficio moderno que no deberíamos pasar por alto. Los asistentes d
59
91
  - **Declarativo:** Tienes que reescribir la salida de la IA para reemplazar el texto con claves.
60
92
  - **Compilador:** Copias y pegas el código de la IA, y simplemente funciona.
61
93
 
62
- ## La Verificación de la Realidad: Por Qué la "Magia" es Peligrosa
94
+ ## La Verificación de la Realidad: Por qué la "Magia" es Peligrosa
63
95
 
64
96
  Aunque la "magia" es atractiva, la abstracción tiene fugas. Confiar en una herramienta de compilación para entender la intención humana introduce fragilidad arquitectónica.
65
97
 
66
- ### 1. Fragilidad Heurística (El Juego de Adivinar)
98
+ ### Fragilidad Heurística (El Juego de Adivinar)
99
+
100
+ El compilador tiene que adivinar qué es contenido y qué es código. Esto conduce a casos límite donde terminas "luchando" contra la herramienta.
101
+
102
+ Considera estos escenarios:
103
+
104
+ - ¿Se extrae `<span className="active"></span>`? (Es una cadena, pero probablemente una clase).
105
+ - ¿Se extrae `<span status="pending"></span>`? (Es un valor de prop).
106
+ - ¿Se extrae `<span>{"Hello World"}</span>`? (Es una expresión JS).
107
+ - ¿Se extrae `<span>Hello {name}. How are you?</span>`? (La interpolación es compleja).
108
+ - ¿Se extrae `<span aria-label="Image of cat"></span>`? (Los atributos de accesibilidad necesitan traducción).
109
+ - ¿Se extrae `<span data-testid="my-element"></span>`? (Los IDs de prueba NO deben traducirse).
110
+ - ¿Se extrae `<MyComponent errorMessage="An error occurred" />`?
111
+ - ¿Se extrae `<p>This is a paragraph{" "}\n containing multiple lines</p>`?
112
+ - ¿Se extrae el resultado de la función `<p>{getStatusMessage()}</p>`?
113
+ - ¿Se extrae `<div>{isLoading ? "The page is loading" : <MyComponent/>} </div>`?
114
+ - ¿Se extrae un ID de producto como `<span>AX-99</span>`?
115
+
116
+ Inevitablemente terminas agregando comentarios específicos (como `// ignore-translation`, o props específicos como `data-compiler-ignore="true"`) para evitar que rompa la lógica de tu aplicación.
117
+
118
+ ### ¿Cómo maneja Intlayer esta complejidad?
119
+
120
+ Intlayer utiliza un enfoque mixto para detectar si un campo debe ser extraído para traducción, intentando minimizar los falsos positivos:
121
+
122
+ 1. **Análisis AST:** Verifica el tipo de elemento (por ejemplo, distinguiendo entre un `reactNode`, una `label` o una propiedad `title`).
123
+ 2. **Reconocimiento de patrones:** Detecta si la cadena está en mayúscula o incluye espacios, lo que sugiere que probablemente sea texto legible por humanos en lugar de un identificador de código.
67
124
 
68
- El compilador tiene que adivinar qué es contenido y qué es código.
125
+ ### El límite estricto de datos dinámicos
69
126
 
70
- - ¿Se traduce `className="active"`? Es una cadena.
71
- - ¿Se traduce `status="pending"`?
72
- - ¿Se traduce `<MyComponent errorMessage="An error occurred" />`?
73
- - ¿Se traduce un ID de producto como `"AX-99"`?
127
+ La extracción del compilador se basa en el **análisis estático**. Debe ver la cadena literal en tu código para generar un ID estable.
128
+ Si tu API devuelve una cadena de código de error como `server_error`, no puedes traducirla con un compilador porque el compilador no sabe que esa cadena existe en tiempo de compilación. Estás obligado a construir un sistema secundario "solo en tiempo de ejecución" únicamente para datos dinámicos.
74
129
 
75
- Inevitablemente terminas "peleando" con el compilador, añadiendo comentarios específicos (como `// ignore-translation`) para evitar que rompa la lógica de tu aplicación.
130
+ ### Falta de segmentación (chunking)
76
131
 
77
- ### 2. El Límite Rígido de los Datos Dinámicos
132
+ Ciertos compiladores no segmentan las traducciones por página. Si tu compilador genera un archivo JSON grande por idioma (por ejemplo, `./lang/en.json`, `./lang/fr.json`, etc.), probablemente terminarás cargando contenido de todas tus páginas para una sola página visitada. Además, cada componente que use tu contenido probablemente será hidratado con mucho más contenido del necesario, lo que puede causar problemas de rendimiento.
78
133
 
79
- La extracción del compilador se basa en **análisis estático**. Debe ver la cadena literal en tu código para generar un ID estable.
80
- Si tu API devuelve un código de error como `server_error`, no puedes traducirlo con un compilador porque este no sabe que esa cadena existe en tiempo de compilación. Te ves obligado a construir un sistema secundario "solo en tiempo de ejecución" solo para datos dinámicos.
134
+ También tenga cuidado al cargar sus traducciones dinámicamente. Si esto no se hace, cargará contenido para todos los idiomas además del actual.
81
135
 
82
- ### 3. "Explosión de Chunks" y Cascadas en la Red
136
+ > Para ilustrar el problema, considere un sitio con 10 páginas y 10 idiomas (todos 100% únicos). Cargaría contenido para 99 páginas adicionales (10 × 10 - 1).
83
137
 
84
- Para permitir el tree-shaking, las herramientas del compilador a menudo dividen las traducciones por componente.
138
+ ### "Explosión de chunks" y cascadas de red
85
139
 
86
- - **La consecuencia:** Una vista de página única con 50 componentes pequeños podría desencadenar **50 solicitudes HTTP separadas** para pequeños fragmentos de traducción. Incluso con HTTP/2, esto crea una cascada de red que hace que tu aplicación se sienta lenta en comparación con cargar un único paquete de idioma optimizado.
140
+ Para resolver el problema del chunking, algunas soluciones ofrecen chunking por componente, o incluso por clave. Sin embargo, el problema solo se resuelve parcialmente. El argumento de venta de estas soluciones suele ser decir "Tu contenido está tree-shakeado."
87
141
 
88
- ### 4. Sobrecarga de rendimiento en tiempo de ejecución
142
+ De hecho, si cargas contenido estáticamente, tu solución eliminará el contenido no utilizado, pero aún así terminarás con contenido de todos los idiomas cargado con tu aplicación.
89
143
 
90
- Para hacer que las traducciones sean reactivas (para que se actualicen instantáneamente cuando cambias de idioma), el compilador a menudo inyecta hooks de gestión de estado en _cada_ componente.
144
+ Entonces, ¿por qué no cargarlo dinámicamente? Sí, en ese caso cargarás más contenido del necesario, pero no está exento de compromisos.
91
145
 
92
- - **El costo:** Si renderizas una lista de 5,000 elementos, estás inicializando 5,000 hooks `useState` y `useEffect` únicamente para el texto. Esto consume memoria y ciclos de CPU que las librerías declarativas (que típicamente usan un único proveedor de Context) ahorran.
146
+ Cargar contenido dinámicamente aísla cada fragmento de contenido en su propio chunk, que solo se cargará cuando el componente se renderice. Esto significa que harás una solicitud HTTP por cada bloque de texto. ¿1,000 bloques de texto en tu página? → 1,000 solicitudes HTTP a tus servidores. Y para limitar el daño y optimizar el tiempo de la primera renderización de tu aplicación, necesitarás insertar múltiples límites de Suspense o Skeleton Loaders.
147
+
148
+ > Nota: Incluso con Next.js y SSR, tus componentes aún se hidratarán después de la carga, por lo que las solicitudes HTTP seguirán realizándose.
149
+
150
+ ¿La solución? Adoptar una solución que permita declarar declaraciones de contenido con ámbito, como lo hacen `i18next`, `next-intl` o `intlayer`.
151
+
152
+ > Nota: `i18next` y `next-intl` requieren que gestiones manualmente las importaciones de tus namespaces / mensajes para cada página con el fin de optimizar el tamaño de tu bundle. Deberías usar un analizador de bundles como `rollup-plugin-visualizer` (vite), `@next/bundle-analyzer` (next.js) o `webpack-bundle-analyzer` (React CRA / Angular / etc) para detectar si estás contaminando tu bundle con traducciones no usadas.
153
+
154
+ ### Sobrecarga de Rendimiento en Tiempo de Ejecución
155
+
156
+ Para hacer que las traducciones sean reactivas (de modo que se actualicen instantáneamente cuando cambias de idioma), el compilador a menudo inyecta hooks de gestión de estado en cada componente.
157
+
158
+ - **El costo:** Si renderizas una lista de 5,000 elementos, estarás inicializando 5,000 hooks `useState` y `useEffect` únicamente para el texto. React debe identificar y volver a renderizar los 5,000 consumidores simultáneamente. Esto provoca un bloqueo masivo del "Main Thread", congelando la interfaz durante el cambio. Esto consume memoria y ciclos de CPU que las librerías declarativas (que típicamente usan un único proveedor de Context) ahorran.
159
+
160
+ > Ten en cuenta que el problema es similar para otros frameworks que no sean React.
93
161
 
94
162
  ## La trampa: Vendor Lock-in
95
163
 
96
- Este es, sin duda, el aspecto más peligroso de la i18n basada en compiladores.
164
+ Ten cuidado al elegir una solución i18n que permita la extracción o migración de las claves de traducción.
97
165
 
98
- En una librería declarativa, tu código fuente contiene la intención explícita. posees las claves. Si cambias de librería, solo cambias la importación.
166
+ En el caso de una biblioteca declarativa, tu código fuente contiene explícitamente tu intención de traducción: estas son tus claves, y tú las controlas. Si deseas cambiar de biblioteca, generalmente solo necesitas actualizar la importación.
99
167
 
100
- En un enfoque basado en compiladores, **tu código fuente es solo texto en inglés.** La "lógica de traducción" solo existe dentro de la configuración del plugin de compilación.
101
- Si esa biblioteca deja de mantenerse, o si la superas, quedas atrapado. No puedes "expulsar" fácilmente porque no tienes ninguna clave de traducción en tu código fuente. Tendrías que reescribir manualmente toda tu aplicación para migrar.
168
+ Con un enfoque de compilador, tu código fuente podría ser solo texto en inglés plano, sin rastro de lógica de traducción: todo está oculto en la configuración de la herramienta de construcción. Si ese plugin deja de mantenerse o quieres cambiar de solución, podrías quedarte atascado. No hay una forma fácil de "expulsar": no hay claves utilizables en tu código, y podrías necesitar regenerar todas tus traducciones para una nueva biblioteca.
169
+
170
+ Algunas soluciones también ofrecen servicios de generación de traducciones. ¿No más créditos? No más traducciones.
171
+
172
+ Los compiladores a menudo generan un hash del texto (por ejemplo, `"Hello World"` -> `x7f2a`). Tus archivos de traducción se ven como `{ "x7f2a": "Hola Mundo" }`. La trampa: si cambias de librería, la nueva librería ve `"Hello World"` y busca esa clave. No la encontrará porque tu archivo de traducción está lleno de hashes (`x7f2a`).
173
+
174
+ ### Bloqueo de Plataforma
175
+
176
+ Al elegir un enfoque basado en compilador, te encierras en la plataforma subyacente. Por ejemplo, ciertos compiladores no están disponibles para todos los bundlers (como Vite, Turbopack o Metro). Esto puede dificultar las migraciones futuras y es posible que necesites adoptar múltiples soluciones para cubrir todas tus aplicaciones.
102
177
 
103
178
  ## El Otro Lado: Riesgos del Enfoque Declarativo
104
179
 
105
- Para ser justos, la forma declarativa tradicional tampoco es perfecta. Tiene su propio conjunto de "peligros".
180
+ Para ser justos, la forma tradicional declarativa tampoco es perfecta. Tiene su propio conjunto de "peligros ocultos".
106
181
 
107
- 1. **Infierno de Espacios de Nombres:** A menudo tienes que gestionar manualmente qué archivos JSON cargar (`common.json`, `dashboard.json`, `footer.json`). Si olvidas uno, el usuario ve las claves sin procesar.
108
- 2. **Sobre-carga de Datos:** Sin una configuración cuidadosa, es muy fácil cargar accidentalmente _todas_ tus claves de traducción para _todas_ las páginas en la carga inicial, inflando el tamaño de tu paquete.
109
- 3. **Deriva de sincronización:** Es común que las claves permanezcan en el archivo JSON mucho después de que el componente que las usaba haya sido eliminado. Tus archivos de traducción crecen indefinidamente, llenos de "claves zombis".
182
+ 1. **Infierno de Namespaces:** A menudo tienes que gestionar manualmente qué archivos JSON cargar (`common.json`, `dashboard.json`, `footer.json`). Si olvidas uno, el usuario verá las claves sin traducir.
183
+ 2. **Sobrecarga de datos:** Sin una configuración cuidadosa, es muy fácil cargar accidentalmente _todas_ tus claves de traducción para _todas_ las páginas en la carga inicial, lo que hincha el tamaño de tu paquete.
184
+ 3. **Desincronización:** Es común que las claves permanezcan en el archivo JSON mucho después de que el componente que las usaba haya sido eliminado. Tus archivos de traducción crecen indefinidamente, llenos de "claves zombis".
110
185
 
111
186
  ## El punto medio de Intlayer
112
187
 
113
188
  Aquí es donde herramientas como **Intlayer** están intentando innovar. Intlayer entiende que, aunque los compiladores son poderosos, la magia implícita es peligrosa.
114
189
 
115
- Intlayer ofrece un comando único **`transform`**. En lugar de hacer magia solo en el paso oculto de compilación, puede realmente **reescribir el código de tu componente**. Escanea tu texto y lo reemplaza con declaraciones explícitas de contenido en tu base de código.
190
+ Intlayer ofrece un enfoque mixto, que te permite beneficiarte de las ventajas de ambos enfoques: gestión declarativa de contenido, también compatible con su compilador para ahorrar tiempo de desarrollo.
116
191
 
117
- Esto te da lo mejor de ambos mundos:
192
+ E incluso si no usas el compilador de Intlayer, Intlayer ofrece un comando `transform` (también accesible mediante la extensión de VSCode). En lugar de hacer magia en un paso oculto de compilación, puede realmente **reescribir el código de tu componente**. Escanea tu texto y lo reemplaza con declaraciones explícitas de contenido en tu base de código.
193
+
194
+ Esto te ofrece lo mejor de ambos mundos:
118
195
 
119
196
  1. **Granularidad:** Mantienes tus traducciones cerca de tus componentes (mejorando la modularidad y el tree-shaking).
120
197
  2. **Seguridad:** La traducción se convierte en código explícito, no en magia oculta en tiempo de compilación.
121
- 3. **Sin dependencia:** Dado que el código se transforma en una estructura declarativa estándar dentro de tu repositorio, no estás ocultando lógica en un plugin de webpack.
198
+ 3. **Sin dependencia:** Dado que el código se transforma en una estructura declarativa dentro de tu repositorio, puedes fácilmente presionar tab, o usar el copilot de tu IDE, para generar tus declaraciones de contenido, no estás ocultando lógica en un plugin de webpack.
122
199
 
123
200
  ## Conclusión
124
201
 
125
202
  Entonces, ¿cuál deberías elegir?
126
203
 
127
- **Si eres un desarrollador junior, un fundador en solitario o estás construyendo un MVP:**
128
- El enfoque basado en compiladores es una opción válida. Te permite avanzar increíblemente rápido. No necesitas preocuparte por la estructura de archivos o las claves. Simplemente construyes. La deuda técnica es un problema para el "Tú del futuro".
204
+ **Si estás construyendo un MVP, o quieres avanzar rápidamente:**
205
+ El enfoque basado en compilador es una opción válida. Te permite avanzar increíblemente rápido. No necesitas preocuparte por la estructura de archivos o las claves. Simplemente construyes. La deuda técnica es un problema para el "Tú del futuro".
206
+
207
+ **Si eres un desarrollador junior, o no te importa la optimización:**
208
+ Si quieres la menor gestión manual, probablemente el enfoque basado en compilador sea el mejor. No necesitarás manejar claves o archivos de traducción tú mismo; solo escribe texto y el compilador automatiza el resto. Esto reduce el esfuerzo de configuración y los errores comunes de i18n ligados a pasos manuales.
209
+
210
+ **Si estás internacionalizando un proyecto existente que ya incluye miles de componentes para refactorizar:**
211
+ Un enfoque basado en compilador puede ser una opción pragmática aquí. La fase inicial de extracción puede ahorrar semanas o meses de trabajo manual. Sin embargo, considera usar una herramienta como el comando `transform` de Intlayer, que puede extraer cadenas y convertirlas en declaraciones explícitas de contenido declarativo. Esto te brinda la velocidad de la automatización mientras mantienes la seguridad y portabilidad de un enfoque declarativo. Obtienes lo mejor de ambos mundos: una migración inicial rápida sin deuda arquitectónica a largo plazo.
129
212
 
130
- **Si estás construyendo una aplicación profesional, de nivel empresarial:**
213
+ **Si estás construyendo una Aplicación Profesional de Nivel Empresarial:**
131
214
  La magia generalmente es una mala idea. Necesitas control.
132
215
 
133
- - Necesitas manejar datos dinámicos desde backends.
216
+ - Necesitas manejar datos dinámicos desde los backends.
134
217
  - Necesitas asegurar el rendimiento en dispositivos de gama baja (evitando explosiones de hooks).
135
- - Necesitas asegurarte de no quedar atrapado para siempre en una herramienta de construcción específica.
218
+ - Necesitas asegurarte de no quedar atrapado para siempre en una herramienta de compilación específica.
136
219
 
137
- Para aplicaciones profesionales, la **Gestión Declarativa de Contenidos** (como Intlayer o bibliotecas establecidas) sigue siendo el estándar de oro. Separa tus preocupaciones, mantiene tu arquitectura limpia y garantiza que la capacidad de tu aplicación para hablar múltiples idiomas no dependa de un compilador "caja negra" que adivine tus intenciones.
220
+ Para aplicaciones profesionales, la **Gestión Declarativa de Contenido** (como Intlayer o bibliotecas establecidas) sigue siendo el estándar de oro. Separa tus preocupaciones, mantiene tu arquitectura limpia y garantiza que la capacidad de tu aplicación para hablar múltiples idiomas no dependa de un compilador "caja negra" que adivine tus intenciones.
@@ -18,120 +18,203 @@ slugs:
18
18
  - compiler-vs-declarative-i18n
19
19
  ---
20
20
 
21
- # Les arguments pour et contre li18n basée sur un compilateur
21
+ # Les arguments pour et contre l'i18n basée sur un compilateur
22
22
 
23
- Si vous développez des applications web depuis plus dune décennie, vous savez que linternationalisation (i18n) a toujours été un point de friction. Cest souvent la tâche que personne ne veut faire : extraire les chaînes, gérer les fichiers JSON, et se soucier des règles de pluriel.
23
+ Si vous développez des applications web depuis plus d'une décennie, vous savez que l'internationalisation (i18n) a toujours été un point de friction. C'est souvent la tâche que personne ne veut faire : extraire les chaînes, gérer les fichiers JSON, et se soucier des règles de pluriel.
24
24
 
25
- Récemment, une nouvelle vague doutils i18n « basés sur un compilateur » a émergé, promettant de faire disparaître cette douleur. L’argument est séduisant : **Il suffit d’écrire le texte dans vos composants, et laissez l’outil de build gérer le reste.** Pas de clés, pas d’importations, juste de la magie.
25
+ Récemment, une nouvelle vague d’**outils i18n basés sur un compilateur** a émergé, promettant de faire disparaître cette douleur. L’argument est séduisant : **Il suffit d’écrire le texte dans vos composants, et laissez l’outil de build gérer le reste.** Pas de clés, pas d’importations, juste de la magie.
26
26
 
27
27
  Mais comme pour toutes les abstractions en ingénierie logicielle, la magie a un prix.
28
28
 
29
- Dans cet article de blog, nous allons explorer le passage des bibliothèques déclaratives aux approches basées sur un compilateur, les dettes architecturales cachées quelles introduisent, et pourquoi la méthode « ennuyeuse » pourrait encore être la meilleure pour les applications professionnelles.
29
+ Dans cet article de blog, nous allons explorer le passage des bibliothèques déclaratives aux approches basées sur un compilateur, les dettes architecturales cachées qu'elles introduisent, et pourquoi la méthode « ennuyeuse » pourrait encore être la meilleure pour les applications professionnelles.
30
30
 
31
- ## Une brève histoire de la traduction
31
+ ## Table des matières
32
+
33
+ <TOC/>
34
+
35
+ ## Un bref historique de l'internationalisation
32
36
 
33
37
  Pour comprendre où nous en sommes, il faut revenir à nos débuts.
34
38
 
35
- Vers 2011–2012, le paysage JavaScript était très différent. Les bundlers tels que nous les connaissons (Webpack, Vite) n’existaient pas ou étaient à leurs débuts. Nous collions les scripts ensemble dans le navigateur. C’est à cette époque que des bibliothèques comme **i18next** sont nées.
39
+ Vers 2011–2012, le paysage JavaScript était très différent. Les bundlers tels que nous les connaissons aujourd’hui (Webpack, Vite) n’existaient pas ou étaient à leurs débuts. Nous collions les scripts directement dans le navigateur. C’est à cette époque que des bibliothèques comme **i18next** sont nées.
36
40
 
37
- Elles ont résolu le problème de la seule manière possible à l’époque : les **Dictionnaires à l’exécution**. Vous chargiez un énorme objet JSON en mémoire, et une fonction recherchait les clés à la volée. C’était fiable, explicite, et fonctionnait partout.
41
+ Elles ont résolu le problème de la seule manière possible à l’époque : **les dictionnaires à l’exécution**. Vous chargiez un énorme objet JSON en mémoire, et une fonction recherchait les clés à la volée. C’était fiable, explicite, et fonctionnait partout.
38
42
 
39
43
  Avançons jusqu’à aujourd’hui. Nous disposons de compilateurs puissants (SWC, bundlers basés sur Rust) capables d’analyser des arbres de syntaxe abstraite (AST) en quelques millisecondes. Cette puissance a donné naissance à une nouvelle idée : _Pourquoi gérer manuellement les clés ? Pourquoi le compilateur ne pourrait-il pas simplement voir le texte "Hello World" et le remplacer pour nous ?_
40
44
 
41
45
  Ainsi est née l’i18n basée sur un compilateur.
42
46
 
43
- ## LAttrait du Compilateur (L’Approche "Magique")
47
+ > **Exemple di18n basée sur un compilateur :**
48
+ >
49
+ > - Paraglide (Modules tree-shaken qui compilent chaque message en une petite fonction ESM afin que les bundlers puissent automatiquement éliminer les locales et clés inutilisées. Vous importez les messages sous forme de fonctions au lieu de faire des recherches par clé de chaîne.)
50
+ > - LinguiJS (Compilateur macro-vers-fonction qui réécrit les macros de message comme `<Trans>` en appels de fonctions JS simples au moment de la compilation. Vous obtenez la syntaxe ICU/MessageFormat avec une empreinte runtime très réduite.)
51
+ > - Lingo.dev (Se concentre sur l’automatisation du pipeline de localisation en injectant le contenu traduit directement lors de la compilation de votre application React. Il peut générer automatiquement des traductions via l’IA et s’intégrer directement dans le CI/CD.)
52
+ > - Wuchale (Préprocesseur orienté Svelte qui extrait le texte en ligne dans les fichiers .svelte et le compile en fonctions de traduction sans wrapper. Il évite les clés de chaîne et sépare complètement la logique d'extraction de contenu du runtime principal de l'application.)
53
+ > - Intlayer (Compilateur / CLI d'extraction qui analyse vos composants, génère des dictionnaires typés, et peut optionnellement réécrire le code pour utiliser explicitement le contenu Intlayer. L'objectif est d'utiliser le compilateur pour la rapidité tout en conservant un noyau déclaratif et agnostique au framework.)
54
+ >
55
+ > **Exemple d’i18n déclarative :**
56
+ >
57
+ > - i18next / react-i18next / next-i18next (La norme industrielle mature utilisant des dictionnaires JSON au runtime et un écosystème étendu de plugins)
58
+ > - react-intl (Fait partie de la bibliothèque FormatJS, se concentrant sur la syntaxe standard des messages ICU et un formatage strict des données)
59
+ > - next-intl (Optimisé spécifiquement pour Next.js avec intégration pour l'App Router et les React Server Components)
60
+ > - vue-i18n / @nuxt/i18n (La solution standard de l'écosystème Vue offrant des blocs de traduction au niveau des composants et une intégration étroite de la réactivité)
61
+ > - svelte-i18n (Un wrapper léger autour des stores Svelte pour des traductions réactives à l'exécution)
62
+ > - angular-translate (La bibliothèque de traduction dynamique héritée reposant sur la recherche de clés à l'exécution plutôt que sur la fusion à la compilation)
63
+ > - angular-i18n (L'approche native d'Angular, en avance sur le temps, fusionnant les fichiers XLIFF directement dans les templates lors de la compilation)
64
+ > - Tolgee (Combine un code déclaratif avec un SDK en contexte pour une édition "click-to-translate" directement dans l'interface utilisateur)
65
+ > - Intlayer (Approche par composant, utilisant des fichiers de déclarations de contenu permettant le tree-shaking natif et la validation TypeScript)
66
+
67
+ ## Le compilateur Intlayer
68
+
69
+ Bien que **Intlayer** soit une solution qui encourage fondamentalement une **approche déclarative** de votre contenu, elle inclut un compilateur pour aider à accélérer le développement ou faciliter le prototypage rapide.
70
+
71
+ Le compilateur Intlayer parcourt l'AST (Abstract Syntax Tree) de vos composants React, Vue ou Svelte, ainsi que d'autres fichiers JavaScript/TypeScript. Son rôle est de détecter les chaînes de caractères codées en dur et de les extraire dans des déclarations dédiées `.content`.
72
+
73
+ > Pour plus de détails, consultez la documentation : [Intlayer Compiler Docs](https://github.com/aymericzip/intlayer/blob/main/docs/docs/fr/compiler.md)
74
+
75
+ ## L'Attrait du Compilateur (L'Approche "Magique")
44
76
 
45
- Il y a une raison pour laquelle cette nouvelle approche est tendance. Pour un développeur, lexpérience est incroyable.
77
+ Il y a une raison pour laquelle cette nouvelle approche est tendance. Pour un développeur, l'expérience est incroyable.
46
78
 
47
79
  ### 1. Vitesse et "Flow"
48
80
 
49
- Quand vous êtes dans votre zone, vous arrêter pour réfléchir à un nom de variable (`home_hero_title_v2`) casse votre flow. Avec une approche compilateur, vous tapez `<p>Welcome back</p>` et continuez. La friction est nulle.
81
+ Quand vous êtes dans votre zone, vous arrêter pour réfléchir à un nom de variable sémantique (`home_hero_title_v2`) casse votre flow. Avec une approche compilateur, vous tapez `<p>Welcome back</p>` et continuez. La friction est nulle.
50
82
 
51
83
  ### 2. La Mission de Sauvetage du Legacy
52
84
 
53
- Imaginez hériter dune énorme base de code avec 5 000 composants et aucune traduction. Adapter cela avec un système manuel basé sur des clés est un cauchemar qui dure des mois. Un outil basé sur un compilateur agit comme une stratégie de sauvetage, extrayant instantanément des milliers de chaînes sans que vous ayez besoin de toucher un seul fichier manuellement.
85
+ Imaginez hériter d'une immense base de code avec 5 000 composants et aucune traduction. Adapter cela avec un système manuel basé sur des clés est un cauchemar qui dure des mois. Un outil basé sur un compilateur agit comme une stratégie de sauvetage, extrayant instantanément des milliers de chaînes sans que vous ayez besoin de toucher un seul fichier manuellement.
54
86
 
55
- ### 3. L’Ère de lIA
87
+ ### 3. L'ère de l'IA
56
88
 
57
- Cest un avantage moderne quil ne faut pas négliger. Les assistants de codage IA (comme Copilot ou ChatGPT) génèrent naturellement du JSX/HTML standard. Ils ne connaissent pas votre schéma spécifique de clés de traduction.
89
+ C'est un avantage moderne qu'il ne faut pas négliger. Les assistants de codage IA (comme Copilot ou ChatGPT) génèrent naturellement du JSX/HTML standard. Ils ne connaissent pas votre schéma spécifique de clés de traduction.
58
90
 
59
- - **Déclaratif :** Vous devez réécrire la sortie de lIA pour remplacer le texte par des clés.
60
- - **Compilateur :** Vous copiez-collez le code de lIA, et ça fonctionne tout simplement.
91
+ - **Déclaratif :** Vous devez réécrire la sortie de l'IA pour remplacer le texte par des clés.
92
+ - **Compilateur :** Vous copiez-collez le code de l'IA, et ça fonctionne simplement.
61
93
 
62
- ## La Réalité : Pourquoi la "Magie" est Dangereuse
94
+ ## Le Réalisme : Pourquoi la "Magie" est Dangereuse
63
95
 
64
- Bien que la "magie" soit séduisante, labstraction fuit. Compter sur un outil de build pour comprendre lintention humaine introduit une fragilité architecturale.
96
+ Bien que la "magie" soit séduisante, l'abstraction présente des fuites. Compter sur un outil de build pour comprendre l'intention humaine introduit une fragilité architecturale.
65
97
 
66
- ### 1. Fragilité Heuristique (Le Jeu de Deviner)
98
+ ### Fragilité heuristique (Le jeu de devinettes)
67
99
 
68
- Le compilateur doit deviner ce qui est contenu et ce qui est code.
100
+ Le compilateur doit deviner ce qui est contenu et ce qui est code. Cela conduit à des cas limites où vous vous retrouvez à "lutter" contre l'outil.
69
101
 
70
- - Est-ce que `className="active"` est traduit ? C’est une chaîne de caractères.
71
- - Est-ce que `status="pending"` est traduit ?
72
- - Est-ce que `<MyComponent errorMessage="An error occurred" />` est traduit ?
73
- - Est-ce qu’un identifiant produit comme `"AX-99"` est traduit ?
102
+ Considérez ces scénarios :
74
103
 
75
- Vous finissez inévitablement par « lutter » contre le compilateur, en ajoutant des commentaires spécifiques (comme `// ignore-translation`) pour l’empêcher de casser la logique de votre application.
104
+ - Est-ce que `<span className="active"></span>` est extrait ? (C'est une chaîne, mais probablement une classe).
105
+ - Est-ce que `<span status="pending"></span>` est extrait ? (C'est une valeur de prop).
106
+ - Est-ce que `<span>{"Hello World"}</span>` est extrait ? (C'est une expression JS).
107
+ - Est-ce que `<span>Hello {name}. How are you?</span>` est extrait ? (L'interpolation est complexe).
108
+ - Est-ce que `<span aria-label="Image of cat"></span>` est extrait ? (Les attributs d'accessibilité nécessitent une traduction).
109
+ - Est-ce que `<span data-testid="my-element"></span>` est extrait ? (Les IDs de test NE DOIVENT PAS être traduits).
110
+ - Est-ce que `<MyComponent errorMessage="An error occurred" />` est extrait ?
111
+ - Est-ce que `<p>This is a paragraph{" "}\n containing multiple lines</p>` est extrait ?
112
+ - Est-ce que le résultat de la fonction `<p>{getStatusMessage()}</p>` est extrait ?
113
+ - Est-ce que `<div>{isLoading ? "The page is loading" : <MyComponent/>} </div>` est extrait ?
114
+ - Est-ce qu’un ID produit comme `<span>AX-99</span>` est extrait ?
76
115
 
77
- ### 2. La limite stricte des données dynamiques
116
+ Vous finissez inévitablement par ajouter des commentaires spécifiques (comme `// ignore-translation`, ou des props spécifiques comme `data-compiler-ignore="true"`) pour éviter que cela ne casse la logique de votre application.
117
+
118
+ ### Comment Intlayer gère-t-il cette complexité ?
119
+
120
+ Intlayer utilise une approche mixte pour détecter si un champ doit être extrait pour traduction, en tentant de minimiser les faux positifs :
121
+
122
+ 1. **Analyse AST :** Il vérifie le type d’élément (par exemple, en distinguant entre un `reactNode`, un `label` ou une prop `title`).
123
+ 2. **Reconnaissance de motifs :** Il détecte si la chaîne est en majuscule ou contient des espaces, ce qui suggère qu’il s’agit probablement d’un texte lisible par un humain plutôt que d’un identifiant de code.
124
+
125
+ ### La limite stricte des données dynamiques
78
126
 
79
127
  L’extraction par le compilateur repose sur une **analyse statique**. Il doit voir la chaîne littérale dans votre code pour générer un ID stable.
80
- Si votre API renvoie une chaîne de code derreur comme `server_error`, vous ne pouvez pas la traduire avec un compilateur car celui-ci ne connaît pas cette chaîne au moment de la compilation. Vous êtes obligé de construire un système secondaire « runtime-only » uniquement pour les données dynamiques.
128
+ Si votre API renvoie une chaîne de code d'erreur comme `server_error`, vous ne pouvez pas la traduire avec un compilateur car ce dernier ne sait pas que cette chaîne existe au moment de la compilation. Vous êtes obligé de créer un système secondaire "runtime-only" uniquement pour les données dynamiques.
129
+
130
+ ### Manque de découpage en chunks
131
+
132
+ Certains compilateurs ne découpent pas les traductions par page. Si votre compilateur génère un gros fichier JSON par langue (par exemple, `./lang/en.json`, `./lang/fr.json`, etc.), vous risquez de charger le contenu de toutes vos pages pour une seule page visitée. De plus, chaque composant utilisant votre contenu sera probablement hydraté avec beaucoup plus de contenu que nécessaire, ce qui peut entraîner des problèmes de performance.
133
+
134
+ Faites également attention à charger vos traductions de manière dynamique. Si cela n'est pas fait, vous chargerez le contenu de toutes les langues en plus de celle en cours.
81
135
 
82
- ### 3. « Explosion des chunks » et cascades réseau
136
+ > Pour illustrer le problème, considérez un site avec 10 pages et 10 langues (toutes 100 % uniques). Vous chargeriez le contenu de 99 pages supplémentaires (10 × 10 - 1).
83
137
 
84
- Pour permettre le tree-shaking, les outils de compilation divisent souvent les traductions par composant.
138
+ ### « Explosion de chunks » et cascades réseau
85
139
 
86
- - **La conséquence :** Une seule vue de page avec 50 petits composants peut déclencher **50 requêtes HTTP distinctes** pour de petits fragments de traduction. Même avec HTTP/2, cela crée un effet de cascade réseau qui rend votre application lente comparée au chargement d’un seul bundle de langue optimisé.
140
+ Pour résoudre le problème du chunking, certaines solutions proposent un découpage par composant, voire par clé. Pourtant, le problème n'est que partiellement résolu. L'argument de vente de ces solutions est souvent de dire « Votre contenu est tree-shaké ».
87
141
 
88
- ### 4. Surcharge des performances à l’exécution
142
+ En effet, si vous chargez le contenu statiquement, votre solution éliminera le contenu inutilisé, mais vous finirez quand même avec le contenu de toutes les langues chargé avec votre application.
89
143
 
90
- Pour rendre les traductions réactives (afin qu’elles se mettent à jour instantanément lorsque vous changez de langue), le compilateur injecte souvent des hooks de gestion d’état dans _chaque_ composant.
144
+ Alors pourquoi ne pas le charger dynamiquement ? Oui, dans ce cas, vous chargerez plus de contenu que nécessaire, mais ce n'est pas sans compromis.
91
145
 
92
- - **Le Coût :** Si vous affichez une liste de 5 000 éléments, vous initialisez 5 000 hooks `useState` et `useEffect` uniquement pour le texte. Cela consomme de la mémoire et des cycles CPU que les bibliothèques déclaratives (qui utilisent généralement un seul fournisseur Context) économisent.
146
+ Le chargement dynamique du contenu isole chaque morceau de contenu dans son propre chunk, qui ne sera chargé que lorsque le composant est rendu. Cela signifie que vous ferez une requête HTTP par bloc de texte. 1 000 blocs de texte sur votre page ? 1 000 requêtes HTTP vers vos serveurs. Et pour limiter les dégâts et optimiser le temps de rendu initial de votre application, vous devrez insérer plusieurs frontières de Suspense ou des Skeleton Loaders.
93
147
 
94
- ## Le Piège : Le Verrouillage Fournisseur
148
+ > Note : Même avec Next.js et le SSR, vos composants seront toujours hydratés après le chargement, donc les requêtes HTTP seront toujours effectuées.
95
149
 
96
- C'est sans doute l'aspect le plus dangereux de l'i18n basée sur un compilateur.
150
+ La solution ? Adopter une solution qui permet de déclarer des contenus à portée locale, comme le font `i18next`, `next-intl` ou `intlayer`.
97
151
 
98
- Dans une bibliothèque déclarative, votre code source contient une intention explicite. Vous possédez les clés. Si vous changez de bibliothèque, vous changez simplement l'import.
152
+ > Note : `i18next` et `next-intl` exigent que vous gériez manuellement l'importation de vos namespaces / messages pour chaque page afin d'optimiser la taille de votre bundle. Vous devriez utiliser un analyseur de bundle comme `rollup-plugin-visualizer` (vite), `@next/bundle-analyzer` (next.js), ou `webpack-bundle-analyzer` (React CRA / Angular / etc) pour détecter si vous polluez votre bundle avec des traductions inutilisées.
99
153
 
100
- Dans une approche basée sur un compilateur, **votre code source n'est que du texte en anglais.** La "logique de traduction" n'existe que dans la configuration du plugin de build.
101
- Si cette bibliothèque cesse d’être maintenue, ou si vous la dépassez, vous êtes bloqué. Vous ne pouvez pas facilement « éjecter » car vous n’avez aucune clé de traduction dans votre code source. Vous devriez réécrire manuellement toute votre application pour migrer.
154
+ ### Surcharge de performance à l'exécution
102
155
 
103
- ## L’autre côté : risques de l’approche déclarative
156
+ Pour rendre les traductions réactives (afin qu'elles se mettent à jour instantanément lorsque vous changez de langue), le compilateur injecte souvent des hooks de gestion d'état dans chaque composant.
157
+
158
+ - **Le coût :** Si vous affichez une liste de 5 000 éléments, vous initialisez 5 000 hooks `useState` et `useEffect` uniquement pour le texte. React doit identifier et re-render tous les 5 000 consommateurs simultanément. Cela provoque un blocage massif du "Main Thread", gelant l'interface utilisateur pendant le changement. Cela consomme de la mémoire et des cycles CPU que les bibliothèques déclaratives (qui utilisent généralement un seul fournisseur Context) économisent.
159
+
160
+ > Notez que le problème est similaire pour d'autres frameworks que React.
161
+
162
+ ## Le piège : l'enfermement fournisseur
163
+
164
+ Faites attention à choisir une solution i18n qui permet l'extraction ou la migration des clés de traduction.
165
+
166
+ Dans le cas d'une bibliothèque déclarative, votre code source contient explicitement votre intention de traduction : ce sont vos clés, et vous les contrôlez. Si vous souhaitez changer de bibliothèque, il vous suffit généralement de mettre à jour l'import.
167
+
168
+ Avec une approche compilateur, votre code source peut être simplement du texte en anglais, sans aucune trace de logique de traduction : tout est caché dans la configuration de l'outil de build. Si ce plugin n'est plus maintenu ou si vous souhaitez changer de solution, vous pourriez être bloqué. Il n'y a pas de moyen simple de "détacher" : il n'y a pas de clés utilisables dans votre code, et vous pourriez devoir régénérer toutes vos traductions pour une nouvelle bibliothèque.
169
+
170
+ Certaines solutions proposent également des services de génération de traduction. Plus de crédits ? Plus de traductions.
171
+
172
+ Les compilateurs hachent souvent le texte (par exemple, `"Hello World"` -> `x7f2a`). Vos fichiers de traduction ressemblent à `{ "x7f2a": "Hola Mundo" }`. Le piège : si vous changez de bibliothèque, la nouvelle bibliothèque voit `"Hello World"` et cherche cette clé. Elle ne la trouvera pas car votre fichier de traduction est rempli de hachages (`x7f2a`).
173
+
174
+ ### Verrouillage de plateforme
175
+
176
+ En choisissant une approche basée sur un compilateur, vous vous enfermez dans la plateforme sous-jacente. Par exemple, certains compilateurs ne sont pas disponibles pour tous les bundlers (comme Vite, Turbopack ou Metro). Cela peut rendre les migrations futures difficiles, et vous pourriez avoir besoin d'adopter plusieurs solutions pour couvrir toutes vos applications.
177
+
178
+ ## L'autre côté : risques de l'approche déclarative
104
179
 
105
180
  Pour être juste, la méthode déclarative traditionnelle n’est pas parfaite non plus. Elle a ses propres « pièges ».
106
181
 
107
- 1. **L’enfer des namespaces :** Vous devez souvent gérer manuellement quels fichiers JSON charger (`common.json`, `dashboard.json`, `footer.json`). Si vous en oubliez un, l’utilisateur voit les clés brutes.
108
- 2. **Surcharge de requêtes :** Sans une configuration soigneuse, il est très facile de charger accidentellement _toutes_ vos clés de traduction pour _toutes_ les pages dès le chargement initial, ce qui alourdit la taille de votre bundle.
109
- 3. **Dérive de synchronisation :** Il est courant que des clés restent dans le fichier JSON bien après que le composant qui les utilise ait été supprimé. Vos fichiers de traduction grossissent indéfiniment, remplis de « clés zombies ».
182
+ 1. **L’enfer des namespaces :** Vous devez souvent gérer manuellement quels fichiers JSON charger (`common.json`, `dashboard.json`, `footer.json`). Si vous en oubliez un, l’utilisateur voit des clés brutes.
183
+ 2. **Surcharge de récupération :** Sans une configuration soigneuse, il est très facile de charger accidentellement _toutes_ vos clés de traduction pour _toutes_ les pages lors du chargement initial, ce qui alourdit la taille de votre bundle.
184
+ 3. **Dérive de synchronisation :** Il est courant que des clés restent dans le fichier JSON longtemps après que le composant qui les utilisait ait été supprimé. Vos fichiers de traduction grossissent indéfiniment, remplis de "clés zombies".
110
185
 
111
- ## Le juste milieu avec Intlayer
186
+ ## Le juste milieu d'Intlayer
112
187
 
113
- Cest là que des outils comme **Intlayer** cherchent à innover. Intlayer comprend que, bien que les compilateurs soient puissants, la magie implicite est dangereuse.
188
+ C'est là que des outils comme **Intlayer** cherchent à innover. Intlayer comprend que, bien que les compilateurs soient puissants, la magie implicite est dangereuse.
114
189
 
115
- Intlayer propose une commande unique **`transform`**. Au lieu de faire simplement de la magie dans une étape de build cachée, elle peut en réalité **réécrire votre code de composant**. Elle analyse votre texte et le remplace par des déclarations de contenu explicites dans votre base de code.
190
+ Intlayer propose une approche mixte, vous permettant de bénéficier des avantages des deux approches : une gestion déclarative du contenu, également compatible avec son compilateur pour gagner du temps de développement.
191
+
192
+ Et même si vous n'utilisez pas le compilateur Intlayer, Intlayer propose une commande `transform` (également accessible via l'extension VSCode). Au lieu de faire simplement de la magie lors de l'étape de build cachée, elle peut en fait **réécrire le code de vos composants**. Elle analyse votre texte et le remplace par des déclarations de contenu explicites dans votre base de code.
116
193
 
117
194
  Cela vous offre le meilleur des deux mondes :
118
195
 
119
196
  1. **Granularité :** Vous gardez vos traductions proches de vos composants (améliorant la modularité et le tree-shaking).
120
- 2. **Sécurité :** La traduction devient un code explicite, et non une magie cachée au moment de la compilation.
121
- 3. **Pas de verrouillage :** Puisque le code est transformé en une structure déclarative standard dans votre dépôt, vous ne cachez pas la logique dans un plugin webpack.
197
+ 2. **Sécurité :** La traduction devient un code explicite, et non une magie cachée au moment du build.
198
+ 3. **Pas de verrouillage :** Puisque le code est transformé en une structure déclarative dans votre dépôt, vous pouvez facilement appuyer sur tab, ou utiliser le copilot de votre IDE, pour générer vos déclarations de contenu, vous ne cachez pas la logique dans un plugin webpack.
122
199
 
123
200
  ## Conclusion
124
201
 
125
202
  Alors, que devriez-vous choisir ?
126
203
 
127
- **Si vous êtes un développeur junior, un fondateur solo, ou que vous construisez un MVP :**
128
- L'approche basée sur le compilateur est un choix valide. Elle vous permet d'avancer extrêmement vite. Vous n'avez pas besoin de vous soucier des structures de fichiers ou des clés. Vous construisez simplement. La dette technique est un problème pour le "Vous du futur".
204
+ **Si vous construisez un MVP, ou souhaitez avancer rapidement :**
205
+ L'approche basée sur le compilateur est un choix valable. Elle vous permet d'avancer incroyablement vite. Vous n'avez pas besoin de vous soucier des structures de fichiers ou des clés. Vous construisez simplement. La dette technique sera un problème pour le "Vous du futur".
206
+
207
+ **Si vous êtes un développeur junior, ou que l'optimisation ne vous importe pas :**
208
+ Si vous souhaitez la gestion la plus simple possible, une approche basée sur le compilateur est probablement la meilleure. Vous n'aurez pas besoin de gérer vous-même les clés ou les fichiers de traduction — écrivez simplement le texte, et le compilateur automatise le reste. Cela réduit l'effort d'installation et les erreurs courantes liées à l'i18n manuelle.
209
+
210
+ **Si vous internationalisez un projet existant qui comprend déjà des milliers de composants à refactoriser :**
211
+ Une approche basée sur un compilateur peut être un choix pragmatique ici. La phase d'extraction initiale peut vous faire gagner des semaines ou des mois de travail manuel. Cependant, envisagez d'utiliser un outil comme la commande `transform` d'Intlayer, qui peut extraire des chaînes et les convertir en déclarations de contenu déclaratives explicites. Cela vous offre la rapidité de l'automatisation tout en conservant la sécurité et la portabilité d'une approche déclarative. Vous obtenez le meilleur des deux mondes : une migration initiale rapide sans dette architecturale à long terme.
129
212
 
130
- **Si vous construisez une application professionnelle de niveau entreprise :**
213
+ **Si vous développez une application professionnelle de niveau entreprise :**
131
214
  La magie est généralement une mauvaise idée. Vous avez besoin de contrôle.
132
215
 
133
216
  - Vous devez gérer des données dynamiques provenant des backends.
134
- - Vous devez garantir la performance sur des appareils peu puissants (en évitant les explosions de hooks).
217
+ - Vous devez garantir la performance sur des appareils bas de gamme (en évitant les explosions de hooks).
135
218
  - Vous devez vous assurer de ne pas être enfermé à jamais dans un outil de build spécifique.
136
219
 
137
220
  Pour les applications professionnelles, la **Gestion de Contenu Déclarative** (comme Intlayer ou des bibliothèques établies) reste la référence. Elle sépare vos préoccupations, maintient votre architecture propre, et garantit que la capacité de votre application à parler plusieurs langues ne dépend pas d'un compilateur "boîte noire" devinant vos intentions.