OfficeCLI i18n and RTL Support in Word Documents: A Technical Deep Dive
OfficeCLI provides built-in, first-class internationalization (i18n) and right-to-left (RTL) language support for Word documents through a multi-layered property cascade that operates independently of Microsoft Word.
OfficeCLI enables AI agents and automation scripts to create, modify, and query Word documents in any language or script. Unlike simple wrappers around COM objects, the iOfficeAI/OfficeCLI repository implements native RTL handling directly within its core engine, ensuring reliable document generation for Arabic, Hebrew, CJK, and other complex scripts.
How OfficeCLI Implements i18n and RTL Support
The architecture follows a three-layer model (Read → DOM → Raw XML) with RTL logic integrated at the DOM layer. This ensures that both high-level view commands and low-level raw-set operations see consistent direction information across the entire document tree.
Document-Wide Defaults
Global RTL settings and language tags are stored in the document's default properties. In WordHandler.Set.DocDefaults.cs, the engine reads and writes <w:bidi> elements within the docDefaults section, handling properties such as docdefaults.rtl and docdefaults.direction.
When you create a document with a locale flag, the CLI automatically sets these defaults. For example, using --locale ar-SA triggers the logic at line 116 in WordHandler.Set.DocDefaults.cs to enable RTL document-wide and insert the appropriate BCP-47 language tag.
Style and Paragraph-Level Cascade
Direction inheritance flows from document defaults through sections, tables, and styles down to individual paragraphs. The ResolveEffectiveParagraphStyleProperties method in WordHandler.StyleList.cs (lines 885-938) merges <w:bidi> values from style paragraph properties, table cells, section defaults, and numbering levels.
This method emits both effective.direction and effective.rtl for downstream consumers, ensuring that any element inheriting from a style receives the correct text direction. The WordHandler.StyleList.cs file (lines 98-106) specifically lifts <w:bidi> attributes from style definitions into an effective run-level RightToLeftText flag.
Run-Level Property Resolution
Individual runs may explicitly set RTL via <w:rtl> elements or inherit direction from their parent paragraph. The ResolveEffectiveRunPropertiesCore method in WordHandler.StyleList.cs (lines 77-88) merges run properties, table-style runs, and paragraph bidi attributes into a single RightToLeftText object.
The method records provenance information in effective.rtl, allowing you to trace whether a run's direction was set explicitly, inherited from a style, or derived from document defaults.
Selector and Query Support
The CLI exposes RTL state through selectors for querying and filtering. In WordHandler.Selector.cs (lines 207-214), the rtl key maps to the run's RightToLeftText value, enabling queries such as paragraph[rtl=true] or run[rtl=true].
The set command accepts multiple value formats for RTL properties, including rtl, righttoleft, true, or 1, parsed through WordHandler.Set.cs.
Language Tags and Per-Script Font Slots
OfficeCLI respects OpenXML's complex script handling through dedicated font slots and language attributes:
- Per-script font slots:
font.eastAsiafor CJK scripts,font.csfor complex scripts (Arabic/Hebrew),font.hAnsifor high ANSI, andfont.asciifor basic Latin. - BCP-47 language tags: Exposed as
lang.latin,lang.ea(East Asian), andlang.cs(complex script). - RTL-specific layout features: Including
rtlGutter,pgBorders, and locale-aware page numbering.
The MergeRunProperties method in WordHandler.StyleList.cs (lines 93-106) handles the inheritance and merging rules for these per-slot properties, ensuring that mixed-script documents render correctly.
Practical Code Examples
Create an RTL Document Automatically
officecli create report.docx --locale ar-SA
This command writes the appropriate BCP-47 tag and sets docDefaults.rtl=true automatically through the document defaults handler.
Set Paragraph Direction Manually
officecli set report.docx '/body/p[1]' --prop direction=rtl
This updates <w:pPr><w:bidi/> on the target paragraph. The effective run-level RTL flag is emitted for all child runs through the cascade logic in StyleList.cs.
Verify Effective Direction on a Run
officecli get report.docx '/body/p[1]/r[1]' --json
Expected output:
{
"tag": "run",
"path": "/body/p[1]/r[1]",
"attributes": {
"text": "مرحبا",
"effective.rtl": true,
"effective.direction": "rtl"
}
}
Query All RTL Runs in a Document
officecli query report.docx "run[rtl=true]" --json
This returns every run whose effective RTL flag is true, regardless of whether the direction originated from a style, section, table, or direct formatting.
Apply Per-Script Font Slots
officecli set report.docx '/body/p[2]/r[1]' \
--prop font.eastAsia=宋体 \
--prop font.cs=Times New Roman \
--prop font.ascii=Calibri
The merge respects the per-slot inheritance rules implemented in MergeRunProperties.
Summary
- OfficeCLI implements native i18n and RTL support through
WordHandler.Set.DocDefaults.csandWordHandler.StyleList.cs, not through external Word automation. - Direction cascades from docDefaults → section → table → style → paragraph → run, tracked via
effective.rtlandeffective.directionproperties. - Selectors and commands support RTL queries using
rtl=trueand accept multiple value formats (rtl,righttoleft,1) for setting direction. - Per-script font handling uses dedicated slots (
eastAsia,cs,hAnsi,ascii) with BCP-47 language tags exposed aslang.latin,lang.ea, andlang.cs. - Provenance tracking in
ResolveEffectiveRunPropertiesCoreallows tracing whether RTL state came from explicit formatting, styles, or document defaults.
Frequently Asked Questions
How does OfficeCLI handle mixed-direction documents containing both LTR and RTL text?
OfficeCLI resolves effective direction at the run level using ResolveEffectiveRunPropertiesCore in WordHandler.StyleList.cs. Each run maintains its own RightToLeftText property, allowing individual Arabic or Hebrew runs to display RTL within English paragraphs, or vice versa. The selector run[rtl=true] filters for specifically RTL content regardless of the surrounding paragraph direction.
Can OfficeCLI set document-wide RTL defaults without modifying every paragraph?
Yes. Use the create command with --locale (e.g., ar-SA or he-IL) or manually set docdefaults.rtl=true via the set command targeting document defaults. In WordHandler.Set.DocDefaults.cs, this writes the <w:bidi> element to the document's docDefaults section, causing all content to inherit RTL direction unless explicitly overridden at the paragraph or run level.
What BCP-47 language tags does OfficeCLI support for font selection?
OfficeCLI supports the full range of BCP-47 tags exposed through OpenXML's language properties: lang.latin for Western scripts, lang.ea (East Asian) for CJK languages, and lang.cs (complex script) for Arabic, Hebrew, Thai, and similar scripts. These map to corresponding font slots (font.ascii, font.eastAsia, font.cs) that are merged according to the rules in MergeRunProperties within WordHandler.StyleList.cs.
How do I query only the paragraphs that contain RTL text in a large document?
Use the query command with the RTL selector: officecli query document.docx "paragraph[rtl=true]" --json. This leverages the selector logic in WordHandler.Selector.cs (lines 207-214), which evaluates the effective RTL flag computed through the style cascade. This flags paragraphs where the resolved direction is RTL, regardless of whether it was set via direct formatting, style inheritance, or document defaults.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →