A large share of the newspapers that want an e-paper publish in Bengali, Hindi, Urdu or Arabic. Their readers should not meet an English toolbar on top of a Bengali front page. For Inkfold 1.1 we translated the whole reader site into Bengali, Hindi and Arabic, including right-to-left layout, while the newsroom stays in English for the staff who run it.
Every visible string through one function
The first step was the least glamorous: every piece of text on the public site now goes through Laravel’s __() helper, plurals through trans_choice(), and dates through Carbon’s translatedFormat(), so “Monday, 26 October” becomes “সোমবার, 26 অক্টোবর” without separate templates. The translations live in plain JSON files, one per language, keyed by the English sentence. Adding French or Urdu later means copying one file and translating the values.
Choosing the language
A small middleware picks the locale for each request, in this order: the visitor’s explicit choice stored in the session, the language saved on a signed-in reader’s account, the browser’s Accept-Language header when more than one language is offered, and finally the site default. Requests to the newsroom skip the middleware entirely. The publisher decides which languages are on offer in the settings.

Right-to-left without mirroring the newspaper
Each language carries its direction in configuration, and the layout writes it to the dir attribute of the page. Most of the interface then follows by itself. A dedicated block of RTL rules handles the rest: side panels swap edges, previous and next arrows flip, and the story pop-up’s “continued on” marker moves to the other side.
One thing deliberately does not flip: the pages. A Bengali or English newspaper was printed left to right, and its page order and story positions must stay as printed even when the interface around them reads right to left. The page container keeps direction: ltr, so the coordinates of every clickable story remain correct.

Fonts only for the language in use
Bengali, Devanagari and Arabic need their own fonts. Loading all of them for every visitor would add weight for nobody’s benefit, so the layout requests the Noto font for the active language only and adds it to the font stack through CSS variables.
A test that fails on a missing translation
Translations rot quietly: someone adds a button and forgets the JSON files. A feature test now scans the reader-site templates for translatable strings and fails if any language file lacks one. It caught one surprise: a key named “Pagination” resolved to Laravel’s own pagination.php file on a case-insensitive file system and returned an array. Avoid keys that match a translation file name.
Key takeaways
- Route all public text through
__(); keep translations in JSON keyed by the source sentence. - Resolve the locale from session, account, browser and default, in that order.
- Set
diron the document and write focused RTL rules, but keep printed content in its own direction. - Load script-specific fonts only for the active language, and test for missing strings.
Earlier in the series: offline reading with a service worker. Switch languages in the header of the Inkfold demo; the software is on Charming Theme.
Need a Laravel or WordPress site in Bengali, Arabic or several languages at once? Let’s Talk — ArtinTech Solution builds multilingual sites every week.