PhotoPrism 前端多语言本地化完全指南:gettext 工作流、翻译文件与构建流程
后端前端图像处理人工智能AI 应用【免费下载链接】photoprismAI-Powered Photos App ✨项目地址https://gitcode.com/gh_mirrors/ph/photoprism点击查看免费下载本篇技术指南以 PhotoPrism 仓库中 frontend/src/locales/README.md 为核心系统讲解 PhotoPrism 如何基于 gettext 标准完成前端及后端的多语言本地化从*.po/*.pot翻译文件的结构与命名规范到用 Poedit 创建、更新翻译的操作步骤再到make gettext-extract、npm run gettext-compile等构建命令的底层实现与源码证据。读完本文你将掌握为 PhotoPrism 添加一门新语言、维护现有翻译、在开发环境中编译并验证多语言界面的完整实战流程。PhotoPrism 的本地化架构前端与后端共用同一套 gettext 标准PhotoPrism 使用 gettext 作为前后端统一的本地化标准它是翻译用户界面时被广泛采用的标准之一见 frontend/src/locales/README.md。这一设计带来的核心约定是以人类可读的英文消息作为翻译 ID例如File not found本身就是msgid翻译系统依靠它查找对应的译文同一字符串在没有翻译时自动作为默认文案回退因此即使某个语言尚未翻译完成界面也不会出现空白或乱码支持占位符插值消息中可包含%{n}之类的占位符用于数字等动态变量例如%{n} files found。从源码实现看这一约定在前端运行时被 frontend/src/common/gettext.js 具体兑现function interpolate(message, params {}) { // ... return text.replace(/%\{(\w)\}/g, (_, key) { // 用 params 中的值替换 %{key} 占位符 }); }这段代码负责把%{n} files found中的%{n}替换为实际数字。需要说明的是占位符命名语法在前后端存在差异前端*.vue/*.js源码中的动态消息使用%{n}花括号风格而后端 Go 代码镜像自 pkg/i18n/messages.go的占位符则是 Go 的 printf 动词风格如%s、%d。frontend/src/common/gettext.js中的Tp()函数专门桥接了这两种风格——它先用英文源消息 id 查译文再通过interpolatePositional()按顺序把有序参数数组逐一填入%s、%d等位置占位符从而让后端推送的通知也能以当前 UI 语言渲染。为此 frontend/src/locales.js 中专门定义了BackendMessages()把后端可能出现的通知消息如Something went wrong, try again、%d files uploaded in %d s注册到前端目录中供提取翻译。翻译文件布局locale 命名、.po/.pot/.mo/.json的分工仓库中所有前端翻译文件都集中在 frontend/src/locales 目录每个语言对应一个*.po文件以 locale 名称 命名。从该目录的实际内容可以看到当前维护的 46 种语言例如de.po—— 德语pt_BR.po—— 巴西葡萄牙语注意下划线写法与葡萄牙语pt.po区分zh.po—— 简体中文、zh_TW.po—— 繁体中文he.po、ar.po、fa.po、ku.po—— 希伯来语、阿拉伯语、波斯语、库尔德语均为从右向左书写的 RTL 语言这些语言在 frontend/src/locales.js 的Options数组中统一注册包含显示名称如简体中文、locale 值如zhRTL 语言还会带rtl: true标记前端据此自动切换排版方向。各类文件的职责划分如下文件作用说明translations.pot模板文件Portable Object Template由源码自动提取生成的待翻译字符串清单是所有语言翻译的基准见 frontend/src/locales/translations.pot*.po各语言的翻译文件Portable Object每条消息含msgid源字符串与msgstr译文可用 Poedit 打开编辑*.mo编译后的机器对象文件Machine Object随*.po自动生成供程序高效读取文本编辑器无法直接阅读json/前端运行时加载的编译结果每个 locale 一个 JSON 文件由gettext-compile生成前端可直接 import打开 frontend/src/locales/en.po 可以看到典型条目结构#: src/locales.js:272 msgid {0} appended action msgstr 而 frontend/src/locales/zh.po 中对应条目则是#: src/locales.js:272 msgid {0} appended action msgstr {0}附加行动其中#:开头的注释行记录了该字符串在源码中的引用位置如src/page/photos.vue:529便于译者定位上下文。注意en.po与translations.pot的差异en.po带有完整的文件头元信息Project-Id-Version、Last-Translator、Plural-Forms等而translations.pot仅保留最基本的头信息因为它是模板而非某个具体语言的翻译。用 Poedit 创建与更新翻译从打开 POT 到保存 POPhotoPrism 官方强烈推荐使用 Poedit 创建和更新翻译它在 Mac、Windows、Linux 上均可免费下载使用其源码托管在 GitHub 上的 vslavik/poedit 项目。*.po文件可以用 Poedit 打开、编辑并保存以更新现有翻译。添加一门全新语言的完整流程用 Poedit 打开 frontend/src/locales/translations.pot点击窗口底部的Create New Translation创建新翻译在弹出的对话框中选择目标语言即可开始逐条翻译翻译完成后以 locale 名称作为文件名保存为*.po文件例如德语保存为de.po、巴西葡萄牙语保存为pt_BR.po并放入frontend/src/locales/目录在 frontend/src/locales.js 的Options数组中登记新语言否则该语言不会出现在前端语言选择器中。参照现有条目添加即可RTL 语言记得加上rtl: true。更新已有翻译当源码新增了待翻译字符串后在 Poedit 菜单栏执行Catalogue Update from POT File...目录 从 POT 文件更新选择新的translations.potPoedit 就会把新增的msgid合并进当前语言的*.po已有译文保持不变只翻译新增条目即可。Git 提交时的文件取舍保存*.po时Poedit 会自动在旁生成对应的二进制*.mo文件。.mo无法在文本编辑器中阅读但必须随.po一起包含在 git 提交中或在你通过邮件发送翻译时一并附上。相反编译生成的*.json文件不需要提交frontend/src/locales/json/目录在 PR 中应保持缺席——因为它经常引发合并冲突且可由gettext-compile随时重新生成。开发环境验证编译 JSON、构建与实时重载如果你已经搭好可用的开发环境可以通过以下命令在本地完整走一遍翻译 → 编译 → 预览链路。第一步把 PO 编译成前端可用的 JSON在frontend目录下运行npm run gettext-compile该命令由 frontend/package.json 定义实际执行vue-gettext-compile --config gettext.config.js会把frontend/src/locales/下现有的全部*.po翻译编译成可由前端 import 的*.json文件。注意命令中设置了GETTEXT_MERGE1对应配置见 frontend/gettext.config.js 的逻辑当GETTEXT_MERGE非 0 或 false 时vue3-gettext 会通过 msgmerge 把msgstr条目合并进编译结果。编译配置的其余关键点同样集中在 frontend/gettext.config.js输入范围include默认覆盖src/**/*.{vue,js,ts}并排除src/common/gettext.js避免把运行时插值函数误当作翻译源输出位置potPath为translations.potjsonPath为json且splitJson: true、flat: true即每个语言生成一个扁平结构的 JSON 文件语言清单locales直接通过 glob 扫描src/locales/*.po动态生成见 frontend/gettext.config.js所以新增语言只需放入.po文件即可被自动识别。第二步构建前端或启动 watch 模式编译完成后运行npm run build或者让下面这条命令在后台保持运行每当源码或翻译文件发生变化时自动重新编译 JS 和 CSSnpm run watchwatch脚本对应 frontend/package.json 中的vite build --watch由 Vite 驱动增量重建。第三步在 Web UI 中验证确保photoprism服务正在运行然后在受支持的浏览器中打开 Web UI。进入Settings设置切换语言后界面会自动触发一次重载新语言即刻生效。语言切换的具体实现位于 frontend/src/locales.js 的Locale()函数它从配置中读取当前语言 locale 与 RTL 状态把Messages(T)编译出的消息对象按 locale 打包返回给 vue3-gettext 运行时。提取新字符串从源码扫描到 POT 更新的完整链路当你在*.js或*.vue源码中新增了界面文案通过$gettext(...)等调用包裹需要重新提取这些待翻译字符串并更新 POT 模板。在仓库根目录运行make gettext-extract该目标定义于 Makefile实际调用./scripts/gettext-extract.sh。深入阅读 scripts/gettext-extract.sh 可以看到完整执行流程首先确定扫描目录列表始终包含frontend/src并自动检测可用的私有前端 overlay——plus/frontend、pro/frontend、portal/frontend目录存在时也会加入扫描这正是 README 中自动扫描社区版源码及私有前端 overlay的底层实现另外可通过GETTEXT_EXTRA_SRC环境变量追加额外的源码目录在frontend目录内以SRC... GETTEXT_MERGE0 npm run gettext-extract执行提取GETTEXT_MERGE0表示提取 POT 时跳过 msgmerge 自动回填用sed把 overlay 目录的相对引用如../plus/frontend统一替换为src保证translations.pot中的源码引用位置在不同构建环境与私有 overlay 下保持稳定最后调用 scripts/gettext-merge.sh用msgmerge --previous --no-fuzzy-matching --update把新模板合并回各个*.po同时也会合并后端的assets/locales目录。如果你只希望扫描 Community Edition社区版源码、不包含任何私有 overlay可以仅运行cd frontend npm run gettext-extract这对应 frontend/package.json 中不带SRC环境变量的提取命令此时 frontend/gettext.config.js 会把扫描目录回退为默认的src。翻译维护的最佳实践小结翻译 ID 即默认文案请保证msgid是准确、人类可读的英文句子因为它在任何未翻译的语言中会直接显示给用户占位符不可翻译%{n}、%s、%d等占位符必须原样保留在译文中否则运行时插值会失败。前端使用%{name}花括号风格、后端通知使用 Go printf 风格%s/%d两者分别由frontend/src/common/gettext.js的interpolate与interpolatePositional处理提交.po与.mo跳过json/避免 JSON 编译产物进入 PR 引起合并冲突提取、更新、编译三步走源码改动后执行make gettext-extract更新 POT 与各语言文件在 Poedit 中用 Update from POT File... 完成翻译最后用npm run gettext-compile编译验证新增语言要登记除创建*.po外务必在 frontend/src/locales.js 的Options中注册RTL 语言加rtl: true后端消息共用同一目录后端通知类消息通过 frontend/src/locales.js 的BackendMessages()注册进前端目录配合Tp()实现后端发消息、前端按当前语言翻译的体验。通过以上流程任何贡献者都可以为 PhotoPrism 添加一门新语言或在数分钟内更新现有翻译并借助npm run watch在本地即时预览效果。赞分享后端前端图像处理人工智能AI 应用【免费下载链接】photoprismAI-Powered Photos App ✨项目地址https://gitcode.com/gh_mirrors/ph/photoprism点击查看免费下载相关推荐Comprehensive Rust 多语言翻译工作流实战指南基于 Gettext 的 .po 文件本地化体系Comprehensive Rust 多语言翻译工作流实战指南基于 Gettext 的 .po 文件本地化体系 Comprehensive Rust 是 Go文档教程Cataclysm-DDA多语言支持完整指南gettext集成与翻译工作流优化Cataclysm DDA多语言支持完整指南gettext集成与翻译工作流优化 Cataclysm DDA作为一款开源的回合制生存游戏通过强大的 gette游戏开发Karabiner-Elements 多语言本地化完全指南JSON 翻译文件结构与 make install 流程解析Karabiner Elements 多语言本地化完全指南JSON 翻译文件结构与 make install 流程解析 导读 Karabiner Elemen开发工具上一篇从实验记录到模型上线MLflow 实验跟踪与部署实战下一篇3步搞定让《星际争霸》《红警2》等经典游戏在Windows 10/11重获联机生命创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考