Localizzazione Di Siti Web Con Una Libreria JavaScript

Quantum
Quest
Algorithms, Math, and Physics

Localizzazione di siti web con una libreria JavaScript

In questo post del blog, presento una libreria JavaScript riutilizzabile che ho sviluppato per semplificare la localizzazione dei siti web. Basata sul mio precedente lavoro con la localizzazione di applicazioni HTML5, questa libreria semplifica la gestione delle traduzioni e consente il cambio dinamico della lingua. Spiegherò l’architettura della libreria, mostrando come recupera e unisce i dati di traduzione da file JSON, aggiorna il contenuto delle pagine e gestisce i metadati. Il mio approccio utilizza i18next e Lodash per migliorare le prestazioni e la flessibilità. Fornirò inoltre approfondimenti sugli script di supporto che ho creato per automatizzare ulteriormente il processo di localizzazione, tra cui uno script Bash per estrarre contenuti traducibili dall’HTML e uno script Python che sfrutta LLM per la traduzione automatica.

La mia libreria ruota attorno al caricamento e all’applicazione efficienti delle traduzioni. Il processo inizia recuperando il percorso dei file di localizzazione da un tag <meta> presente nell’HTML:


<meta name="locale-path" content="/path/to/locales/">

Grazie a questa configurazione, lo script può essere adattato a diverse strutture di progetto. La funzione principale, loadLanguage(lang), è responsabile del recupero e dell’elaborazione dei dati di traduzione:


  const loadLanguage = async function(lang) {
    if (!i18next.hasResourceBundle(lang)) {
      try {
        const fetchPromises = [];
        if (optionalBaseEnabled) {
          fetchPromises.push(
            fetchJson(`/data/json/loc/base/${lang}.min.json?id=fdc3af`).catch(() => {
              console.log(`Resource at /data/json/loc/base/{lang}.min.json?id=fdc3af for language {lang} was not found`);
              return null;
            })
          );
        }
        fetchPromises.push(
          fetchJson(`{localesPath}{lang}.min.json?id=fe5cf3`).catch(() => {
            console.log(`Resource at {localesPath}{lang}.min.json?id=fe5cf3 for language ${lang} was not found`);
            return null;
          })
        );
        const results = await Promise.all(fetchPromises);
        const resources = optionalBaseEnabled ? _.merge({}, results[0] || {}, results[1]) : results[0];
        if (!resources) {
          console.log(`Skipping loading language ${lang} due to missing resource.`);
          return;
        }
        Object.keys(resources).forEach(namespace => {
          i18next.addResourceBundle(lang, namespace, resources[namespace], true, true);
        });
      } catch (error) {
        console.error(`An error occurred while loading resources for lang: ${lang}`, error);
        return;
      }
    }
    await i18next.changeLanguage(lang);
    updateContent();
};

Questa funzione verifica innanzitutto se le risorse per la lingua specificata siano già state caricate. In caso contrario, utilizza Promise.all per scaricare contemporaneamente i file di traduzione base e specifici del percorso. Successivamente, uso la funzione _.merge di Lodash per combinare i set di dati. I dati combinati vengono quindi aggiunti a i18next tramite addResourceBundle. Infine, la funzione updateContent() applica le traduzioni alla pagina.

La funzione updateContent() si occupa quindi di applicare le traduzioni caricate alla pagina. Ciò include l’aggiornamento dei metadati:


document.documentElement.lang = i18next.t('htmlLang');
document.querySelector('meta[http-equiv="content-language"]').content = i18next.t('contentLanguage');
document.title = i18next.t('title');
document.querySelector('meta[name="description"]').content = i18next.t('description');

E l’aggiornamento del testo e degli attributi degli elementi:


const text = i18next.getResourceBundle(i18next.language, 'text');
Object.keys(text).forEach(key => {
    const element = document.getElementById(key);
    if (element) {
        element.innerHTML = i18next.t(`text:${key}`);
    }
});

// Logica simile per aggiornare gli attributi dei link

Automatizzare il flusso di lavoro

Per semplificare il flusso di lavoro di localizzazione, ho sviluppato due script di supporto. Uno script Bash estrae tutti gli attributi data-local-* dall’HTML, fornendo un elenco di contenuti traducibili. Ad esempio, il frammento HTML:


<p id="my_paragraph" data-local-text="welcomeMessage"></p>

porterà all’estrazione di welcomeMessage, che può quindi essere utilizzato come chiave nei file JSON di traduzione.

Ho inoltre sviluppato uno script Python che sfrutta LLM per tradurre automaticamente il contenuto dei file JSON. Questo riduce notevolmente l’impegno richiesto per la traduzione manuale. Il flusso di lavoro tipico prevede di usare lo script Bash per generare le chiavi, creare un file base en.json e poi utilizzare il mio script Python per generare gli altri file di lingua a partire dall’inglese.

Esempio di struttura JSON

Un esempio di file JSON per la lingua inglese potrebbe essere:


{
  "text": {
    "welcomeMessage": "Welcome to my website"
  },
  "links": {
    "aboutLink": {
      "href": "/about",
      "alt": "About us page"
    }
  }
}

Per ulteriori approfondimenti su questo argomento, potete consultare i dettagli qui.