Bỏ qua để đến nội dung

Dịch ReputeCast

Hướng dẫn thao tác
Dành cho:
Nhà phát triển

Giao diện của chính ReputeCast có tiếng Anh và tiếng Việt: ứng dụng, các trang đăng nhập và lời mời, thông điệp máy chủ gửi tới thành viên (lỗi kèm cách khắc phục, “ai có thể giúp”, thông báo) và các email ReputeCast gửi cho thành viên. Hướng dẫn này chỉ cho người dịch và nhà phát triển cách dịch ReputeCast sang một ngôn ngữ khác, hoặc hoàn thiện một ngôn ngữ đang dịch dở, và cách kiểm tra kết quả.

Những gì một không gian làm việc gửi tới liên hệ (chiến dịch, email giao dịch, trang công khai và biểu mẫu) do chính không gian làm việc đó dịch, dưới dạng phiên bản ngôn ngữ trong trình soạn thảo. Xem Gửi cho mỗi người đọc đúng ngôn ngữ của họ.

  • Một bản ReputeCast cục bộ chạy từ mã nguồn (Chạy ReputeCast từ mã nguồn).
  • Bảng thuật ngữ của ngôn ngữ bạn dịch, nếu đã có. Bảng thuật ngữ tiếng Việt, docs/i18n/glossary-vi.md, cố định từ ngữ cho mọi màn hình. Hãy dịch các thuật ngữ trong bảng thuật ngữ trước, rồi mới đến các màn hình.
Nội dung Nguồn tiếng Anh Bản dịch
Ứng dụng web web/src/**/messages.ts, web/src/**/<screen>.messages.ts messages.<code>.ts cạnh tệp nguồn
Thông điệp máy chủ và email gửi thành viên internal/<package>/messages/en.json internal/<package>/messages/<code>.json
Từ ngữ ReputeCast dùng docs/i18n/glossary-<code>.md

Một tệp nguồn web khai báo các thông điệp kèm ID (namespace.key):

web/src/features/campaigns/messages.ts
export const m = defineMessages('campaigns', {
newCampaign: 'New campaign',
blockingIssues: '{count, plural, one {# blocking issue} other {# blocking issues}}',
})

Bản dịch của nó lặp lại những khóa mà nó dịch:

web/src/features/campaigns/messages.vi.ts
export default translate(m, {
newCampaign: 'Chiến dịch mới',
blockingIssues: '{count} lỗi chặn gửi',
})

Tệp nguồn định nghĩa nhiều nhóm (mb, m, mp) sẽ có một translate() cho mỗi nhóm, gộp lại bằng toán tử spread: export default { ...translate(mb, { … }), ...translate(m, { … }) }.

Catalog phía máy chủ là một đối tượng JSON gồm các cặp "key": "text", hoặc "key": { "message": "text", "note": "for translators" } khi câu tiếng Anh cần giải thích. Hãy đọc các ghi chú: chúng cho biết một đối số chứa gì. Một số khóa được tạo từ dữ liệu, chẳng hạn short.<event type> trong internal/notify/messages. Một loại sự kiện mới hiển thị câu tiếng Anh từ mã nguồn cho đến khi khóa của nó được thêm vào en.json, vì vậy hãy thêm khóa vào đó khi bạn thêm loại sự kiện.

Khóa nào thiếu trong bản dịch sẽ hiển thị bằng tiếng Anh, nên màn hình không bao giờ bị trống.

