Come i workflow di traduzione batch rompono il Continuous Deployment
Il Continuous Deployment promette soprattutto una cosa: qualsiasi modifica, da un bugfix di una riga a una nuova funzionalità, può passare dal commit alla produzione in sicurezza e con il proprio ritmo. La maggior parte dei team ha impiegato anni per arrivarci. Poi aggiungono una seconda lingua, e nel mezzo della pipeline ricompare in silenzio uno step che nessuno ha automatizzato: l'handoff di traduzione batch.
A prima vista non sembra un problema di deployment. Sembra un processo: esportare le stringhe, inviarle a un fornitore di traduzioni, attendere, riavere i file, importarli, risolvere i conflitti, rideployare. Ma quel round-trip è uno step che blocca le release travestito da workflow, e rompe il Continuous Deployment in modi precisi e prevedibili.
Questa è la versione da ingegnere del perché, e di come appare davvero l'alternativa continua quando è cablata in CI/CD.
- Traduzione batch: esportare in file, passare a un fornitore, attendere, reimportare, rideployare. Uno step serializzato e fuori banda dentro un flusso altrimenti automatizzato.
- La rottura: le traduzioni atterrano dopo che la funzionalità è stata rilasciata, le reimportazioni vanno in conflitto con codice che è andato avanti, e una correzione di una parola richiede un redeploy completo. I team compensano con un content freeze.
- Localizzazione continua: le chiavi raggiungono il TMS dal tuo codice, una CLI mantiene tutto sincronizzato in CI, e le traduzioni vengono consegnate tramite una CDN senza redeploy.
- Qualità, in continuo: la traduzione automatica IA più la Quality Estimation gestisce il grosso; solo le stringhe a bassa confidenza passano al review umano.
Come un workflow di traduzione batch rompe la CI/CD
Il Continuous Deployment funziona perché ogni step è automatizzato, veloce e reversibile. Un handoff batch non è nessuna di queste cose. Ecco dove si rompe concretamente.
Serializza un processo parallelo. Lo sviluppo è continuo; un handoff batch è uno stop. Finisci una funzionalità, poi aspetti giorni o settimane le traduzioni prima che la versione localizzata possa uscire. La funzionalità è pronta, la traduzione no, e la release è ostaggio della lingua più lenta. Il Continuous Deployment avrebbe dovuto eliminare proprio questo tipo di gate.
La reimportazione va in conflitto con codice che è andato avanti. Quando i file tradotti tornano, la codebase è cambiata: chiavi rinominate, stringhe divise, una schermata rifattorizzata. Fare il merge dei file restituiti è un esercizio manuale di risoluzione dei conflitti, lo stesso problema che crea un branch di lunga durata, salvo che il branch è una cartella di file .json o .xliff gestita da persone fuori dal tuo repo. Più lungo è il batch, peggiore è il merge.
Una correzione di una parola diventa una release completa. Hai trovato un refuso nel testo tedesco, o una stringa che sfora il suo pulsante? In un modello batch-and-bundle il file corretto deve essere committato, buildato e rideployato attraverso l'intera pipeline. Del testo che non ha nulla a che fare con il codice è ora bloccato dietro un deploy di codice. È al contrario.
Spinge i team verso un content freeze. Poiché il round-trip è lento e rischioso, la difesa comune è bloccare tutte le stringhe due o tre mesi prima di un lancio, così c'è tempo per tradurre. Ora la metà rapida del prodotto (il testo) viene congelata per adattarsi alla metà lenta (il batch). I costi nascosti di tutto questo, il coordinamento, i nuovi round-trip, il rollout ritardato, di solito superano il costo della traduzione stessa.
Non ha stato condiviso. I file in viaggio verso un fornitore non hanno alcun registro di chi ha revisionato cosa, quali stringhe sono approvate, quale sia la terminologia concordata o quanto sia affidabile una data traduzione. Quello stato vive in thread di email e fogli di calcolo, non nella tua pipeline. La CI non può ragionarci sopra, quindi la CI non può farci gate.
Niente di tutto questo è colpa dei traduttori, e non si risolve traducendo più in fretta. È un problema di architettura: uno step serializzato, con stato e manuale è stato inserito in una pipeline pensata per essere parallela, senza stato tra un'esecuzione e l'altra e automatizzata.
Come appare il continuo, cablato nella pipeline
La soluzione è trattare le traduzioni come già tratti codice e configurazione: scorrono di continuo nella pipeline, hanno il proprio canale di consegna e non bloccano mai una release. In concreto, con i18next e Locize, ci sono tre parti in movimento.
1. Le chiavi raggiungono il TMS dal tuo codice, non da un foglio di calcolo
Quando scrivi una nuova funzionalità, le nuove chiavi di traduzione dovrebbero comparire nel sistema di traduzione nel momento in cui esistono nel codice. Il saveMissing di i18next fa proprio questo: ogni chiave che non ha ancora un valore viene segnalata automaticamente.
import i18next from 'i18next'
import LocizeBackend from 'i18next-locize-backend'
i18next.use(LocizeBackend).init({
// ...
saveMissing: true, // le nuove chiavi compaiono in Locize mentre scrivi codice
backend: {
projectId: '<your-project-id>',
apiKey: '<your-api-key>', // solo in sviluppo, non rilasciarla mai in produzione
referenceLng: 'en'
}
})Gira in sviluppo e solo dalla lingua di riferimento, così la single source of truth per "cosa va tradotto" è il tuo codice reale, non un export mantenuto a mano. Non c'è alcun batch da assemblare perché l'elenco è sempre aggiornato.
2. Uno step CLI mantiene tutto sincronizzato in CI
Nella tua pipeline, la CLI di locize riconcilia le tue stringhe di riferimento locali con il progetto e riporta indietro le traduzioni. Fa un vero diff (aggiungi, aggiorna, rimuovi) invece di una sovrascrittura cieca, e per le esecuzioni automatizzate puoi renderla conservativa:
# In CI: push delle chiavi di riferimento, pull delle traduzioni, niente eliminazioni automatiche
locize sync \
--project-id <your-project-id> \
--api-key $LOCIZE_API_KEY \
--ver latest \
--path ./locales \
--update-values false \
--skip-delete truePer impostazione predefinita sync ispeziona solo la lingua di riferimento (--reference-language-only true) e fa il backup di qualsiasi segmento che rimuoverebbe prima di toccarlo. Eseguilo prima con --dry true per vedere il diff senza scrivere. Il punto è che il drift delle traduzioni diventa uno step visibile e scriptabile in CI invece di un merge manuale a posteriori.
3. Pubblica una versione fissata al momento del deploy
Questa è la parte che rende davvero atomica una release. La tua app carica le traduzioni da una versione con nome (pensa a latest per la copia di lavoro, production per ciò che viene rilasciato), e pubblichi quella versione esattamente nel momento in cui deployi:
# Step finale della pipeline, accanto al deploy del codice
locize publish-version --ver production --project-id <your-project-id> --api-key $LOCIZE_API_KEYPoiché l'app in esecuzione è fissata a una versione invece di leggere la copia di lavoro live, le modifiche in corso non finiscono mai in produzione a metà del deploy. E poiché le traduzioni vengono consegnate tramite una CDN, una correzione di testo pubblicata tra una release e l'altra raggiunge gli utenti senza redeploy. Il backend di i18next rifà la fetch al proprio intervallo; rilasci la correzione del refuso tedesco in secondi, non in una release.
La release resta atomica e reversibile. Le modifiche di testo tra release viaggiano su un canale separato e più veloce. Nessuna delle due blocca l'altra.
Per un approfondimento su come si è evoluto questo modello, vedi localizzazione continua moderna e la visione originale su sviluppo, integrazione e localizzazione continui.
Mantenere la qualità senza un gate di review batch
L'obiezione onesta a "rilascia le traduzioni in continuo" è la qualità. L'intero motivo per cui i batch esistono è lo step di review umano. Ma non ti serve un batch per avere la review; ti serve che la review sia continua e selettiva invece che tutta in una volta.
Quando arriva una nuova chiave, Locize la traduce automaticamente. Puoi portare la tua chiave provider (OpenAI, Gemini, Mistral, DeepL o Lara) o usare l'IA integrata, e il risultato viene poi valutato dalla Quality Estimation su una scala da 0 a 1. L'instradamento è la parte importante:
- Le traduzioni sopra la soglia (0,7 per impostazione predefinita) vengono salvate e possono essere pubblicate automaticamente.
- Le traduzioni sotto la soglia, o segnalate con un problema grave, vengono instradate nel workflow di review umano.
Così, invece che una persona controlli migliaia di stringhe in un file esportato una volta a trimestre, i tuoi revisori vedono solo le stringhe che hanno davvero bisogno di un umano, nel contesto, man mano che compaiono. Un glossario e uno styleguide mantengono terminologia e brand voice coerenti su tutto. Il gate di review esiste ancora; semplicemente ha smesso di essere un batch.
I ruoli (admin, manager, publisher, traduttore), gli scope per lingua e per namespace, e un editor in-context fanno sì che traduttori e revisori lavorino direttamente sul progetto live. Non c'è alcun export da spedire né alcun file da rimergiare.
Come uscire dal batch
Non devi ricostruire tutto in una volta. Una migrazione pragmatica:
- Fissa la tua app a una versione. Punta la produzione a una versione con nome (per esempio
production) invece che alla copia di lavoro live. Già solo questo rende i deploy atomici. - Sposta il freeze su un publish. Sostituisci il content freeze con la pubblicazione di quella versione al momento del deploy. Le stringhe restano modificabili fino all'istante in cui rilasci.
- Metti
syncin CI. Aggiungi lo step di sync della CLI così il drift nella lingua di riferimento viene rilevato automaticamente, iniziando con--skip-delete truefinché non ti fidi. - Attiva la traduzione automatica più la QE. Lascia che l'IA copra il volume e instradi agli umani solo le stringhe a bassa confidenza, così la coda di review è piccola e continua.
- Crea un branch per le modifiche rischiose. Per un grande rename o ristrutturazione, usa un progetto branch così l'esperimento non tocca mai la versione di produzione finché non è mergiato.
Ogni step rimuove un pezzo dell'handoff batch. Alla fine, la traduzione è solo un'altra cosa che la tua pipeline fa in continuo, e "aspettare le traduzioni" non è più una voce nel tuo piano di release.
Dove si inserisce Locize
Il Continuous Deployment ha rotto il modello batch per il codice un decennio fa. La stessa logica vale per le stringhe: un handoff serializzato, manuale e con stato non ha posto in una pipeline automatizzata. Locize è costruito attorno a questa idea, chiavi dal tuo codice, una CLI per la CI, publishing fissato a una versione, consegna via CDN e traduzione IA gated dalla Quality Estimation, così la localizzazione smette di essere lo step che blocca la release.
Se il tuo processo di traduzione ha ancora una fase "manda fuori i file e aspetta", quella è la parte della tua pipeline che il Continuous Deployment non ha mai raggiunto. Scopri come funziona la localizzazione continua, oppure crea un account Locize gratuito e cablalo nel tuo prossimo deploy.
Stanco di gestire le traduzioni a mano?
Locize è il backend di gestione delle traduzioni creato dal team di i18next: distribuzione via CDN, traduzione con AI, editing in-context, senza nuovi deploy.
Inizia la prova gratuita di 14 giorni