2011-11-07 7 views
12

Estoy desarrollando una aplicación web PHP multilingüe, y tengo textos largos (-ish) que necesito traducir con gettext. Estas son plantillas de correo electrónico (generalmente cortas, pero aún varias líneas) y partes de la vista (bloques de texto descriptivos más largos). Estos textos incluirían algo de HTML simple (cosas como negrita/cursiva para enfatizar, probablemente un enlace aquí o allá). Las plantillas son scripts PHP cuyo resultado se captura.Traduciendo textos largos (ver y enviar plantillas de correo electrónico) con gettext

El problema es que gettext parece muy torpe para manejar textos más largos. Los textos más largos generalmente tendrían más cambios a lo largo del tiempo que los textos cortos: puedo cambiar el msgid y asegurarme de actualizarlo en todas las traducciones (podría ser un montón de trabajo y muy propenso a errores cuando el msgid es largo), o puedo mantener el msgid no se modifica y solo modifica las traducciones (lo que dejaría textos obsoletos engañosos en las plantillas). Además, he visto consejos contra incluir HTML en cadenas de texto, pero evitarlo sería romper una sola pieza de texto natural en muchos trozos, lo que será una pesadilla aún mayor para traducir y volver a montar, y también he visto consejos contra división innecesaria de cadenas de texto gettext en archivos separados.

El otro enfoque que veo es ignorar el texto completo para estos textos más largos, y separar esos bloques en subtemplates externos para cada configuración regional, e incluir solo el de la configuración regional actual. La desventaja es que estoy separando el esfuerzo de traducción entre los archivos gettext .po y las plantillas separadas ubicadas en una ubicación completamente diferente.

Dado que esta aplicación se utilizará como punto de partida para otras aplicaciones en el futuro, estoy tratando de encontrar el mejor enfoque a largo plazo. Necesito algunos consejos sobre las mejores prácticas en dichos escenarios. ¿Cómo has implementado casos similares? ¿Qué resultó funcionar y qué resultó una mala idea?

+1

