CLIFF 格式速览
CLIFF(Contextual Localization Integrated File Format)1.0 是面向 AI 与人工评审设计的纯文本本地化格式。它把「哪条文本、什么类型、什么语气、什么状态、上下文是什么」写成人类可读、机器可校验、可直接喂给模型的字段,而不是把语义塞进键名。
本页只覆盖使用插件时必需的要点。权威规范见 cliff-format 仓库(spec/cliff-1.0.0.md 与 spec/abnf/cliff-1.0.abnf)。
文件骨架
CLIFF 1.0 # 版本行:必须是第一个非空非注释行,区分大小写
namespace: my-game # header:项目/产品标识
clan: settings # header:语义家族(一个文件 = 一个 clan)
source-language: en-US
target-language: zh-Hans
[video] # 分组行:点号表示嵌套,写完整路径
context: "Video settings screen." # 组元数据(仅 context/type/emotion/max-width)
type: label
emotion: [objective]
max-width: 12
<resolution> # 条目行:尖括号内的稳定 ID
source: "Resolution" # 必需
target: "分辨率"
status: final # 必需
- 顺序是硬性的:版本行 → header 字段 → 若干 section。
- 缩进不携带语义,字段可以完全平铺;空行只用于阅读。
- 注释只有整行
#(可选前导空白),没有行内注释,也没有 PO 风格的#./#:标记。
header 字段
| 字段 | 必需 | 说明 |
|---|---|---|
namespace | ✅ | 规范 ID 的第一段,小写 kebab-case(插件中来自 CLIFF Namespace 设置) |
clan | ✅ | 语义家族,对应一个 UE Namespace(经映射表解析) |
source-language | ✅ | BCP 47 源语言 |
target-language | ✅ | BCP 47 目标语言(与目录/文件名布局必须一致) |
version | ⛔ | 源内容/项目版本,如 "1.4.2"(不是 CLIFF 规范版本) |
variant | ⛔ | standard(默认)或 glossary |
title / info / standard | ⛔ | 族标题、族说明、翻译标准(standard 会被 AI 翻译当作准则) |
dependency | ⛔ | 依赖文件路径列表,如 ["../shared/terms.zh-Hans.cliff"] |
x-… | ⛔ | 扩展字段,严格校验器只警告不拒绝 |
NOTE
namespace+clan+ 分组路径 + 条目 ID 组成规范 ID:my-game.settings.video.resolution。它在文件内必须唯一,重复是硬错误(不允许「后者覆盖前者」)。
分组与继承
分组行 [video.advanced] 携带完整点号路径(不存在嵌套括号,也没有闭合标记)。写在第一条条目之前的组元数据只有四个键:context、type、emotion、max-width。
| 字段 | 是否继承 | 规则 |
|---|---|---|
context | ✅ | 组值 + 条目值,都以单个空格连接 |
type | ✅ | 条目覆盖组;两者至少要有一个 |
emotion | ✅ | 条目覆盖组(列表不合并) |
max-width | ✅ | 条目覆盖组 |
source / target / status / reference / reviewer | ⛔ | 从不继承,必须逐条写出(source、status 为必需) |
值的形状
CLIFF 里形状即类型,没有简写:
type: label # 标签:裸写、不加引号
status: final # 标签
emotion: [calm, polite] # 列表:必须加方括号
reference: ["src/ui.cpp:42"] # 列表:单项也要方括号
max-width: 24 # 正整数
source: "Hello " "world" # 相邻字符串自动拼接,得到 "Hello world"
target: "Line 1\nLine 2" # 字符串内的 \n 才是真正的换行
WARNING
写出
emotion: calm(缺方括号)、type: "label"(标签加了引号)、reference: "src/ui.cpp:42"(列表写成标量)在 CLIFF 1.0 中都是有效性错误。多行文本用相邻字符串拼接或\n,没有|之类的块标量语法。
固定词表
词表是封闭的,未列出的值会被拒绝:
| 字段 | 数量 | 取值 |
|---|---|---|
type | 26 | 词级:noun verb adjective adverb pronoun numeral preposition conjunction particle interjection proper-noun;短语级:noun-phrase verb-phrase adjective-phrase adverb-phrase fixed-phrase idiom;文本级:sentence description narration dialogue monologue prompt label subtitle accessibility-cue |
emotion | 23 | neutral objective mechanical joyful sad angry fearful surprised curious disgusted anxious calm playful serious urgent romantic hopeful grateful formal informal polite rude nostalgic |
status | 4 | initial(无译文)translated reviewed final |
variant | 2 | standard glossary |
emotion 省略时按 type 取默认值:dialogue / monologue / idiom → [neutral],其余 → [objective]。完整含义见 词表与映射。
ICU 与占位符
CLIFF 不定义自己的占位符语法:source / target 中的 ICU MessageFormat(MF1 与 MF2)原样保留。唯一硬约束是含 { 或 } 的字符串必须花括号平衡;明显畸形的 ICU 应被拒绝。
<inbox-count>
source: "{count, plural, =0 {No new messages} one {# new message} other {# new messages}}"
target: "{count, plural, =0 {没有新消息} other {# 条新消息}}"
type: sentence
status: reviewed
NOTE
UE 的
FText::Format并不按 ICU 语义求值。插件导入时原样透传字符串,并在编译.locres时关闭格式校验(EGenerateLocResFlags::None),因此 ICU 文本可以安全地存放在 UE 中,由运行时或外部工具自行解释。
文件命名与布局
header 是权威,文件名与目录必须与 header 一致(任一不一致即校验失败):
<target-language>/<clan>.cliff # 目录布局(推荐,插件导出即此布局)
zh-Hans/settings.cliff
ja/settings.cliff
<clan>.<target-language>.cliff # 平铺布局(小项目可用)
settings.zh-Hans.cliff
编码约定:UTF-8(输入可带 BOM 并被忽略,规范输出无 BOM)、LF 换行(CRLF 被接受;裸 CR 无效)。
校验口径
插件内置的 FCliffDocument::ParseAndValidate 与 Python 参考实现 cliff_format.validate() 判定一致,issue 分为 7 类:syntax、semantic、vocabulary、icu、id、extension、warning。其中 extension 与 warning 不计入失败。
典型错误与告警:
| 类别 | 例子 |
|---|---|
syntax | 版本行不是 CLIFF 1.0、未闭合字符串、列表跨行、未知转义、entry 写在任何 section 之前 |
semantic | 缺 source / status / 有效 type、header 重复、translated 却没有 target、组元数据里出现非法键 |
vocabulary | type: paragraph、emotion: Sadness、status: Final(大小写与拼写都必须精确) |
id | 分组路径重复、条目 ID 重复、ID 含大写或下划线 |
icu | 花括号不平衡 |
extension | x- 扩展字段(仅警告,不失败) |
warning | status: initial 却带了 target;开启宽度检查后译文超出 max-width |
CLIFF 与 UE 的对应关系
| CLIFF | UE | 说明 |
|---|---|---|
clan | UE Namespace | 经 Clan to Namespace 映射表解析(如 display-name → UObjectDisplayNames) |
<group-path>.<entry-id> | UE Key | 有侧车时按侧车原样恢复,否则由分组路径与 ID 生成 |
source | manifest 源文本 | 写入 FLocTextHelper 的 Source |
target | archive 译文 | status: initial 只写 manifest,不写 archive |
type / emotion / status / context | archive KeyMetadataObj | 以 cliff.* 键持久化,UE 侧没有对应字段 |
细节见 语义映射 与 原键侧车。下一步:Dashboard 工作流。