Translate Toolkit
The Translate Toolkit is a comprehensive suite of software and a Python API designed to enhance the productivity of localizers and streamline localization and translation engineering workflows. It supports a wide array of file formats, including common standards like Gettext PO and XLIFF, alongside many others. As of April 2026, the current version is 3.19.5, actively maintained with regular releases that include improvements and bug fixes.
Common errors
-
UnicodeDecodeError: 'charmap' codec can't decode byte 0x81 in position X: character maps to <undefined>
cause File encoding mismatch, where the default system encoding or an assumed encoding (e.g., UTF-8) does not match the actual encoding of the localization file.fixExplicitly specify the correct encoding when reading files (e.g., `PoFile(filename, encoding='iso-8859-1')`). The toolkit has improved charset detection in newer versions, but explicit specification is always safer for diverse inputs. -
Machine translation errors due to Django/Python template variables (e.g., `{{ variable }}`) being translated or mangled.cause Automatic tokenization in machine translation services often breaks or translates placeholders/variables, as they are not recognized as non-translatable tokens.fixBefore sending to machine translation, pre-process your localization files to replace template variables with simple, unique placeholders (e.g., `_VAR_1_`). After translation, post-process to restore the original variables.
Warnings
- breaking Translate Toolkit versions 3.19.x and newer require Python 3.11 or later. Older Python versions (e.g., 3.10) are no longer supported.
- breaking The `tmserver` (translation memory server) and related project storage components were removed from the toolkit.
- gotcha CSV column headers generated by `csv2po` changed from `comment,original,translation` to `location,source,target` for better alignment with toolkit terminology.
- gotcha All generated PO files now consistently include headers, which may cause layout changes when `pofilter` or `pogrep` are used on older, headerless files.
Install
-
pip install translate-toolkit -
pip install "translate-toolkit[all]" -
uv pip install translate-toolkit
Imports
- PoFile
from translate.storage.po import pofile
- XliffFile
from translate.storage.xliff import xliff
Quickstart
import os
from translate.storage import po
# 1. Create a dummy PO file for demonstration
po_content = '''
msgid ""
msgstr ""
"Project-Id-Version: Example Project 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
msgid "Hello, world!"
msgstr "¡Hola, mundo!"
msgid "Welcome to our application."
msgstr "Bienvenido a nuestra aplicación."
'''
with open("example.po", "w", encoding="utf-8") as f:
f.write(po_content)
# 2. Load the PO file
try:
po_file = po.pofile.PoFile("example.po")
print(f"Loaded PO file with {len(po_file.units)} translation units (including header).")
# 3. Iterate and print translation units
for unit in po_file.units:
if not unit.isblank(): # Skip the header unit
print(f"---\nOriginal: '{unit.source}'\nTranslated: '{unit.target}'")
# 4. Modify a translation unit (example)
if len(po_file.units) > 1: # Ensure there's at least one real unit after header
first_translatable_unit = po_file.units[1]
print(f"\nModifying unit: '{first_translatable_unit.source}'")
first_translatable_unit.target = "¡Saludos, universo!"
print(f"New translation: '{first_translatable_unit.target}'")
# 5. Save the modified PO file (optional)
po_file.save("example_modified.po")
print("\nModified file saved to example_modified.po")
except Exception as e:
print(f"An error occurred: {e}")
finally:
# 6. Clean up dummy files
if os.path.exists("example.po"):
os.remove("example.po")
if os.path.exists("example_modified.po"):
os.remove("example_modified.po")
print("\nCleaned up dummy files.")