Comment structurez-vous les fichiers i18n yaml dans Rails?

J’ai commencé à remplir un fichier en yaml dans Rails et je peux déjà dire qu’il sera désordonné et déformé avant longtemps. Existe-t-il une convention pour conserver ce fichier organisé?

Jusqu’à présent, j’ai cette structure:

language: resource: pages: # index, show, new, edit page html elements: # h1, title activerecord: atsortingbutes: model: property: 

Maintenant, j’ai les choses suivantes que je veux intégrer dans cette structure, mais je ne sais pas comment:

  1. La navigation
  2. Texte du bouton (enregistrer les modifications, créer un compte, etc.)
  3. Messages d’erreur du contrôleur flash
  4. Comment append des clés multi-mots. Est-ce que j’utilise un espace ou un soulignement? Pour exmaple, t(".update button") ) ou t(".update_button")

Existe-t-il une convention pour la structure des fichiers de parameters régionaux?

J’ai trouvé que la meilleure stratégie globale consiste à reproduire quelque peu la structure du fichier afin que, quelle que soit la traduction, je puisse immédiatement trouver d’où elle provient. Cela me donne une sorte de contexte pour faire la traduction.

La majorité des traductions d’applications se trouvent dans des vues, donc mon plus grand espace de noms de niveau supérieur est généralement les views .

Je crée des sous-espaces de noms pour le nom du contrôleur et le nom de l’action ou partiel étant utilisé ex:

  • views.users.index.title
  • views.articles._sidebar.header

Ces deux exemples devraient indiquer clairement quelle partie de mon application nous traduisons et quel fichier rechercher pour le trouver.

Vous mentionnez la navigation et les boutons, s’ils doivent être génériques, ils appartiennent alors à l’ views.application noms views.application tout comme leurs homologues de vue:

  • views.application._main_nav.links.about_us – un lien dans la navigation principale de notre application partielle
  • views.application.buttons.save
  • views.application.buttons.create – J’ai un tas de ces boutons prêts à être utilisés en cas de besoin

Les messages Flash sont générés à partir du contrôleur, leur espace de noms de premier niveau est donc … des controllers ! 🙂

Nous appliquons la même logique aux vues:

  • controllers.users.create.flash.success|alert|notice

Encore une fois, si vous souhaitiez fournir des messages flash génériques tels que “Opération réussie”, vous écririez quelque chose comme ceci:

  • controllers.application.create.flash.notice

Enfin, les clés peuvent être tout ce qui est valide en YAML, mais veuillez vous en tenir aux périodes . comme séparateurs et soulignés _ entre les mots comme une question de convention.

La seule chose qu’il rest à régler maintenant, c’est de faire traduire les rails dans son propre espace de noms pour nettoyer notre niveau supérieur 🙂

Je sais qu’une réponse a déjà été acceptée, mais cette question m’a donné matière à reflection et je pensais partager une autre structure pour les fichiers Rails i18n yml pour votre considération / critique.

Étant donné que je voudrais

  1. conserver la structure par défaut de l’application afin que je puisse utiliser des recherches “paresseuses” comme t('.some_translation') dans mes vues,
  2. éviter autant de répétitions de chaînes que possible, en particulier avec des mots qui ne sont pas les mêmes, mais qui ont également des contextes / significations identiques,
  3. il suffit de changer une clé une fois pour la faire refléter partout où elle est référencée,

pour un fichier config / locales / en.yml qui ressemble à ceci:

 activerecord: atsortingbutes: user: email: Email name: Name password: Password password_confirmation: Confirmation models: user: User users: fields: email: Email name: Name password: Password confirmation: Confirmation sessions: new: email: Email password: Password 

Je peux voir qu’il y a une répétition significative, et que le contexte des mots comme “Email” et “Password” sont sans ambiguïté et ont la même signification dans leurs vues respectives. Ce serait un peu ennuyeux de devoir les changer tous si je décidais de changer “Email” en “E-mail”, donc je voudrais refactoriser les chaînes pour faire référence à un dictionnaire quelconque. Alors, que diriez-vous d’append un hachage de dictionnaire en haut du fichier avec certains & ancres comme ceci:

 dictionary: email: &email Email name: &name Name password: &password Password confirmation: &confirmation Confirmation activerecord: atsortingbutes: user: email: *email name: *name password: *password password_confirmation: *confirmation models: user: User users: fields: email: *email name: *name password: *password confirmation: *confirmation sessions: new: email: *email password: *password 

Chaque fois que vous obtenez plus d’une instance de exactement le même mot / phrase dans vos vues, vous pouvez la réorganiser dans le dictionnaire. Si la traduction du dictionnaire d’une clé dans la langue de base n’a pas de sens pour une langue cible, remplacez simplement la valeur référencée dans la langue cible par une chaîne statique ou ajoutez-la comme entrée supplémentaire dans le dictionnaire de la langue cible. Je suis sûr que le dictionnaire de chaque langue pourrait être refait dans un autre fichier s’ils deviennent trop gros et trop lourds.