Thông điệp dùng ICU MessageFormat:

  • Đối số trong dấu ngoặc nhọn do ứng dụng điền vào: {name}, {count}, {date}. Giữ nguyên cách viết như trong tiếng Anh và đặt chúng vào vị trí mà ngôn ngữ của bạn cần: edited {time} by {name} thành {name} sửa lúc {time}.
  • Số nhiều: {count, plural, one {# day} other {# days}}. Dùng các nhóm số nhiều của ngôn ngữ bạn (CLDR). Tiếng Việt chỉ có other, nên {count} ngày là đủ. =1 {…} khớp một số chính xác khi cách diễn đạt thay đổi.
  • Lựa chọn: {status, select, drafts {…} sent {…} other {…}}. Giữ nguyên các giá trị bên trái (drafts, sent, other) và dịch văn bản trong dấu ngoặc nhọn.
  • Thẻ đánh dấu đoạn văn bản mà ứng dụng định kiểu hoặc gắn liên kết: <b>…</b>, <link>…</link>, <mono>…</mono>, <k>…</k>, <kbd>…</kbd>. Giữ mỗi thẻ quanh những từ đóng cùng vai trò.
  • Một thông điệp là một câu hoặc một nhãn trọn vẹn. Đừng tách nó ra, và đừng giả định rằng hai thông điệp sẽ xuất hiện cạnh nhau theo một thứ tự nhất định.
  • Tên ngôn ngữ ({language}, {languages}) có dạng nhãn mà ngôn ngữ của bạn dùng khi tên đứng riêng. Tiếng Việt viết chữ “tiếng” thường khi tên nằm trong câu, và ứng dụng tự làm việc đó theo vị trí của đối số, nên hãy viết {language}, không bao giờ viết tiếng {language}.
  • Dấu nháy đơn có thể giữ nguyên (isn't, l'été). Để hiển thị dấu ngoặc nhọn dưới dạng văn bản, hãy đặt nó trong dấu nháy: '{'.

Không bao giờ dịch nội dung của không gian làm việc (tên chiến dịch, danh sách, phân khúc, mẫu, biểu mẫu và vai trò tùy chỉnh), tên người và địa chỉ email, khóa quyền (campaigns:send), tên hành động trong nhật ký kiểm tra, mã lỗi API, tên và mã nhà cung cấp (Amazon SES, Postal, Postmark), tên sản phẩm (ReputeCast, HostRepute, Gmail, Outlook), bản ghi DNS và loại bản ghi (SPF, DKIM, DMARC, BIMI, CNAME), header (List-Unsubscribe), mã mẫu, đầu ra CLI, và các thuật ngữ MCP, 2FA, TOTP, IdP, SSO, JIT, A/B, HTML, CSS, API và webhook.

Số, ngày và giờ lấy từ định dạng khu vực của người đọc, không bao giờ từ bản dịch: hãy viết {date}, không viết một ngày cụ thể. Định dạng khu vực tách biệt với ngôn ngữ, nên một thành viên có thể đọc giao diện tiếng Anh với định dạng Việt Nam.

  1. Chạy công cụ kiểm tra từ thư mục web:

    Terminal
    cd web
    pnpm run i18n:check # every missing message, by file
    pnpm run i18n:check --lang vi # one language
    pnpm run i18n:check --summary # one line per language
    pnpm run i18n:check --hardcoded # every hard-coded string, with its line

    Công cụ đọc mã nguồn và bản dịch của web cùng các catalog của máy chủ. Nó liệt kê những thông điệp mà mỗi ngôn ngữ còn thiếu, nhóm theo tệp định nghĩa câu tiếng Anh, và đếm số văn bản viết cứng còn sót trong các màn hình (văn bản JSX, và chuỗi thuần trong các thuộc tính mà người dùng đọc, như title, label, placeholder và aria-label). Một chuỗi ký tự không phải văn bản cần dịch, chẳng hạn một định dạng, hãy đặt trong biểu thức: placeholder={'xxxx-xxxx-xxxx'}.

  2. Sửa những gì không đạt. Công cụ báo lỗi với thông điệp không phải ICU hợp lệ, khóa đã dịch mà tiếng Anh không có, và đối số hoặc thẻ mà tiếng Anh không dùng. Catalog máy chủ còn được kiểm tra khi package của nó được nạp, nên một bản dịch hỏng sẽ làm máy chủ và mọi bài kiểm thử Go dừng ngay.

  3. Commit web/src/i18n/status.gen.ts khi tệp này thay đổi. Công cụ kiểm tra ghi tệp này với những ngôn ngữ đã hoàn chỉnh trong bản build, và mọi bản build đều chạy công cụ kiểm tra trước.

  4. Xem trực tiếp các màn hình. Đổi ngôn ngữ ứng dụng của bạn trong Tài khoản và bảo mật, rồi Ngôn ngữ và khu vực, rồi đọc các màn hình stress-test (Chiến dịch, Kiểm tra và gửi và Cài đặt, rồi Nhóm) ở 1440 và 390 px. Từ dài phải xuống dòng hoặc được rút gọn, không bao giờ tràn ra ngoài hay bị cắt; mục “Text expansion” trong docs/dev/CONVENTIONS.md hướng dẫn cách làm.

Pseudo-locale Pseudo (+40%) thêm dấu vào mọi chữ cái, làm mỗi thông điệp dài thêm khoảng 40% và bao nó trong ⟦ ⟧: “⟦Šçĥéðûļé šéñð ţö 31,604 ŕéçîþîéñţš ·········⟧”. Văn bản không có dấu ngoặc này chưa đi qua hệ thống dịch; thiếu dấu ⟧ nghĩa là văn bản đã bị cắt.

Pseudo-locale có trong bộ chọn ngôn ngữ ở bản phát triển. Trên máy chủ staging, hãy bật nó bằng i18n.pseudo_locale (REPUTECAST_I18N__PSEUDO_LOCALE=true; xem tham chiếu cấu hình).

  1. Viết bảng thuật ngữ trước, docs/i18n/glossary-<code>.md, theo các mục của bảng thuật ngữ tiếng Việt.

  2. Thêm ngôn ngữ vào web/src/i18n/languages.ts (APP_LANGUAGES, kèm tên ngôn ngữ viết bằng chính ngôn ngữ đó) và vào internal/i18n/locale.go (appLocales), rồi chọn định dạng khu vực mà ngôn ngữ dùng theo mặc định (defaultRegionFor trong ứng dụng web, DefaultRegion trên máy chủ). Quy tắc số nhiều lấy từ CLDR ở cả hai phía.

  3. Nếu thiếu định dạng khu vực của ngôn ngữ, hãy thêm nó vào internal/i18n/region.go và web/src/i18n/regions.ts, kèm các vector kiểm thử trong internal/i18n/testdata/regions.json mà cả hai phía đều phải vượt qua.

  4. Thêm các tệp messages.<code>.ts cho ứng dụng web và messages/<code>.json cho các package máy chủ, rồi chạy pnpm run i18n:check --lang <code> cho đến khi không còn gì được liệt kê.

  5. Kiểm tra phông chữ. IBM Plex hỗ trợ chữ Latinh, tiếng Việt, chữ Kirin và chữ Hy Lạp; hệ chữ khác cần một subset phông chữ trong web/src/styles/fonts.css.

Một người bản ngữ duyệt ngôn ngữ trước khi nó có mặt trong bản phát hành. ReputeCast chưa hỗ trợ các ngôn ngữ viết từ phải sang trái.

  • pnpm run i18n:check --lang <code> --summary báo không thiếu gì và không còn văn bản viết cứng.
  • Khi chọn ngôn ngữ của bạn trong Tài khoản và bảo mật, rồi Ngôn ngữ và khu vực, các màn hình bạn đã dịch không còn tiếng Anh và không có gì nằm trong dấu ⟦ ⟧.
  • Một màn hình vẫn hiển thị tiếng Anh: khóa của nó thiếu trong tệp của bạn (công cụ kiểm tra liệt kê khóa đó), hoặc văn bản được viết cứng trong màn hình (--hardcoded liệt kê nó).
  • Máy chủ không khởi động sau khi sửa một catalog .json: catalog có ICU không hợp lệ, một khóa không xác định hoặc một đối số mà tiếng Anh không có. Thông báo lỗi nêu tên khóa.
  • Ngôn ngữ của bạn không có trong bộ chọn ở bản phát hành: ngôn ngữ đó chưa hoàn chỉnh. Bản build phát triển hiển thị mọi ngôn ngữ.