EmDash 的管理介面可使用 Lingui 進行訊息提取,並使用 Lunaria 追蹤翻譯進度。所有翻譯都儲存在 PO (gettext) 檔案中 — 每個語言一個。
翻譯狀態
檢視翻譯儀表板以了解所有語言的目前進度。
誰可以翻譯
每個翻譯都必須由母語者或流利的使用者監督。接受 AI 生成的翻譯,但僅限於流利的使用者在提交之前審查每個字串並在執行中的管理面板中預覽的情況。不接受無監督的機器輸出。請參閱下面的 AI 輔助翻譯 和測試您的翻譯。
讓字串保持未翻譯狀態比錯誤翻譯更好。錯誤的翻譯會誤導使用者;英文回退只會給他們帶來不便。
檔案結構
翻譯目錄位於 packages/admin/src/locales/:
packages/admin/src/locales/
├── en/
│ └── messages.po # English (source)
├── de/
│ └── messages.po # German
└── ...
每個 .po 檔案包含 msgid/msgstr 對。msgid 是英文來源文字;msgstr 是您的翻譯。空的 msgstr 表示「尚未翻譯」 — Lingui 在執行時將回退到英文。
翻譯字串
-
檢視翻譯儀表板 以了解需要處理的內容。檢查開啟的 PR 以避免重複工作。
-
Fork 儲存庫並建立分支:
git checkout -b i18n/de -
開啟您語言的 PO 檔案(例如,
packages/admin/src/locales/de/messages.po)。 -
填寫翻譯。 每個條目如下所示:
#: packages/admin/src/components/LoginPage.tsx:304 msgid "Sign in with Passkey" msgstr ""填寫
msgstr:#: packages/admin/src/components/LoginPage.tsx:304 msgid "Sign in with Passkey" msgstr "Mit Passkey anmelden" -
測試您的翻譯(見下文)。
-
開啟針對
main的 PR。標題格式:i18n(de): add/update German translations。
需要翻譯的內容
- 每個條目的
msgstr值。
不應翻譯的內容
msgid值 — 這些是查詢鍵。- 插值佔位符,如
{error}、{email}、{label}— 保持完全不變。 - XML 風格的標籤,如
<0>、</0>— 這些包裝互動元素(連結、按鈕)。保留標籤並翻譯它們之間的文字。 - 以
#:開頭的註解 — 這些是 Lingui 新增的來源參考。
插值和標籤
某些字串包含佔位符和標籤:
msgid "Authentication error: {error}"
msgstr "Authentifizierungsfehler: {error}"
msgid "Don't have an account? <0>Sign up</0>"
msgstr "Noch kein Konto? <0>Registrieren</0>"
msgid "If an account exists for <0>{email}</0>, we've sent a sign-in link."
msgstr "Falls ein Konto für <0>{email}</0> existiert, haben wir einen Anmeldelink gesendet."
佔位符({error}、{email})在執行時被動態值替換。標籤(<0>...</0>)包裝 React 元件。兩者都必須在您的翻譯中以與來源中完全相同的方式出現 — 相同的名稱、相同的巢狀。
測試您的翻譯
-
編譯並執行展示:
pnpm run locale:compile pnpm build pnpm --filter emdash-demo dev -
在管理設定頁面中切換語言,並驗證您的翻譯在上下文中看起來正確。
虛擬語言
EmDash 提供一個虛擬語言,它將所有包裝的字串轉換為帶重音符號的相似字元 — "Dashboard" 變成 "Ðàšĥƀöàřð",依此類推。在虛擬語言啟用時以正常英文顯示的任何字串要麼缺少 t\…“ 包裝器,要麼來自目錄外部。
要啟用它,請在展示目錄中的 .env 檔案中新增以下內容:
EMDASH_PSEUDO_LOCALE=1
然後重新啟動開發伺服器。虛擬語言在登入頁面和設定的語言選擇器中顯示為 Pseudo。切換到它以一目了然地發現未包裝的字串。
新增新語言
如果您的語言還沒有 PO 檔案:
-
將語言新增到
packages/admin/src/locales/locales.ts:export const LOCALES: LocaleDefinition[] = [ { code: "en", label: "English", enabled: true }, { code: "de", label: "Deutsch", enabled: true }, // ... { code: "ja", label: "日本語", enabled: false }, // add yours ];這是唯一的真理來源 —
lingui.config.ts、lunaria.config.ts和管理執行時都從此檔案衍生其語言清單。除非您的翻譯達到 100% 覆蓋率,否則設定enabled: false— 一旦翻譯達到足夠的覆蓋率,維護者將啟用它。 -
執行提取以產生空的 PO 檔案:
pnpm run locale:extract這將建立
packages/admin/src/locales/{your-locale}/messages.po,其中包含所有準備翻譯的字串。 -
按照上述步驟翻譯和測試。
翻譯標準
準確性
翻譯應忠實地以母語者水準表示英文來源文字。不要新增、刪除或重新解釋意義。如果來源字串含糊不清,請檢查 #: 註解以取得來源檔案位置 — 閱讀元件程式碼以理解上下文。
一致性
在您的語言中使用一致的術語。如果您在一個地方將 “collection” 翻譯為 “Sammlung”,請不要在其他地方切換到 “Kollektion”。如果您的語言已經有翻譯,請在開始之前閱讀現有的 PO 檔案以匹配已建立的術語。
語氣
管理介面使用直接、專業的語氣。在您的語言中匹配它 — 避免過於正式或過於隨意的措辭。
AI 輔助翻譯
您可以使用 AI 工具產生翻譯,包括完整的第一遍,但流利的使用者必須監督結果:
- 流利的使用者必須審查每個字串。AI 工具會犯下只有流利使用者才能發現的細微錯誤 — 錯誤的語域、不自然的措辭、不正確的技術術語。
- 流利的使用者必須在執行中的管理介面中預覽翻譯。AI 工具不了解版面配置約束或 UI 上下文。
- 在您的 PR 描述中揭露 AI 使用情況。
- 包含無監督機器翻譯的 PR 將被關閉。
部分翻譯
歡迎部分翻譯。您不需要在一個 PR 中翻譯每個字串 — 任何進展都有幫助。未翻譯的字串將在執行時回退到英文。