Frontend Development 13 min read

Internationalization (i18n) Implementation for JSP/VM Frontend Using Gettext and Easygettext

This article describes a frontend engineer's exploration of i18n for JSP and VM pages, detailing the challenges of hard‑coded strings, the use of jquery‑i18next, gettext tools, a custom i18n‑gettext npm package, Makefile automation, and the resulting workflow for extracting, merging and compiling translation files.

Qunar Tech Salon
Qunar Tech Salon
Qunar Tech Salon
Internationalization (i18n) Implementation for JSP/VM Frontend Using Gettext and Easygettext

The project aims to make the backend of a travel platform more international‑friendly by introducing i18n support for pages rendered with JSP, VM, jQuery, Mustache and custom string files.

Project Background

International suppliers need a localized backend, so the team began exploring internationalization (i18n) practices.

Project Overview

i18n stands for "internationalization" (the 18 letters between i and n are omitted). The focus of this article is on handling JSP, VM, and jQuery+Mustache+string files.

Initial Exploration

Front‑back Interaction Flow

The user request includes an Accept-Language header and a cookie storing the language‑pack version. The backend decides whether to return a new language pack or use the cached one from LocalStorage .

Language Pack and Page Rendering

Typical i18n libraries such as jquery-i18next require both i18next and the jQuery plugin. Example DOM structure:

<div id="page">
  <ul class="nav">
    <li><a href="#" data-i18n="nav.home">主页</a></li>
    <li><a href="#" data-i18n="nav.page1"></a></li>
    <li><a href="#" data-i18n="nav.page2"></a></li>
  </ul>
</div>

Corresponding language‑pack JSON:

{
  "nav": {
    "home": "Home",
    "page1": "Page One",
    "page2": "Page Two"
  }
}

Calling $("#page").localize(); replaces all elements with a data-i18n attribute inside the #page scope.

Problems with the current approach include repeated rendering, difficulty extracting hard‑coded strings into a single JSON file, poor separation of translation work, and string reuse issues.

Final Solution Determination

The team decided to adopt GNU gettext tooling. While xgettext can extract strings from many languages, it does not support .string or .mustache files, so the easygettext npm package is used for those.

Example of easygettext supported markup:

<div translate>Hello World</div>
<div placeholder="Hello World"></div>
<translate>Hello World</translate>

A custom npm package i18n-gettext provides two CLI commands: gettext-extract (extracts markers from VM/template files) and gettext-compile (compiles .po files to JSON). The extraction process is orchestrated by a Makefile:

.PHONY: clean makemessages vmMakemessages translations

makemessages: /tmp/template.pot
clean:
    rm -f /tmp/template.pot

translations: ./$(LANG_DIR)/translations.string
    mkdir -p $(LANG_DIR)
    gettext-compile --dir ./$(LANG_DIR)/ $(LOCALE_FILES)

Key extraction commands:

gettext-extract --startDelim "[#" --endDelim "#]" --quiet --attribute i18n \
    --output $@ $(GETTEXT_TEMPLATE_SOURCES)

xgettext --language=JavaScript --keyword=i18n \
    --from-code=utf-8 --join-existing --no-wrap \
    --output $@ $(GETTEXT_JS_SOURCES)

Sample .po entry generated:

#: path/to/file.js:618
msgid "建议至少在当天的 {hour}:{minute} 前预定"
msgstr "Recommend to book at least {hour} hours {minute} minutes before departure."

Template files are marked with the custom delimiter [# ... #] so that extraction does not heavily intrude existing code:

<th>[# '你好,世界' | i18n #]</th>

In JavaScript, strings are wrapped with QNR.i18n to include variables:

str = QNR.i18n("建议至少在当天的 {hour}:{minute} 前预定", { hour: hour, minute: minute });

Advantages of this approach include minimal code intrusion, automatic merging of old translations, clear separation of extraction and translation tasks, and better semantic context for translators.

Remaining issues are handling input‑heavy VM fragments, manual upload of generated JSON language packs, and the need for further automation.

VMJSPi18nInternationalizationmakefilegettext
Qunar Tech Salon
Written by

Qunar Tech Salon

Qunar Tech Salon is a learning and exchange platform for Qunar engineers and industry peers. We share cutting-edge technology trends and topics, providing a free platform for mid-to-senior technical professionals to exchange and learn.

0 followers
Reader feedback

How this landed with the community

login Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.