Gettext avec PHP sur Windows 11
Oui, j'ai réussi, après avoir passé seulement 8 heures entre les tests et le débogage, j'ai réussi à activer gettext sur Windows pour mon environnement PHP local ! Si vous lisez ceci, j'imagine que vous vous battez aussi avec ça comme je l'ai fait aujourd'hui.
Remarque importante : Dans mon cas, j'ai utilisé Laragon et PHP 8.1.10 avec Apache comme serveur web. Cela peut fonctionner différemment avec d'autres environnements comme XAMP ou WAMP, ou avec Nginx et d'autres versions de PHP.
Table des matières
- Préparation de l'environnement PHP
- Format des langues régionales de Windows
- Comment gettext fonctionne avec PHP sous Windows
- Obtenir la langue de l'utilisateur à partir du navigateur
- Traduire automatiquement les fichiers PHP avec xgettext et msgfmt
- Modifier les variables système de l'environnement sous Windows
- Modifier la variable système PATH
- Ajouter une nouvelle variable avec le chemin des exécutables gettext
- Exécuter les commandes pour compiler et mettre à jour les fichiers PO automatiquement
- Traduire tous les fichiers PHP en une seule fois
- Compilation automatique des fichiers MO
- Supprimer les chaînes de caractères obsolètes qui ne sont plus nécessaires
- Comment traduire manuellement avec PoEdit
- Modifier les fichiers PO avec un éditeur de texte
- Conclusions
- Lire aussi
Préparation de l'environnement PHP
Tout d'abord, activons l'extension gettext dans PHP, en éditant le php.ini
# php.ini extension=gettext
Ensuite, nous vérifions qu'elle a bien été activée avec phpinfo:
// index.php phpinfo() ;
La sortie doit nous montrer que gettext est effectivement activé:
Vous pourriez aussi être intéressé par : Comment utiliser le suivi côté serveur de Matomo
Format des langues régionales de Windows
Je sais que cela peut paraître incroyable, mais l'utilisation de gettext dépend du format régional de la langue que nous avons sur Windows. J'ai passé des heures à arriver à cette conclusion, mais c'est ainsi, du moins pour moi.
Vérifions donc notre format régional :
Nous pouvons également trouver les codes de langue dans la documentation de Microsoft:
En général, nous n'avons besoin que des codes à deux lettres: "it" pour l'italien, "en" pour l'anglais, etc. Il se peut que vous deviez utiliser un code plus spécifique, comme "it-IT" ou "en-US". Sachez que Windows utilise le tiret alors qu'Unix utilise le trait de soulignement. Sous Linux, vous avez "fr_FR" alors que Windows a "fr-FR".
Nous utiliserons ce code avec setlocale en PHP et, comme nous allons le voir, pour le domaine textuel.
Comment fonctionne gettext avec PHP sous Windows
En bref : Supposons que nous ayons "italien" comme langue régionale (voir ci-dessus). Gettext cherchera les fichiers MO dans le dossier "it" dans le chemin que nous spécifierons en PHP avec les fonctions sur le domaine textuel :
$language = 'fr' ; // Français, ou je pourrais aussi utiliser fr-FR $domain = 'mydomain_' . $language ; // Le domaine sera mydomain_fr, donc PHP cherchera le fichier mydomain_fr.mo setlocale(LC_ALL, $language) ; bindtextdomain($domain, 'C:\laragon\usr\locale') ; // PHP cherchera dans ce chemin le dossier "it" basé sur le code de la langue du format régional de notre système textdomain($domain) ; bind_textdomain_codeset($domain, 'UTF-8') ; # Tous mes fichiers .mo doivent donc se trouver dans C:\laragon\usr\locale\it
Veuillez noter que sous Windows , nous utilisons LC_ALL, nous n'avons pas LC_MESSAGES ni LC_TIME qui sont utilisés sous Unix. LC_ALL est utilisé pour toutes les locales, comme indiqué dans la documentation PHP pour setlocale.
Après tout, gettext est un logiciel GNU.
Obtenir la langue de l'utilisateur à partir du navigateur
Si nous voulons connaître la langue dans laquelle l'utilisateur navigue, nous pouvons procéder comme suit :
$language = substr($_SERVER['HTTP_ACCEPT_LANGUAGE'], 0, 2) ;
Il s'agit simplement d'un en-tête envoyé par le navigateur, il peut ne pas être défini du tout, alors assurez-vous de définir une locale par défaut comme "en".
Avec cette configuration, nous devons avoir tous les fichiers .mo qui suivent cette structure :
C:\laragon\N - usr - locale - it (code de langue pour mon format régional sur Windows) .\mydomain_fr.mo ---> c'est le fichier qui va être chargé parce que j'ai fixélocale() à "fr" .\mydomain_it.mo .\nbsp;\nbsp;\n;\n;\n;\n;\n;\n;\n;\n;\n;\n;\n;\n;\n-es.mo
Nous pouvons changer le $domain pour utiliser un fichier MO différent pour un autre projet (myotherdomain_fr.mo) et nous pouvons changer le $language pour utiliser le fichier MO pour une autre langue (mydomain_es.mo).
Traduire automatiquement les fichiers PHP avec xgettext et msgfmt
Cette étape est facultative, elle n'est utile que si nous avons besoin de compiler et de mettre à jour automatiquement les fichiers PO, pour les nouvelles chaînes de texte que nous avons ajoutées dans notre site web ou application PHP.
Même sous Windows , nous pouvons effectuer les mêmes actions que sous Unix en utilisant xgettext et msgfmt.
Toutes les chaînes utilisées avec la fonction php gettext() ou avec son alias _() seront configurées dans un fichier PO pour être traduites, ce qui sera fait automatiquement, ce qui nous fera gagner beaucoup de temps !
Exemple de chaînes traduisibles :
# index.php _('Titre de la page') _('Mon texte') gettext('Un autre texte')
Voyons comment procéder :
- Nous allons télécharger gettext pour Windows à partir du dépôt Github de Michele Locali, que nous remercions pour cela. Si le téléchargement ne fonctionne pas, j'ai téléchargé la dernière version de gettext ici : gettext 0.21 Windows
- Alternativement, nous pouvons installer Poedit, un logiciel open source qui offre une interface graphique pour éditer des fichiers PO et générer des fichiers MO
- Dansle dossier d'installation de Poedit , nous trouverons GettextTools\bin où se trouvent les fichiers exécutables pour Windows (.exe.) pour xgettext et msgfmt.
- À ce stade, configurons le chemin d'accès dans les variables du système Windows. Vous trouverez ci-dessous les captures d'écran avec les étapes à suivre :
- Nous recherchons dans Windows l'option Editer les variables d'environnement
- Puis nous cliquons sur Variables d'environnement
- Dans les variables système, en bas, on modifie Path, ou on l'ajoute si absent
- On ajoute une nouvelle variable avec le chemin qui mène à Poedit\GettextTools\bin
En pratique, les variables Path sont utilisées pour rendre certaines commandes telles que xgettext et msgfmt exécutables depuis n'importe quel point du terminal, ou par exemple cwebp si l'on utilise les bibliothèques WebP, ou ffmpeg si l'on veut convertir une vidéo.
Modifier les variables système de l'environnement sous Windows
En utilisant la barre de recherche de Windows , nous pouvons ouvrir l'outil permettant d'éditer les variables du système:
Modification de la variable système PATH
Modifions la variable PATH pour notre système, ou éventuellement seulement pour notre utilisateur si nous le préférons :
Ajout d'une nouvelle variable avec le chemin des exécutables gettext
Nous ajoutons maintenant une nouvelle variable pour le chemin, en écrivant le chemin vers le dossier gettext avec les exécutables :
Je dois remercier l'utilisateur Desintegr de StackOverflow, c'est grâce à lui que j'ai découvert que les exécutables Windows se trouvaient dans le dossier GettextTools de Poedit.
Exécution des commandes pour compiler et mettre à jour les fichiers PO automatiquement
Après avoir effectué ces opérations pour définir globalement xgettext et msgfmt, passons à l'étape suivante. En fait, nous pourrions également lancer les exécutables directement à partir du dossier Poedit, mais il est beaucoup plus pratique de définir les variables d'environnement.
Si nous avons opté pour PoEdit, l'exécutable msgattrib n'est pas présent dans les GettextTools. Pour l'utiliser, nous devons télécharger gettext pour Windows à partir du dépôt Github de Michele Locali, comme nous l'avons déjà mentionné. Dans ce cas, la variable d'environnement Path doit pointer vers le chemin où nous avons placé gettext, par exemple C:\NProgrammes\Ngettext.
REM Traduire un seul fichier, un fichier PHP dans ce cas xgettext -d it -p \path\to\project\locale\it -L PHP --from-code=UTF-8 --no-location -j \path\to\project\index.php REM Compiler les fichiers MO msgfmt -D \path\to\project\locale\it it.po -o \path\to\project\locale\it\LC_MESSAGES\mydomain_it.mo
Note: Pour être détectées par gettext, les chaînes de caractères doivent être utilisées avec la fonction gettext() ou son alias _(). Voir la documentation de gettext.
Si vous obtenez une erreur "No such file or directory" pour le fichier PO, c'est probablement parce que nous devons d'abord créer le fichier PO, qui n'est pas créé par gettext, il doit déjà exister. Nous pouvons le créer comme un simple fichier texte ou utiliser PoEdit.
Traduire tous les fichiers PHP en une seule fois
Nous pouvons modifier ce code selon nos besoins et le sauvegarder dans un fichier .bat :
@echo off REM ici nous pouvons omettre le compte et la pause si ce n'est pas nécessaire SET count=1 REM demander la langue à l'utilisateur, comme es ou fr SET /p language=Enter language :
FOR /f "tokens=*" %%G IN ('dir *.php /b /s') DO (call :subroutine "%%G") pause GOTO :eof :subroutine REM ici on peut aussi omettre les commandes echo et set echo %count%:%1 REM on ajoute --no-location si on veut enlever du fichier PO le chemin où la traduction a été trouvée xgettext.exe -j %1 -d %language% -p \path\to\locale\it -L PHP --from-code=UTF-8 set /a count+=1 GOTO :eof
Ce fichier BAT sauvegardera dans \path\to\locale\it le fichier it.po avec toutes les chaînes précompilées pour chaque PHP trouvé. Nous pouvons éviter d'utiliser "pause" si nous voulons que le terminal soit fermé dès que la tâche est terminée.
Note: ce script recherche tous les fichiers PHP dans le même dossier et les sous-dossiers, à partir de l'endroit où se trouve le fichier BAT. Il est possible d'élargir ou de réduire l'étendue des dossiers en déplaçant simplement les fichiers BAT dans l'arborescence des dossiers.
Je dois remercier pour cela la documentation sur la boucle FOR sur CMD de SS64 car j'avais du mal à faire fonctionner la boucle, puis j'ai trouvé cette page et j'ai compris que je devais utiliser le sous-programme.
Le décompte est juste utile pour avoir un meilleur résultat dans l'invite de commande.
Nous ajoutons --no-location si nous voulons supprimer du fichier PO le chemin où la traduction a été trouvée.
L'erreur suivante peut être ignorée, elle est probablement causée par l'utilisation de l'attribut -j à l'intérieur de la boucle for.
Le jeu de caractères "CHARSET" n'est pas un nom d'encodage portable. La conversion du message vers le jeu de caractères de l'utilisateur risque de ne pas fonctionner.
Compilation automatique des fichiers MO
Si vous ne souhaitez pas utiliser PoEdit pour créer le fichier MO et que vous voulez le faire automatiquement, vous pouvez enregistrer ce code dans un fichier BAT, après l'avoir adapté à vos besoins :
@echo off REM demande la langue à l'utilisateur, comme es ou fr, et le domaine, par exemple "mon_projet" SET /p language=Enter language :
SET /p domain=Entrer le domaine : msgfmt -D \path\to\locale\%language% %language%.po -o \path\to\locale\%language%\LC_MESSAGES\mydomain_%language%.mo
Vous pouvez supprimer la langue et le domaine si vous préférez. Merci à Instantsoup de StackOverflow pour l'idée.
Supprimer les chaînes obsolètes qui ne sont plus nécessaires
REM Pour mettre à jour les fichiers PO, en supprimant les chaînes inutilisées trouvées dans les fichiers PHP : REM 1) Créer le PO SET /p sourcelanguage=Enter the language to refer to :
SET /p destinationlanguage=Entrer la langue de destination :
xgettext -d %sourcelanguage% -p \path\to\project\locale\%sourcelanguage% -L PHP --from-code=UTF-8 --no-location -j file.php REM 2) Faire une différence entre it.po et en.po, puis marquer comme obsolètes les chaînes supplémentaires qui ne sont pas dans it.po msgattrib --set-obsolete --ignore-file=\path\to\project\locale\%sourcelanguage%.po -o \path\to\project\locale\%destinationlanguage%.po \path\to\project\locale\%destinationlanguage%.po REM 3) Supprimer les chaînes obsolètes msgattrib --no-obsolete -o \path\to\project\locale\%destinationlanguage%.po \path\to\project\locale\%destinationlanguage%.po
Nous enregistrons le code ci-dessus sous la forme d'un fichier .bat, après l'avoir adapté à nos besoins.
En gros, après avoir créé le fichier PO, nous lançons msgattrib qui trouvera les chaînes qui sont toujours dans en.po mais qui ne sont plus dans it.po, marquera les chaînes supplémentaires comme obsolètes, et les supprimera.
Gardez à l'esprit que si msgattrib trouve des chaînes non traduites, où msgstr est vide, il supprimera ces chaînes.
Comment traduire manuellement avec PoEdit
Il est évident que tôt ou tard, nous devrons également traduire les textes, ou les confier à des traducteurs.
Les fichiersPO (Portable Object) sont "lisibles par l'homme", nous pouvons les ouvrir avec n'importe quel éditeur de texte et les modifier. Les fichiers MO (Machine Object) , en revanche, ne sont lisibles que par l'ordinateur, ce sont des fichiers binaires. Par ailleurs, les fichiers POT (Portable Object Template) constituent un modèle de départ pour la création de fichiers PO, mais ils sont facultatifs.
Voici un exemple de fichier PO :
# it.po msgid "This is a title" msgstr "Questo è un titolo" msgid "Some other text" msgstr "Dell'altro testo"
Nous avons donc le msgid qui indique la chaîne à traduire, et le msgstr qui indique la traduction effective dans la langue d'intérêt.
Nous pouvons éditer ces PO via l'éditeur ou avec PoEdit: sachez qu'avec PoEdit, nous ne pouvons éditer que les traductions finales, et non les chaînes de caractères originales :
En haut se trouvent les chaînes de caractères présentes dans le PO, en bas le texte source (msgid) et la traduction (msgstr).
Sur la droite, nous avons également les traductions suggérées, qui sont toutefois une fonctionnalité payante.
Nous sauvegardons le fichier PO et le fichier MO sera automatiquement généré dans le même dossier. Nous pouvons également générer uniquement le fichier MO en allant dans Fichier > Compiler MO.
Modifier les fichiers PO avec un éditeur de texte
Comme nous l'avons vu, nous pouvons modifier les fichiers PO avec n'importe quel éditeur. Personnellement, j'utilise VSCodium et j'ai installé l'extension gettext pour la coloration syntaxique. On peut aussi utiliser Notepad++ ou le bon vieux Notepad de Windows.
Lorsque nous avons terminé, nous pouvons sauvegarder le fichier PO en écrasant le précédent. Pour le convertir en MO, nous devrons utiliser PoEdit ou lancer la commande msgfmt.
Conclusions
Ce qui compte vraiment, c'est que tous les fichiers MO se trouvent dans le même dossier, en fonction de notre format régional Windows!
Si cet article vous a été utile, suivez-moi sur Facebook et Youtube! Laissez un commentaire ci-dessous pour me dire ce que vous en pensez, ou si vous avez eu des difficultés à installer gettext !
A lire également
- Comment convertir les fichiers WEM en fichiers audio lisibles OGG et MP3
- Comment fusionner plusieurs vidéos facilement et rapidement avec FFMPEG concatenate
Si vous le pouvez, soutenez mon travail! Crédits de l'image de prévisualisation : Unsplash