Relacionado: [Cómo trabajar eficazmente con los archivos PO de gettext al realizar pequeñas ediciones en valores de texto grandes] (http://stackoverflow.com/questions/2966026/), [Combinación de claves y texto completo cuando se trabaja con gettext y. archivos po] (http://stackoverflow.com/questions/15743919/), [¿Es una buena idea que el ID del mensaje sea el texto en inglés?] (http://stackoverflow.com/questions/216478/), [¿Puedo actualizar automáticamente los archivos .god de gettext para cambios de texto triviales?] (Http://stackoverflow.com/questions/8288050/) – ento

Respuesta

9

Aquí está el flujo de trabajo he utilizado, en un sitio muy traficada fuertemente que tenía sobre varios bloques docena de largo ish de contenido textual de estilo, traducido a seis idiomas:

  1. elegir un lenguaje de marcado basado en texto (utilizamos Markdown)
  2. Para cadenas largas, utilizamos identificadores de mensajes fijos, como "About_page_intro_markdown" que:
    • describe la intención del texto
    • deja claro que será interpretado en formato de rebajas
  3. tener nuestra aplicación render "* _markdown" cuerdas adecuadamente, asegurándose de permitir que sólo unas pocas etiquetas HTML seguras
  4. construir una herramienta para los traductores que:
    • ellos muestra su Markdown dictada en tiempo real (algo así como el Markdown dingus)
    • hace que sea fácil para ellos ver la traducción en idioma base ahora autorizada del texto (puesto que ya no está en el msgid)
  5. traductores mostrarán cómo utilizar el nuevo flujo de trabajo

Pros de este flujo de trabajo:

  • identificadores de mensaje no cambian todo el tiempo
  • Debido a que los traductores están editando en un nivel más alto de seguridad sintaxis, difícil de estropear HTML
  • Los traductores no técnicos encontraron muy fácil escribir en Markdown, frente a HTML

contras de este flujo de trabajo:

  • Tener identificadores de mensaje que no cambian estáticas significa cambios en el texto deben ser transmitida fuera de banda (que nos gustaría hacer de todos modos, como texto tiempo puede plantear preguntas sobre el tono o énfasis)

Estoy muy contento con la forma en que funciona este flujo de trabajo para nuestro sitio web, y lo recomiendo totalmente, y lo vuelva a utilizar. Tomó un par de días para comenzar, pero fue fácil de construir, entrenar y lanzar.

Espero que esto ayude, y buena suerte con su proyecto.

+0

Su enfoque es realmente interesante, pero tengo una duda. ¿Es este enfoque totalmente independiente de gettext o pretende funcionar con él? Si está destinado a trabajar con gettext. ¿Dónde está la conexión? Probablemente me estoy perdiendo algo. – lordscales91

+0

@ lordscales91Este flujo de trabajo puede funcionar bien con gettext o cualquier sistema equivalente, siempre y cuando construya las herramientas adicionales descritas en los pasos 3 y 4. – Anirvan

3

gettext no fue diseñado para traducir grandes piezas de texto.

fwiw He incluido HTML básico (strong, a, etc.) en gettext strings ya que estaba seguro de que nuestros traductores sabían lo que estaban haciendo (sobre todo correcto) y que las traducciones serían bien probadas.

He intentado el enfoque de dividir el texto en una cadena por párrafo. A grandes rasgos, parece extraño si hay un párrafo de inglés en el medio del texto. Donde una de esas cadenas ha cambiado esto ha significado que hemos tenido que esperar por traducciones antes de lanzar una nueva versión, lo que nos ha retrasado. En el lado positivo, es fácil para los traductores ver qué parte del texto ha cambiado. Este enfoque funcionó bien para la única aplicación con la que lo probé.

Dividir parte del texto en ubicaciones externas también funcionó, pero causó una sobrecarga de administración, en lugar de solo un archivo .po o dos, había un montón de otro texto que tenía que ser comparado manualmente con la versión en inglés y actualizado en consecuencia. Esto es factible si recuerda proporcionar notas a sus traductores explicando dónde y cuál fue la diferencia en la versión en inglés.

Todavía no me venden en ninguno de los dos enfoques.

5

Acabo de tener este problema en particular, y creo que lo resolvió de una manera elegante.

El problema: queríamos usar Gettext en PHP, y usar cadenas de lenguaje principal como traducciones de claves. Sin embargo, para grandes bloques de HTML (con H1, H2, P, A, etc ...) Me o bien tienen que:

  • crear una traducción para cada etiqueta con el contenido.

o

  • poner toda la cuadra con etiquetas en una traducción.

Ninguna de esas opciones me atrajo, así que esto es lo que hice:

  • Mantener cadenas simples ("OK", "Añadir", "Confirmar", "Mi impresionante App") como entradas normales de Gettext .po, con el texto original como la clave
  • Escriba el contenido (bloques de texto grande) en el marcado y guárdelos en los archivos. Ejemplo archivos serían /homepage/content.md (texto primario/fuente), /homepage/content.da-DK.md, /homepage/content.de-DE.md

  • escribir una clase que recupera los archivos de contenido (para la localización actual) y lo analiza. Yo entonces lo utilizó gusta:

    <?=Template::getContent("homepage/content")?>

Sin embargo, ¿qué pasa con el texto grande dinámico? Sencillo. Use un motor de plantillas. Decidí Smarty, y lo usé en mi clase Template.

Ahora podría usar la lógica de plantillas ... dentro de la marca de reducción! ¡Qué maravilloso es eso!

Entonces vino la parte difícil ..

Para que el contenido se ve bien, a veces se necesita para estructurar el código HTML de forma diferente. Considere un área de campaña con 3 "cajas de características" debajo de ella. La solución fácil: tenga un archivo para el área de la campaña, y uno para cada de las 3 casillas.

Pero podría hacerlo mejor que eso.

Escribí un analizador de bloques rápido, así que escribía todo el contenido en un solo archivo y luego procesaba cada bloque por separado.

Ejemplo archivo:

[block campaign] 
Buy this now! 
============= 

Blaaaah... And a smarty tag: {$cool} 
[/block] 

[block feature 1] 
Feature 1 
--------- 

asdasd you get it.. 
[/block] 

[block feature 2] ... 

Y así es como me gustaría hacerlas en el marcado:

<?php 
// At the top of the document... 

// Class handles locale. :) 
$template = Template::getContent("homepage/content", [ 
    "cool" => "Smarty variable! AWESOME!" 
]); 
?> 

... 

<title><?=_("My Awesome App")?></title>  

... 

<div class="hero"> 
    <!-- Template data already processed! :) --> 
    <?=$template->renderBlock("campaign")?> 
</div> 
<div class="featurebox"> 
    <?=$template->renderBlock("feature 1")?> 
</div> 
<div class="featurebox"> 
    <?=$template->renderBlock("feature 2")?> 
</div> 

Me temo que no puedo proporcionar cualquier código fuente, ya que esto era para un proyecto de la compañía, pero espero que entiendas la idea.

Cuestiones relacionadas