Cette façon de structurer les fichiers i18n yaml semblait bien fonctionner avec certaines applications de test locales que j’ai essayées. J’espère que le merveilleux Localeapp apportera son soutien à ce type d’ancrage / de référencement dans le futur. Mais de toute façon, toute cette conversation de dictionnaire ne peut pas être une idée originale, alors y a-t-il d’autres problèmes avec le référencement d’ancrage dans YAML, ou peut-être simplement avec le concept “dictionnaire” en général? Ou est-il juste préférable de simplement extraire entièrement le backend par défaut et de le remplacer par Redis ou quelque chose du genre ?

Votre question n’est pas facile à répondre et il n’y a pas beaucoup de matériel disponible sur ce sujet. J’ai trouvé les meilleures ressources:

  • Rails Styleguide , section Internationalisation
  • Il y a beaucoup de ressources dans le wiki I18n , mais je n’y ai pas trouvé de réponses à vos questions.

Je vais donc essayer directement ici:

  • La navigation

    Je pense que vous voulez dire ici les éléments de navigation comme le fil d’Ariane, les tabs, … Vous devez définir des vues pour eux, puis coller la règle pour déplacer tous les éléments de vue dans des fichiers séparés dans les views répertoire (voir le guide de style). .

  • Texte du bouton (enregistrer les modifications, créer un compte, etc.)

    Voir les éléments, aller aussi dans les mêmes fichiers. Si vous utilisez les mêmes boutons dans différentes vues, définissez un fichier commun et utilisez-le ensuite.

  • Messages d’erreur du contrôleur flash

    J’utiliserais la même règle que pour les vues. Définir un répertoire séparé, y inclure les fichiers pour les contrôleurs.

  • Comment append des clés multi-mots. Est-ce que j’utilise un espace ou un soulignement? Pour exmaple, t (“. Update button”)) ou t (“. Update_button”)

    .update_button , je préférerais utiliser le .update_button , pas le .update button , car cela rend plus explicite que c’est une clé.

Cela fait presque deux ans que j’ai posé cette question et je veux partager quelques idées. Je pense que la structure optimale consiste à nommer les traductions en fonction de leur rôle MVC (modèles, vues, contrôleurs). Cela permet de conserver le fichier de parameters régionaux et d’empêcher les collisions d’espaces de noms (par exemple, la scope en.users peut représenter une vue ou un contrôleur).

 en: controllers: users: show: welcome_flash: "Welcome back!" mailers: users_mailer: welcome_email: subject: "Good of you to join us" views: users: show: notice: "Oh no! 

Mais en utilisant des espaces de noms propres comme celui-ci, la fonctionnalité de recherche paresseuse dans Rails est interrompue. Si vous utilisez la recherche paresseuse, Rails insérera automatiquement l’espace de noms pour vous et n’inclura pas les espaces de noms de premier niveau que vous avez créés ( views , controllers , etc.).

Par exemple, la scope de t('.welcome_flash') se en.users.show à en.users.show . Ce qui pue parce que les utilisateurs ne sont pas clairement définis. Qu’Est-ce que c’est? Un contrôleur? Une vue? Autre chose?

Pour résoudre ce problème, j’ai créé le joyau I18nLazyLookup . Il vous permet d’utiliser la recherche paresseuse avec vos propres espaces de noms personnalisés.

Au lieu d’utiliser t , vous pouvez utiliser t_scoped('welcome_flash') , ce qui résoudra automatiquement la scope en en.controllers.users.show . Cela fonctionne également pour les vues et les mailers, et vous pouvez personnaliser l’espace de noms comme vous le souhaitez.

Modifier directement les fichiers yaml conduit à des fichiers désordonnés et illisibles.
De plus, il vous sera difficile de donner access à des traducteurs si, un jour, vous souhaitez qu’un non-développeur ajoute une nouvelle langue.

Je recommande d’utiliser localeapp , qui génère un seul fichier yaml.
Mais vous permet de voir et de gérer facilement vos traductions dans une interface Web.
Et pour créer un access supplémentaire aux traducteurs.

Plusieurs années après la bataille, voici une réponse (quelque peu totalement différente).

Pour commencer, je n’aime pas le style standard t('.xxx') avec l’espace de nommage par défaut basé sur la structure de fichier. Je n’aime pas non plus la catégorisation des traductions en fonction de la structure DOM. Bien que ce soit une approche intéressante pour les traductions très structurées, elle est souvent répétitive et peu intuitive.

Je préfère regrouper mes traductions dans des catégories plus utiles, afin de faciliter la tâche de mes traducteurs, car ils peuvent travailler sur des thèmes concrets, plutôt que sur des styles étranges (certains traducteurs ne savent même pas ce que signifie MVC)

donc mon fichier de traduction est structuré comme ceci

 fr: theme1: theme11: translationxxx: blabla theme2: translationyyy: blabla 

Selon les besoins, les «thèmes» peuvent être un modèle, un contexte plus abstrait, etc., le plus intuitif pour les traducteurs.

Étant donné que ce serait fastidieux d’écrire à chaque fois la scope de mes vues, j’ai ajouté des méthodes pratiques dans mes assistants pour créer un contexte de traduction basé sur la stack.

  • Je pousse / pop les étendues de traduction sur une stack dans mes vues en appelant t_scope([new_scope] et pop_t
  • Je remplace le t helper pour utiliser le dernier domaine de la stack

Le code pour les méthodes de définition de la traduction est disponible dans cette réponse.