five languages
The blog speaks Chinese and Russian now. Well, the furniture does: navigation, buttons, forms, footers, all of it, under /zh and /ru. The posts themselves will follow as I translate them, which is honest work I am not rushing.
Getting from three languages to five forced the cleanup I had been putting off. Language lists had quietly multiplied, one in the routing, one in the switcher, one in the date formatting, one in the sitemap. Now there is a single registry, and everything else derives from it. I proved it to myself with a test that invents a fake sixth language and checks that routing, the switcher, translate targets and the sitemap all pick it up with no other edits. Adding language number six will be one registry entry and one file of strings.
The switcher had to change too. Three languages fit as links in the sidebar; five start to look like a ransom note. It is a dropdown now, same spot, each language written in its own tongue: English, norsk, español, 中文, русский. Pick a language the current page exists in and you land on that version; pick one it does not and you land on that language's front page instead of a 404.
Missing translations get a soft landing elsewhere as well. The privacy page under /ru shows the English text inside Russian chrome until I write the Russian one, which beats an error page in any language.
And to keep myself organized there is a new Languages section in the admin: a grid of every site page against every language, showing what exists and what is missing. A missing cell gives me two buttons, translate it, or create it from the English version as a starting point so I am rewriting instead of staring at an empty box. Posts are not in that grid on purpose, I translate those one by one from the editor when a post deserves it.
The fonts turned out to be the easy part, decent CJK and Cyrillic fallbacks and the serif look holds up. Now I just owe the shelves some books.