# gt: General Translation CLI tool: 键级元数据 URL: https://generaltranslation.com/zh/docs/cli/reference/keyed-metadata.mdx --- title: 键级元数据 description: JSON 和 YAML 文件中针对每个键的翻译元数据 --- ## 概述 键级元数据允许你为 JSON 和 YAML 文件中的各个键附加翻译说明。你需要提供一个配套的 `.metadata.json` 或 `.metadata.yaml` 文件,它会映射源文件的键结构,并在叶子节点层级放置元数据对象。 CLI 会自动检测这些配套的元数据文件,依据源文件结构进行校验,并将其发送给翻译引擎。 *** ## 文件结构 配套的元数据文件必须: * 与源文件位于同一目录 * 遵循 `{name}.metadata.{ext}` 的命名约定 (例如,`translations.json` 对应 `translations.metadata.json`) * 键结构与源文件保持一致 ``` translations.json # 源字符串 translations.metadata.json # 各键的元数据 ``` 元数据文件与源键结构保持一致,只是在叶子节点处使用元数据对象而非字符串: ```json title="translations.json" { "nav": { "home": "Home", "bank": "Bank", "save": "Save" }, "alerts": { "new_lead": "You have a new lead!" } } ``` ```json title="translations.metadata.json" { "nav": { "bank": { "context": "河岸——河流的岸边。不是金融机构。" }, "save": { "context": "体育术语——守门员扑救阻止进球。不是保存数据。", "maxChars": 12 } }, "alerts": { "new_lead": { "context": "销售/CRM 语境。'lead' 指潜在客户。", "maxChars": 30 } } } ``` 并非每个键都需要元数据——`home` 在上方没有对应条目,也会照常翻译。只需为需要特定翻译说明的键提供条目。 *** ## 字段参考 | 字段 | 类型 | 必填 | 说明 | | ------------ | --------------------------------------------------------------------- | -- | ------------------ | | `context` | `string` | 否 | 该字符串的翻译说明 | | `maxChars` | `number` | 否 | 翻译输出的最大字符数 | | `sourceCode` | `Record` | 否 | 周围源代码的上下文,按文件路径作为键 | *** ## 字段 ### `context` 类型:`string` 应用于特定字符串的翻译说明。使用它来消除一词多义带来的歧义、指定领域术语,或说明期望表达的含义。 ```json { "bank": { "context": "Riverbank. The side of a river where land meets water, NOT a financial institution." } } ``` ### `maxChars` 类型:`number` 对译文输出施加的最大字符限制。引擎会使用更短的近义表达、缩写或更精简的措辞,以尽量控制在该限制内。这是尽力而为的机制。如果源内容无法满足该限制,则会返回完整译文。 ```json { "save": { "maxChars": 10 } } ``` ### `sourceCode` 类型:`Record` 字符串的周边源代码上下文。以文件路径为键,每个条目包含: * `before` — 目标行上方的源代码行 * `target` — 包含待翻译字符串的那一行 * `after` — 目标行下方的源代码行 如果同一个字符串在不同位置出现,则同一文件支持多个条目。 ```json { "new_lead": { "sourceCode": { "components/Dashboard.tsx": [ { "before": "function NotificationBanner({ type }) {\n const gt = useGT();", "target": " const msg = gt('You have a new lead!');", "after": " return {msg};\n}" } ] } } } ``` ### 综合示例 单个键包含全部三个字段: ```json { "save_button": { "context": "Sports term. A goalkeeper's save — preventing a goal from being scored. NOT saving data.", "maxChars": 12, "sourceCode": { "components/MatchStats.tsx": [ { "before": "const stats = useMatchStats();\nconst gt = useGT();", "target": "const label = gt('Save');", "after": "return }>{label}: {stats.saves};" } ] } } } ``` *** ## YAML 对于 `.metadata.yaml` 或 `.metadata.yml` 配套文件,做法也相同: ```yaml title="translations.metadata.yaml" ui: buttons: save: context: "体育术语。守门员的扑救,而非保存数据。" maxChars: 12 draft: context: "生啤酒,即扎啤。而非文档版本。" labels: date: context: "椰枣树的可食用果实。而非日历日期。" ``` *** ## 验证 CLI 会根据源文件的结构来验证元数据文件。出现以下情况时,进程会报错并退出: * 元数据键在源文件中不存在 * 源文件中是嵌套对象,但元数据值是基本类型 * 源文件中是对象,但元数据值是数组 (或反过来) * 根类型 (数组或对象) 与源文件不一致 * 元数据文件无法解析 *** ## Schema 支持 键级元数据支持 JSON schema (`include` 和 `composite`) 以及 YAML schema (`include`) 。这些元数据会沿用与源内容相同的 schema 处理流程自动转换,因此无论文件结构如何,翻译时的键路径都能保持一致。 *** ## 配套文件过滤 配套元数据文件会自动匹配到对应的源文件,不会作为独立文件单独翻译。只有当文件列表中存在对应的源文件时,才会应用此规则。没有匹配源文件的 `.metadata.json` 文件会被视为普通文件。 *** ## 重新翻译行为 如果源内容未发生变化,仅修改元数据文件不会触发重新翻译。要应用更新后的元数据,源内容也必须同时发生变化。