Miten automatisoida .po-tiedostojen kääntäminen CI/CD-putkessasi

Tiimisi yhdistää muutoksia main-haaraan neljätoista kertaa päivässä. Jokainen näistä yhdistämisistä voi lisätä uuden käyttäjälle näkyvän merkkijonon – painikkeen tekstin, virheilmoituksen, työkaluvinkin. Ja jokainen näistä merkkijonoista alkaa elämänsä vain englanniksi. Jossain julkaisuprosessissasi ihmisen on huomattava uudet merkkijonot, vietävä ne, käännätettävä ne, liitettävä ne takaisin ja käännettävä uudelleen. Tämä ihminen on pullonkaula, ja nopeasti toimituksia tekevässä tiimissä tämä pullonkaula tarkoittaa, että saksalaiset käyttäjät näkevät englanninkielisiä paikkamerkkejä kahden sprintin ajan.
Ratkaisu on automatisoida käännökset CI/CD -putkessasi niin, että uudet merkkijonot käännetään samassa yhdistämisessä, jossa ne esiteltiin – ilman ihmistä kriittisellä polulla rutiinitapauksissa. Tämä on täysin saavutettavissa tänään, mutta vain jos vältät ansaa, johon useimmat tiimit lankeavat: käsin kirjoitettuja raakoja LLM-kutsuja, jotka hiljaa vioittavat %s-paikkamerkkejäsi ja .po-rakennettasi. Tämä opas käy läpi realistisen CI-putkimallin, toimivan GitHub Actions -rungon ja suunnittelupäätökset – idempotenttisyys, vain uusien kääntäminen, tarkistusportit – jotka erottavat auttavan putken sellaisesta, joka tuottaa rikkinäisiä koontiversioita.
Miksi manuaalinen käännös on julkaisujen pullonkaula
Vastaus kysymykseen "miksi ei vain kääntää ennen jokaista julkaisua" on, että ajoitus ei koskaan osu kohdalleen. Kehittäjät lisäävät merkkijonoja jatkuvasti, mutta käännökset tehdään erissä eri henkilön toimesta eri aikataululla. Näiden kahden rytmin välinen kuilu on se, missä lokalisointivelkasi kasautuu.
Kahden rytmin ongelma
Kuvittele manuaalinen työnkulku. Kehittäjä lisää __( 'Export to CSV', 'mytextdomain' ) ja yhdistää muutoksen. Kukaan ei luo uudelleen .pot-tiedostoa. Kaksi viikkoa myöhemmin joku ajaa wp i18n make-pot, huomaa neljäkymmentä uutta kääntämätöntä merkkijonoa (joista osa on peräisin kehittäjiltä, jotka ovat sittemmin lähteneet lomalle), arvailee puolet niiden tarkoituksesta ja lähettää .po-tiedoston kääntäjälle. Käännös palautetaan, liitetään paikalleen, ja ehkä paikkamerkit säilyivät ehjinä ja ehkä eivät. Samaan aikaan kolme julkaisua toimitettiin kyseisillä merkkijonoilla englanniksi.
Jokainen askel on manuaalinen, eräajona suoritettava ja virhealtis. CI/CD-automaation tavoitteena on tiivistää tämä joksikin, joka suoritetaan automaattisesti yhdistämisen yhteydessä, kääntää vain todella muuttuneet asiat ja epäonnistuu äänekkäästi, kun jokin näyttää väärältä – muuttaen käännöksen määräajoin toistuvasta rutiinista näkymättömäksi osaksi putkea.
Putkimalli: Poimi, Vertaa, Käännä, Tallenna
Korkealla tasolla automatisoitu käännöstyö suorittaa neljä vaihetta main-haaraan yhdistettäessä: luo mallipohjan uudelleen, tunnistaa uudet asiat, kääntää vain kyseiset merkkijonot ja tallentaa tulokset takaisin. Koko prosessin tulisi olla idempotentti – sen ajaminen yhdistämisessä ilman merkkijonomuutoksia ei saa tuottaa eroja eikä ylimääräistä.
Poimi ja Vertaa
Ensimmäinen vaihe on poiminta. Luo .pot-tiedosto uudelleen nykyisestä lähdekoodista niin, että se heijastaa jokaista koodikannan merkkijonoa:
wp i18n make-pot . languages/myplugin.pot
Toinen vaihe on vertailu. Tämä on koko putken tärkein suunnittelupäätös. Et halua kääntää uudelleen jokaista merkkijonoa jokaisella yhdistämiskerralla – se kuluttaa API-kutsuja, uhkaa kääntää uudelleen merkkijonoja, jotka ihminen on jo korjannut, ja tuottaa valtavia tarkistuseroja. Sen sijaan yhdistät tuoreen .pot-tiedoston jokaiseen olemassa olevaan .po-tiedostoon ja käännät vain ne merkinnät, jotka ovat nyt tyhjiä (aidosti uudet merkkijonot):
# Merge new template into each locale, preserving existing translations.
# Newly-added strings appear with empty msgstr; --backup=none keeps the tree clean.
for po in languages/*.po; do
msgmerge --update --backup=none "$po" languages/myplugin.pot
done
Kun msgmerge on suoritettu, vain upouusissa merkkijonoissa on tyhjä msgstr. Kaikki aiemmin käännetyt jäävät koskemattomiksi. Tämä ominaisuus tekee putkesta idempotentin ja pitää tarkistuserot pieninä ja tarkistettavina.
Käännä ja Tallenna
Kolmas vaihe lähettää juuri nämä tyhjät merkinnät käännösvaiheeseen. Neljäs vaihe tallentaa päivitetyn .po-tiedoston, kääntää .mo-tiedoston ja luo uudelleen kaikki JSON-tiedostot. Kytkemme kaiken tämän seuraavaksi GitHub Actionsiin.
GitHub Actionsin runko
Tässä on vastaus kysymykseen "miltä tämä todellisuudessa näyttää työnkulkutiedostossa": työ, joka käynnistyy muutoksen pushauksesta main-haaraan ja suorittaa poimi-vertaa-käännä-tallenna -syklin ja avaa pull requestin tuloksilla sen sijaan, että tallentaisi suoraan main-haaraan.
Työnkulkutiedosto
name: Translate on merge
on:
push:
branches: [ main ]
jobs:
translate:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Install WP-CLI and gettext
run: |
sudo apt-get update && sudo apt-get install -y gettext
curl -O https://raw.githubusercontent.com/wp-cli/builds/gh-pages/phar/wp-cli.phar
sudo mv wp-cli.phar /usr/local/bin/wp && sudo chmod +x /usr/local/bin/wp
- name: Regenerate template and merge into locales
run: |
wp i18n make-pot . languages/myplugin.pot
for po in languages/*.po; do
msgmerge --update --backup=none "$po" languages/myplugin.pot
done
- name: Translate only new (empty) strings
env:
TRANSLATE_API_KEY: ${{ secrets.TRANSLATE_API_KEY }}
run: ./scripts/translate-new-strings.sh languages/
- name: Compile .mo and JSON
run: |
wp i18n make-mo languages/
wp i18n make-json languages/ --no-purge
- name: Open pull request with translations
uses: peter-evans/create-pull-request@v6
with:
branch: chore/auto-translations
title: "chore: auto-translate new strings"
commit-message: "chore: auto-translate new strings"
Missä todellinen työ piilee
Vaihe translate-new-strings.sh on se, missä varsinainen käännös tapahtuu. Naiivi versio kyseisestä skriptistä lukee jokaisen tyhjän merkinnän, lähettää sen LLM API:lle merkkijono kerrallaan ja liittää vastauksen takaisin. Tuo naiivi versio on juuri se ansa, ja on syytä selittää miksi.
Miksi käsin kirjoitetut LLM-kutsut rikkovat tiedostojasi
Lyhyt vastaus: raa'at LLM-kutsut käsittelevät .po-merkkijonojasi proosana, mutta .po-merkkijonosi eivät ole proosaa – ne ovat strukturoitua dataa, jossa on paikkamerkkejä, monikkomuotoja ja kontekstia, jotka chat-pohjainen käännös mielellään tuhoaa.
Paikkamerkkien vioittuminen, jota et näe testeissä
Lähetä Deleted %d of %s files yleiseen chat-päätepisteeseen, ja saatat saada takaisin Supprimé %d des %s fichiers (hyvä) tai Supprimé %d de % s fichiers (välilyönti hiipi paikkamerkkiin, ja nyt sprintf() heittää virheen suorituksen aikana). Lähetä monikkomuotoinen merkintä, ja malli voi yhdistää kaksi muotoa yhdeksi, mikä rikkoo kieliä, joissa on enemmän kuin kaksi monikkoluokkaa. Lähetä merkkijono, jossa on <a href="%s">, ja malli saattaa kääntää URL-osoitteen tai pudottaa tunnisteen. Yksikään näistä virheistä ei näy testeissäsi, ellet erikseen testaa renderöityä tulostetta jokaisella lokalisoinnilla – ne ilmestyvät suoritusaikaisina virheinä tuotannossa käyttäjille, joilta et voi lukea virheraportteja.
Ylläpidon ansa
Voit yrittää puolustautua tätä vastaan prompt engineeringin ja regex-jälkikäsittelyn avulla, ja monet tiimit tekevät niin. Ongelmana on, että ylläpidät nyt haurasta käännöskonetta sivuhankkeena, löytäen uudelleen jokaisen paikkamerkin reunaehdon, jonka Gettext-ekosysteemi on jo ratkaissut. Kartoitamme tarkat tavat, joilla muuttujat vääristyvät – ja miten ne estetään – artikkelissa PO-tiedostojen kääntäminen rikkomatta koodimuuttujia. Opetus pätee suoraan: mallin laatu on harvoin ongelma; pikemminkin sen ympärillä oleva rakenteellinen käsittely.
API-pohjaisen pilvikääntäjän integrointi CI:hin
Tässä API-pohjainen käännöspalvelu korvaa translate-new-strings.sh-arvailusi. Sen sijaan, että kirjoittaisit käsin LLM-kutsuja ja jälkikäsittelisit regex-säännöillä, CI-vaiheesi lataa muuttuneen .po-tiedoston palveluun, joka jo ymmärtää Gettext-rakenteen ja palauttaa siistin tuloksen. Putken muoto pysyy identtisenä – poimi, vertaa, käännä, tallenna – mutta hauraasta välivaiheesta tulee yksi API-kutsu.
API-kutsu, joka korvaa skriptisi
SimplePoTranslate on rakennettu juuri tähän tarkoitukseen. Se tarjoaa pilvi-API:n, joka soveltuu automaatioon ja CI:hin, joten työnkulkusi käännösvaiheesta tulee pyyntö, joka luovuttaa .po-tiedoston ja saa takaisin käännetyn, ilman merkkijonokohtaista silmukointia. Sen Syntaksin lukitus pitää %s, %1$s, {count}, HTML- ja kooditunnukset paikallaan automaattisesti – koko edellisen osion virheluokka hoidetaan koneella, ei ylläpitämälläsi regexillä. Täydellä Gettextin monikko- ja msgctxt-tuella monikkomuodot ja konteksti selviävät edestakaisesta matkasta, mitä chat-pohjainen käännös ei voi taata.
Idempotenttisyys ja tarkistusportti pysyvät sinun hallinnassasi
Kaksi suunnittelupäätöstä kuuluu edelleen sinulle riippumatta siitä, mitä moottoria käytät. Ensimmäinen, idempotenttisyys: jatka vain tyhjien merkintöjen kääntämistä msgmerge-komennon jälkeen, jotta tyhjäkäyntiä tekevät yhdistämiset eivät tuota eroa. Toinen, tarkistusportti: anna työn avata pull request, kuten yllä oleva runko tekee, sen sijaan, että tallentaisit suoraan main-haaraan. Konekäännös on erinomainen merkkijonojen nopeaan julkaisuun, mutta ihmisen silmäys ennen yhdistämistä havaitsee harvinaisen kontekstin puutteen – ja PR antaa sinulle tämän silmäyksen estämättä yleistä tapausta. Tiimit, jotka käsittelevät monia lokalisointeja tai useita asiakassivustoja, tunnistavat tämän muodon ihanteellisesta lokalisointityönkulusta toimistoille, jossa sama automatisoi-sitten-tarkista -malli skaalautuu kymmeniin projekteihin.
Yhteenveto
Jotta voit automatisoida käännökset CI/CD:ssä ilman rikkinäisiä julkaisuja, malli on johdonmukainen: luo .pot-tiedosto uudelleen yhdistämisen yhteydessä, yhdistä se msgmerge-komennolla kuhunkin lokalisointiin, jotta vain uudet merkkijonot tulevat esiin, käännä vain kyseiset merkkijonot ja tallenna tulos pull requestin tarkistusportin taakse. Idempotenttisyys pitää erosi puhtaina; tarkistusportti pitää harvinaiset huonot käännökset poissa tuotannosta.
Oikein tehtävä osuus on itse käännösvaihe. Käsin kirjoitetut LLM-kutsut vioittavat paikkamerkkejä ja monikkomuotoja tavoilla, joita testisi eivät havaitse, ja käytät enemmän aikaa käännöksen liimaosien ylläpitoon kuin itse ominaisuuskoodin. API-pohjainen moottori, jossa on Syntaksin lukitus, poistaa koko tämän vikatilan, joten putkesi kääntää uudet merkkijonot samassa yhdistämisessä, joka ne esitteli – ja ei-englanninkieliset käyttäjäsi lakkaavat näkemästä englanninkielisiä paikkamerkkejä.
Oletko valmis automatisoimaan käännökset putkessasi rikkomatta paikkamerkkejä? Kokeile SimplePoTranslatea ilmaiseksi – luottokorttia ei tarvita. Aloita ilmaisella tasolla, validoi API omia
.po-tiedostojasi vastaan ja kytke se CI:hin, kun olet valmis.