Internacionalización de WordPress: cómo traducir temas y plugins
Prepare su tema o plugin de WordPress para su traducción. Esta guía cubre los dominios de texto, las funciones gettext, la generación de archivos POT y el mecanismo de carga que muestra las traducciones a los usuarios. PTC (Private Translation Cloud) traduce después los archivos de recursos y revisa visualmente el tema o plugin renderizado en todos los idiomas.
Esta guía está dirigida a desarrolladores que escriben el código. Si ya tiene un archivo POT o PO y solo necesita traducirlo, diríjase a la página de archivos PO para conocer el flujo de trabajo de 3 pasos.
Al finalizar esta guía, su tema o plugin estará:
- Internacionalizado correctamente según los estándares de código de WordPress.
- Listo para ser traducido por PTC a más de 40 idiomas.
- Preparado para su distribución a través de los paquetes de idioma de WordPress.org.
- Verificado en cada lanzamiento con la revisión visual de traducciones de PTC.
¿Qué es la internacionalización de WordPress?
La internacionalización (i18n) es el trabajo de preparar su código para que pueda ser traducido. La localización (l10n) es el siguiente paso: produce las cadenas traducidas reales para idiomas específicos.
Para los temas y plugins de WordPress, la i18n implica tres cosas:
- Envolver cada cadena orientada al usuario en funciones gettext para que WordPress pueda intercambiarlas en tiempo de ejecución.
- Definir un dominio de texto que vincule sus traducciones con su proyecto.
- Generar un archivo POT a partir del cual trabajarán los traductores (o PTC).
Una vez realizado ese trabajo, tendrá todo lo necesario para producir archivos traducidos PO, MO, JSON y .l10n.php para cualquier idioma.
PTC traduce archivos POT a MO, JSON y .l10n.php para WordPress
En cualquier flujo de trabajo de traducción de WordPress intervienen cinco extensiones de archivo. PTC traduce desde .pot (su origen) a .po, .mo, .json y .l10n.php para cada idioma de destino. Cada formato tiene una función específica:
- POT (Portable Object Template). El archivo de origen generado a partir de su código. Enumera cada cadena traducible sin traducciones adjuntas. Usted entrega este archivo a PTC.
- PO (Portable Object). Una copia del POT con las traducciones añadidas para un idioma específico. Es texto plano, legible por humanos. PTC devuelve un PO por cada idioma de destino.
- MO (Machine Object). La versión binaria compilada de un PO. WordPress lee los archivos MO en tiempo de ejecución porque se cargan más rápido que el texto de los PO.
- JSON. El equivalente en JavaScript del MO. WordPress no puede leer MO desde JavaScript, por lo que el pipeline de compilación produce archivos JSON para las cadenas del lado del navegador.
- .l10n.php. Una alternativa más reciente al MO, introducida en WordPress 6.5. Se carga más rápido y utiliza menos memoria. WordPress lo selecciona automáticamente cuando existe junto al archivo MO.
Active .l10n.php para nuevos proyectos. Es estrictamente mejor que el MO en las versiones compatibles de WordPress.
Por qué la traducción de la comunidad no es suficiente
WordPress.org ofrece traducción comunitaria a través de GlotPress. En la práctica, esto cubre una pequeña fracción de lo que la mayoría de los plugins y temas necesitan. Un análisis de más de 60.000 plugins y temas de WordPress reveló que la traducción comunitaria cubre menos del 5 % de las necesidades de traducción en 40 idiomas.
Dos problemas estructurales explican esta brecha:
- Los voluntarios escasean en la mayoría de los locales. Un puñado de plugins con bases de usuarios masivas atraen a traductores. La mayoría no.
- Las traducciones pueden tardar meses o años en aparecer, si es que aparecen. Si quiere que los usuarios vean su plugin o tema en su idioma desde el primer día, no puede depender de la comunidad.
Esta guía asume que usted desea una cobertura de traducción completa y constante en un calendario de lanzamientos que usted controle. Eso es lo que ofrece PTC.
Preparación de su tema o plugin de WordPress para la traducción
Un dominio de texto mal emparejado o una cadena sin envolver significan que ese texto nunca aparecerá en su resultado traducido. Los detalles importan.
Paso 1: Defina su dominio de texto y la ruta del dominio
Cada tema o plugin necesita un dominio de texto. El dominio de texto es un identificador único que indica a WordPress qué archivos de traducción pertenecen a su proyecto. Debe coincidir exactamente con el slug de su plugin o tema.
Declárelo en la cabecera del archivo principal de su plugin:
<?php
/**
* Plugin Name: My Plugin
* Description: An example plugin.
* Version: 1.0.0
* Text Domain: my-plugin
* Domain Path: /languages
*/
O en el archivo style.css de su tema:
/*
Theme Name: My Theme
Text Domain: my-theme
Domain Path: /languages
*/
La ruta del dominio (Domain Path) indica a WordPress dónde residen sus archivos de traducción en relación con la raíz del plugin o tema. /languages es el estándar.
Paso 2: Envuelva sus cadenas de PHP en funciones gettext
Cualquier cadena que desee traducir debe estar envuelta en una de las funciones gettext de WordPress. En tiempo de ejecución, esas funciones buscan la traducción correcta. Si no se encuentra ninguna, recurren a la cadena original.
Cadenas básicas. Utilice __() cuando necesite devolver una cadena. Para la salida HTML, utilice las variantes con escape. Los estándares de código de WordPress recomiendan echo esc_html__() en lugar de _e(). La variante con escape hace que la limpieza de la salida sea explícita y previene ataques XSS en el punto de salida:
// Return a translated string
$label = __( 'Settings', 'my-plugin' );
// Echo a translated string, escaped for HTML
echo esc_html__( 'Settings saved.', 'my-plugin' );
Cadenas con variables. No concatene variables en las cadenas. Los traductores solo ven fragmentos y no pueden reordenar las palabras para idiomas con una sintaxis diferente. Utilice printf() o sprintf() con un marcador de posición. Añada un comentario para el traductor para que sepa qué representa %s:
printf(
/* translators: %s: the user's display name */
esc_html__( 'Welcome back, %s.', 'my-plugin' ),
esc_html( $display_name )
);
Formas plurales. Los plurales en inglés son sencillos (one comment, two comments). Otros idiomas no lo son. Utilice _n() para gestionar todas las reglas de plural que WordPress conoce:
printf(
esc_html( _n( '%s comment', '%s comments', $count, 'my-plugin' ) ),
number_format_i18n( $count )
);
Cadenas que necesitan contexto. Algunas palabras significan cosas diferentes según dónde aparezcan. Utilice _x() para dar a los traductores el contexto que necesitan:
// "Export" as a noun (the file) vs. a verb (the action)
echo esc_html_x( 'Export', 'button label', 'my-plugin' );
Paso 3: Internacionalice sus cadenas de JavaScript
WordPress proporciona el paquete wp-i18n para que pueda utilizar las mismas funciones gettext en JavaScript que utiliza en PHP. Al registrar su script, declare wp-i18n como una dependencia:
wp_register_script(
'my-plugin-script',
plugins_url( 'js/app.js', __FILE__ ),
array( 'wp-i18n' ),
'1.0.0',
true
);
Después, en su archivo JavaScript:
const { __, _n, sprintf } = wp.i18n;
const message = __( 'Settings saved.', 'my-plugin' );
Si utiliza un empaquetador como Webpack, instale @wordpress/babel-plugin-makepot. Este extrae las cadenas traducibles de su paquete como parte de su compilación.
Paso 4: Genere su archivo POT
Una vez que sus cadenas estén envueltas, genere un archivo POT. El POT es el archivo de origen a partir del cual trabaja PTC (o cualquier traductor). Contiene cada cadena traducible pero ninguna traducción.
wp i18n make-pot . languages/my-plugin.pot
WP-CLI escanea sus archivos PHP, JavaScript y block.json en busca de llamadas gettext. Las compila en un único POT. Si su equipo utiliza Composer, añada este comando como un script de Composer. Eso mantiene el uso de WP-CLI consistente en todo el equipo sin necesidad de una instalación global.
La suite completa de comandos wp i18n cubre el resto del pipeline:
| Comando | Qué hace |
|---|---|
wp i18n make-pot |
Genera un archivo POT desde el origen. |
wp i18n update-po |
Sincroniza los archivos PO existentes cuando su POT cambia. |
wp i18n make-mo |
Compila archivos PO en archivos binarios MO. |
wp i18n make-json |
Extrae cadenas JS de PO a archivos JSON. |
wp i18n make-php |
Genera archivos .l10n.php (WordPress 6.5+). |
No necesita Poedit. Todo en este flujo de trabajo se ejecuta a través de WP-CLI y PTC. WP-CLI gestiona la generación de POT y la compilación de MO/JSON. PTC gestiona la traducción y devuelve todos los formatos de archivo que WordPress necesita. Poedit es un editor de escritorio útil para la traducción manual, pero no forma parte de este flujo de trabajo.
Traducción de archivos POT con PTC
PTC se ha diseñado pensando en los desarrolladores de WordPress. Comience con un archivo POT y reciba archivos de traducción listos para producción. La prueba gratuita de 30 días cubre hasta 20.000 palabras en dos idiomas.
Configure su primer proyecto de traducción
Suba su archivo POT. Elija qué formatos de salida necesita. PTC devuelve cualquier combinación de:
- Archivos
.popara cada idioma de destino. - Archivos
.mo, compilados y listos para enviar. - Archivos
.jsonpara sus cadenas de JavaScript. - Archivos
.l10n.phppara una carga más rápida en WordPress 6.5+.
El asistente de configuración le pedirá que describa su tema o plugin. PTC utiliza la descripción para generar traducciones con el tono y el contexto adecuados. Añada términos específicos de la marca al glosario en esta etapa. El glosario mantiene los nombres, las etiquetas de funciones y cualquier otra terminología consistente en todos los idiomas.
PTC analiza la estructura de gettext al subir el archivo. Reconoce marcadores de posición (%s, %1$s, %d), formas plurales (entradas extraídas con _n() con su cabecera Plural-Forms) y contextos (entradas _x() con msgctxt). A continuación, genera las categorías de plural correctas por idioma. El polaco obtiene one / few / many / other. El japonés obtiene solo other. El árabe obtiene seis formas.
Pase a la localización continua
Una vez traducidos sus primeros archivos, actualice al pago al consumo. Conecte PTC a su repositorio de GitHub, GitLab o Bitbucket. A partir de ese momento, no tendrá que subir archivos manualmente:
# .github/workflows/translate.yml
name: Regenerate POT for PTC
on:
push:
branches: [main]
paths:
- 'languages/my-plugin.pot'
jobs:
translate:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Generate POT
run: |
wp i18n make-pot . languages/my-plugin.pot --domain=my-plugin
- name: Trigger PTC translation
run: |
curl -X POST https://api.ptc.wpml.org/v1/projects/${{ secrets.PTC_PROJECT_ID }}/sync \
-H "Authorization: Bearer ${{ secrets.PTC_API_KEY }}"
Tiene dos formas de automatizar esto. Con la integración con Git, PTC vigila su repositorio y abre un pull request con las traducciones actualizadas cada vez que el archivo de origen cambia. Para ejecutar la traducción dentro de su propio trabajo de CI, utilice la CLI de PTC: esta sube el archivo modificado, espera a que finalice la traducción y descarga los archivos traducidos. En la guía de configuración de pipelines de CI/CD encontrará plantillas de flujo de trabajo listas para usar para GitHub Actions, GitLab CI y Bitbucket Pipelines.
Cualquiera de los flujos entrega un pull request o una descarga con los archivos .po, .mo, .json y .l10n.php actualizados. Consulte la referencia de la API de PTC para ver el webhook completo y la API REST.
El hecho de confirmar los archivos .mo en su repositorio depende de la política de su equipo. Muchos plugins los generan en el momento del lanzamiento. La integración de CI de PTC los produce en cada ejecución de traducción. Inclúyalos solo si desea tener los archivos traducidos en el historial de versiones.
Carga de traducciones en WordPress
Una vez disponga de los archivos traducidos, colóquelos correctamente e indique a WordPress dónde encontrarlos. El nombre del archivo es lo primero. WordPress busca los archivos de traducción utilizando un patrón de nomenclatura específico. Un nombre de archivo que no coincida significa que el archivo no se cargará.
Cómo nombrar correctamente sus archivos
Los códigos de configuración regional siguen el formato idioma_PAÍS. de_DE es alemán (Alemania). fr_FR es francés (Francia). pt_BR es portugués (Brasil). zh_CN es chino simplificado. El portal de traducción de WordPress enumera todos los locales compatibles.
El nombre de archivo esperado depende de dónde coloque el archivo:
| Ubicación | Patrón | Ejemplo |
|---|---|---|
Carpeta /languages/ del plugin |
{text-domain}-{locale}.mo |
my-plugin-de_DE.mo |
Carpeta /languages/ del tema |
{locale}.mo |
de_DE.mo |
Directorio global de idiomas de WordPress (/wp-content/languages/) |
{text-domain}-{locale}.mo |
my-plugin-de_DE.mo |
Los temas utilizan una convención de nomenclatura más corta cuando los archivos se incluyen dentro del tema. En el directorio global de idiomas, tanto los plugins como los temas utilizan el patrón {text-domain}-{locale}.
Carga de traducciones para plugins (PHP)
Registre las traducciones en WordPress en el hook init. No utilice plugins_loaded, ya que activa un aviso de obsolescencia en las versiones actuales de WordPress:
add_action( 'init', function () {
load_plugin_textdomain(
'my-plugin',
false,
dirname( plugin_basename( __FILE__ ) ) . '/languages/'
);
} );
Carga de traducciones para temas (PHP)
Utilice load_theme_textdomain() enganchado a after_setup_theme:
add_action( 'after_setup_theme', function () {
load_theme_textdomain( 'my-theme', get_template_directory() . '/languages' );
} );
Carga de traducciones de JavaScript
Después de registrar su script (Paso 3 anterior), llame a wp_set_script_translations(). WordPress cargará entonces las traducciones JSON para ese identificador de script:
add_action( 'init', function () {
wp_set_script_translations(
'my-plugin-script',
'my-plugin',
plugin_dir_path( __FILE__ ) . 'languages'
);
} );
Verifique la carga
- Establezca el idioma de su sitio WordPress en un locale de destino. El ajuste se encuentra en Ajustes > General > Idioma del sitio.
- Recargue el front-end y las páginas de administración que su plugin o tema renderiza.
- Las cadenas envueltas en
__()oesc_html__()deberían aparecer en el nuevo idioma.
Si falta algo, consulte ¿No aparecen las traducciones del plugin de WordPress? Solucione las traducciones que faltan para conocer las causas más comunes.
Idiomas de derecha a izquierda y diseños bidireccionales
El flujo de trabajo de traducción es el mismo para los idiomas de derecha a izquierda (RTL). El árabe, el hebreo, el persa y el urdu utilizan el mismo pipeline POT/PO/MO.
El paso adicional es asegurarse de que su tema admita estilos RTL. WordPress carga automáticamente un archivo rtl.css si existe en el directorio de su tema. Utilice la función is_rtl() para aplicar condicionalmente estilos o scripts específicos para RTL.
Localización de fechas, números y monedas
Una cadena traducida no lo es todo. Las fechas, los números y las monedas también deben seguir el locale del usuario. Utilice las funciones de formato integradas de WordPress en lugar de las nativas de PHP:
date_i18n()formatea las fechas según el locale activo.number_format_i18n()formatea los números con separadores de decimales y millares adaptados al locale.
Estas funciones no forman parte del flujo de trabajo de los archivos de traducción. Son importantes para una experiencia totalmente localizada.
Internacionalización de bloques del Editor de bloques (Gutenberg)
Los bloques añaden dos pasos adicionales al pipeline estándar:
- Las traducciones de JavaScript necesitan un archivo
.jsonpor locale. Genérelo a partir del.poconwp i18n make-json. - El script del editor del bloque necesita
wp_set_script_translations()en PHP. Esto indica a WordPress que sirva el JSON al bloque.
La salida renderizada por el bloque en el front-end utiliza las mismas llamadas __() que el resto de su PHP. No hay trabajo adicional ahí.
Traducción de su README y de la ficha de WordPress.org
Su archivo readme.txt no es un archivo de recursos. WP-CLI no lo detectará al generar un POT. Para traducirlo, utilice la función Pegar para traducir de PTC. Pegue el contenido, elija sus idiomas de destino y descargue el resultado. Los correos electrónicos para clientes enviados desde el plugin y la descripción de la página del plugin en WordPress.org se traducen de la misma manera, todo en el mismo proyecto para que la terminología sea consistente.
Si su plugin o tema aparece en WordPress.org, la descripción traducida aparecerá en la pestaña Detalles del plugin en el idioma del usuario. Para que las traducciones se publiquen allí, siga el proceso de importación de WordPress.org.
Traduzca el contenido de usuario del plugin con la API de PTC
Los plugins que almacenan datos generados por los usuarios (plugins de foros, de reseñas, de comentarios) pueden traducir ese contenido a medida que llega. La API REST de PTC traduce entradas, comentarios y reseñas de usuarios bajo demanda con autenticación mediante token Bearer, utilizando el mismo glosario y voz de marca que sus archivos .po.
Revisión visual de la traducción de su tema o plugin renderizado: publique sin control de calidad manual por idioma
Un archivo .po traducido es necesario, pero no suficiente. El tema o plugin traducido aún necesita verificación:
- Una etiqueta traducida puede desbordar un botón de la página de ajustes en alemán.
- “Submit” puede traducirse como un sustantivo en francés cuando la acción de administración requería un verbo.
- Una cadena en inglés codificada directamente fuera de
__()se renderizará sin traducir, independientemente de cuántos idiomas ofrezca.
La revisión visual de traducciones de PTC sustituye al paso de control de calidad manual. Los temas y plugins de WordPress se renderizan en el navegador (tanto en wp-admin como en el front-end). La opción adecuada es la extensión de navegador.
Instálela una vez. Grabe un recorrido por su tema o plugin en un sitio de prueba. Cubra las páginas de ajustes, las acciones de administración y la salida del front-end. PTC reproduce la grabación en cada idioma de destino después de cada actualización de traducción. Captura cada pantalla e informa de dos tipos de correcciones:
- Correcciones en los archivos
.pocuando PTC los controla. PTC vuelve a traducir un sentido erróneo, elige un sinónimo más corto que quepa en un botón o regenera una forma plural. - Prompts para Cursor o Claude Code cuando el problema reside en su código PHP o JavaScript. Los ejemplos incluyen un envoltorio
__()ausente, una cadena en inglés codificada directamente o una frase construida mediante concatenación que debería utilizarsprintf( __( ... ) ).
Usted publica un plugin verificado y multilingüe en cada lanzamiento. El trabajo pesado del control de calidad manual desaparece.
Precios: prueba gratuita de 30 días y después pago al consumo
La prueba gratuita cubre 20.000 palabras en 2 idiomas sin necesidad de tarjeta de crédito. Cuando finaliza la prueba, PTC ofrece el pago al consumo. Sin suscripción. Sin compromiso mínimo. Las primeras 500 palabras de cada mes son gratuitas. Solo paga por el resto. La página de precios tiene una calculadora de costes. Regístrese con un correo electrónico de empresa para obtener una prueba extendida para negocios.
¿Listo para publicar un plugin o tema verificado?
PTC genera las traducciones y revisa el plugin renderizado. Usted confirma el resultado y publica. El ciclo completo se ejecuta sin control de calidad manual:
- Genere su archivo
.potconwp i18n make-pot. - Súbalo a PTC y reciba los archivos
.po,.mo,.l10n.phpy.jsonen cuestión de minutos. - Instale la extensión de navegador para verificar el plugin en funcionamiento en cada idioma de destino.
Comience su prueba gratuita de 30 días: 20.000 palabras por nuestra cuenta, sin necesidad de tarjeta de crédito.
Relacionado:
- Traducir archivos PO online con IA: la página canónica de traducción de PO/POT.
- GlotPress frente a PTC para la traducción de plugins/temas de WordPress: cuándo elegir la traducción comunitaria frente a PTC.
- ¿No aparecen las traducciones del plugin de WordPress? Solucione las traducciones que faltan: guía de resolución de problemas.
- Cómo importar traducciones de temas y plugins a WordPress.org: proceso CLPTE y una alternativa más rápida.
- Referencia de la API de PTC: endpoints REST para la integración de CI.