AMIR:Aira Modeling Intermediate Representation 规范:模型身份、类型与值
主文档与完整目录。本分篇与主文档共同构成同一规范,版本、状态与权威以主文档为准;仅拆分阅读结构,条款编号和正文语义不变。
3. Document、Revision 与标识符
Section titled “3. Document、Revision 与标识符”3.1 Document
Section titled “3.1 Document”一个 canonical AMIR Document 必须是单个 JSON object。顶层字段如下:
| 字段 | 必需 | 语义 |
|---|---|---|
$schema |
是 | 所使用的 JSON Schema URI |
amirVersion |
是 | AMIR 语义版本,当前实现为 0.4.0 |
documentId |
是 | 跨 Revision 不变的 DocumentId |
revision |
是 | 当前 Revision 清单 |
settings |
是 | 单位、坐标系、容差与 Field 符号约定 |
parameters |
是 | ParameterId 到 Parameter 的 map,可为空 |
nodes |
是 | NodeId 到 Node 的 map |
bodies |
是 | BodyId 到稳定 body 身份及其当前权威输出的 map,可为空 |
product |
否 | 修订所有的产品结构、配置、物料身份及关联工程声明 |
assertions |
是 | AssertionId 到 Assertion 的 map,可为空 |
roots |
是 | 对外发布的具名根输出;可为空,执行时另行检查所请求输出 |
metadata |
否 | 标题、说明、标签等非几何语义信息 |
extensions |
是 | 命名空间化扩展,可为空 object |
除 extensions 外,顶层未知字段必须被结构验证器拒绝。Artifact、内核句柄、Geometry Certificate 和渲染缓存禁止内嵌进 Document;它们属于运行时 Artifact Store。
当前文档级 product 与草案中的通用 Assembly 运算端口是不同概念;不能由后者尚未实现推断产品结构不存在。
product.root 引用共享 Body 或装配定义,assemblies 中的重复引用展开为不同实例路径;所有定义引用必须存在,包含未使用定义在内的装配定义图必须无环。Body 保持零件几何的唯一权威,实例不复制出另一份建模定义。
配置、显式物料身份、关联图纸、工程尺寸、基准、公差和交换来源保存在同一产品声明中;几何求值、BOM、图纸与交换消费所选配置下的产品结果。声明字段存在不代表支持任意尺寸类型、修饰语义或制造标准。精确字段与接受域见当前 schema,组织方式见工程定义方案,实现与验证状态只见工作进度。
3.2 标识符
Section titled “3.2 标识符”DocumentId、NodeId、BodyId、ParameterId、ExpressionId、ConstraintId、AssertionId、SemanticRefId 和 ToleranceProfileId:
- 必须在所属 Document 中唯一;
- 必须匹配
^[A-Za-z][A-Za-z0-9._:-]{0,127}$; - 禁止包含
#、/、空白或依赖数组位置; - 一旦进入 committed Revision,身份不得通过“重命名”改变;可修改独立的
label; - 不得编码拓扑索引或执行顺序。
实现应该使用 UUID、ULID 或等价稳定 ID。本文示例使用可读 ID 仅为便于说明。
PortName 必须匹配 ^[A-Za-z][A-Za-z0-9_]{0,63}$。canonical PortRef 使用对象形式:
{ "port": { "node": "n.extrude", "port": "solid" } }字符串简写 n.extrude#solid 可以存在于表层语言中,但不得出现在 canonical AMIR。
3.3 Revision
Section titled “3.3 Revision”Revision 清单至少包含:
{ "id": "draft:01K3EXAMPLE000000000000000", "state": "draft", "parents": [], "operationCatalog": "amir.ops/0.1.0", "createdAt": "2026-08-29T00:00:00Z", "actor": { "kind": "human", "id": "user:example" }}规则如下:
state只能是draft或committed。- draft 的
id必须为draft:<uuid-or-ulid>,可以随候选事务废弃。 - committed Revision 必须不可变,
id必须为rev:sha256:<64 lowercase hex>。 - committed Revision 必须包含
modelHash、patchHash和authoringLockHash。authoringLockHash只锁定解释模型所需的 schema、Operation Catalog 与 semantic extension packages,不包含具体 kernel/platform build。 parents为 RevisionId 数组;常规提交恰有一个父版本,初始提交为空,合并提交可以多于一个。operationCatalog必须固定完整版本,不能使用latest、范围或未固定 URL。- 当前契约不含迁移记录,旧版字段直接拒绝;不提供修订迁移或兼容读取。
actor.kind只能是human、ai、service或import。
modelHash 与 RevisionId 的计算见第 14 节。
3.4 Evaluation identity
Section titled “3.4 Evaluation identity”Model Revision 与几何执行必须分离。一个 canonical Candidate 或 committed Revision 可以在 browser、native 或 server 上产生多个 Evaluation,而不会改变 AMIR 或 RevisionId。Evaluation 的计算身份由模型语义内容决定,不要求预先存在尚未提交的 RevisionId。
EvaluationId 必须为:
eval:sha256(SHA-256(JCS({ modelHash, authoringLockHash, executionManifestHash, executionClass, qualityProfileId, inputArtifactsByLogicalKey})))inputArtifactsByLogicalKey 是以稳定逻辑输入名为 key 的 map,不得使用依赖枚举顺序的裸数组。ExecutionManifest 固定 compiler/adapter/kernel/plugin build、平台和浮点策略、线程/seed、实际 tolerance、资源策略与 capability resolution。Artifact 和 Geometry Certificate 必须绑定 EvaluationId。
Evaluation provenance 使用独立、不可变的 EvaluationBinding 关联 source subject:{revisionId},或 {candidateId, baseRevision, patchHash}。Candidate 在提交后,如果 modelHash、authoringLockHash、ExecutionManifest、execution class、quality profile 和输入 artifacts 完全相同,可以复用同一 EvaluationId;commit 另写一个 Revision binding 与新的 committed Certificate,不修改原 candidate binding/certificate。更换 kernel、平台或 quality profile 只创建新 Evaluation;只有 AMIR 语义或 authoring lock 改变时才创建新 Model Revision。
{ "evaluationId": "eval:sha256:...", "modelHash": "sha256:...", "authoringLockHash": "sha256:...", "source": { "candidateId": "candidate:sha256:...", "baseRevision": "rev:sha256:...", "patchHash": "sha256:..." }}4. 类型系统、单位与 Value
Section titled “4. 类型系统、单位与 Value”4.1 类型表达式
Section titled “4.1 类型表达式”AMIR 是名义类型系统。Operation Catalog 中的所有公共 Port 必须声明完整类型;禁止使用无约束的 Any、宿主语言对象或内核类名。
本版基础类型至少包括:
- 标量:
Bool、Int、Count、Real、String、BytesHash;Count是非负整数名义类型,不从负值或任意Int隐式构造; - 量纲:
Length、Angle、Area、Volume、Mass、Time、Ratio; - 空间值:
Point2、Point3、Direction2、Direction3、Vec2<T>、Vec3<T>、Quaternion、Transform3D、Axis2D、Axis3D、Plane3D、Box2D、Box3D; - 几何:第 4.4 节定义的表示类型;
- 集合:
List<T>、Set<T>、Optional<T>、Map<String,T>; - 选择结果:
EntitySet<Face>、EntitySet<Edge>、EntitySet<Vertex>、EntitySet<SketchEntity>、EntitySet<Instance>。
泛型类型使用 Name<T,...> 的 canonical 字符串形式。Operation Catalog 必须解析类型表达式,不能把它当作仅供显示的字符串。
4.2 单位与量纲
Section titled “4.2 单位与量纲”每个有量纲常量必须显式携带单位。settings.units 只是表层输入和 UI 的默认单位,不能使 canonical 常量省略单位。
settings 必须包含 units、coordinateSystem、tolerances 和 fieldConvention。本版 canonical 坐标系必须明确 handedness、up axis 与 forward axis。fieldConvention 必须固定为本文定义的 negative/zero/positive,保留该字段是为了让 adapter 错误可被结构检查发现,而不是允许 Document 改变符号约定。
settings.tolerances 是内嵌、版本化的 ToleranceProfile,至少包含:
| 字段 | 类型 | 用途 |
|---|---|---|
profileId |
ToleranceProfileId | 稳定配置身份 |
profileVersion |
SemVer | 配置 schema/取值版本 |
modelingLinear |
Length | 建模退化、重合与最小几何尺度基线 |
modelingAngular |
Angle | 建模方向/角度判等基线 |
intersectionLinear |
Length | 曲线/曲面相交判定 |
fuzzyBooleanLinear |
Length | 仅供 descriptor 明确允许的 fuzzy Boolean 使用 |
sewingLinear |
Length | sewing/healing 接合阈值 |
constraintLinearResidual |
Length | 约束求解线性残差上限 |
constraintAngularResidual |
Angle | 约束求解角度残差上限 |
validationDistance |
Length | 跨执行几何距离与验证比较 |
quantityRelative |
Ratio | 面积、体积、质量等量值的相对比较 |
所有数值字段都必须使用第 4.3 节的 canonical const Value。优先级固定为:Document ToleranceProfile → Operation descriptor 明确允许的普通 input override → adapter 计算出的 effective value。前两层属于模型语义并进入 model/subgraph hash;effective value 属于 ExecutionManifest、EvaluationId 和 Certificate。Adapter 不得静默放宽阈值;若内核不能满足请求,必须失败或由显式 Patch 修改 profile/input 后重新验证。
Tessellation、Field sampling/cell size 和导出精度不是可被全局 epsilon 偷偷替代的容差:canonical conversion Node 必须把它们写成普通 input 并进入 modelHash;仅用于视图或导出的值写入独立 view/delivery quality profile,并进入对应 Evaluation/job hash。
本版必须识别:
- 长度:
um、mm、cm、m、in、ft; - 角度:
rad、deg; - 时间:
ms、s; - 质量:
g、kg; - 面积和体积:上述长度单位的
^2、^3形式,例如mm^2、m^3; - 比例:
1,百分比必须在表层解析时转换为Ratio,canonical 值不保存%。
单位区分大小写。实现必须用固定单位表进行转换,禁止使用当前 locale。角度不是普通 Real;三角函数必须接受 Angle,返回 Real。允许的隐式赋值只有:
Int到Real;- 同一量纲内的单位归一化;
- 第 4.5 节明确规定的 Field 子类型提升。
Length 与 Angle、Length 与 Real、Area 与 Length 之间禁止隐式转换。
4.3 常量编码
Section titled “4.3 常量编码”为避免不同 JSON parser 和语言对浮点字面量的解释差异,所有 Int、Count、Real 和有量纲数值的 canonical value 必须是十进制字符串。它必须为有限值,不得为 NaN、Infinity、指数或十六进制;-0 必须规范化为 0。
Int使用^-?(?:0|[1-9][0-9]*)$,但禁止-0。Count使用^(?:0|[1-9][0-9]*)$。Real与有量纲十进制使用^-?(?:0|[1-9][0-9]*)(?:\.[0-9]*[1-9])?$,禁止尾随零、小数点无小数和正号;物理值为零时统一写0。
实现必须对数位总长度设置一致的 schema 上限,并在 conformance fixtures 中覆盖极小值、极大值、负值、零和等价非规范输入。
{ "const": { "type": "Length", "value": "12.5", "unit": "mm" } }{ "const": { "type": "Vec3<Length>", "value": ["0", "0", "25"], "unit": "mm" } }{ "const": { "type": "Bool", "value": true } }Enum 值使用其名义类型和字符串值,例如:
{ "const": { "type": "PrincipalPlane", "value": "XY" } }4.4 几何表示类型
Section titled “4.4 几何表示类型”| 类型 | 契约 |
|---|---|
Sketch2D |
位于明确 Plane3D 上的稳定 2D entity 集、约束及求解状态;允许 under-constrained,但必须报告 DOF |
Profile2D |
已求值、闭合、定向、无自交的平面区域,可含孔;不满足条件时不得产出此类型 |
ExactSolid |
以拓扑 B-Rep 和解析/参数曲面为权威表示的有效 solid;允许内部容差和浮点算法,不等于数学精确证明 |
ExactSurface |
B-Rep surface/shell,不承诺封闭体积 |
RawMesh |
未经 solid 契约验证的顶点/面数据,可开放、自交或非流形 |
MeshSurface |
已验证索引和定向的表面网格,但可开放 |
MeshSolid |
定向、封闭、watertight 的 2-manifold 网格;可有多个连通分量,分量数写入证书 |
Field3D<K> |
三维标量场,K 为第 4.5 节的场契约;AMIR 统一采用负内、零面、正外 |
Assembly |
具名 part/assembly instance、变换和 mate 的层级图;它本身不是 fused solid |
DisplayMesh |
Runtime-only 派生三角网格,用于显示、拾取和 source mapping;禁止作为 canonical Node output、Body authority 或 authoring root |
每个 root part/body 必须有且只有一个权威表示。一个 Feature DAG 可以同时包含不同表示,但转换必须是显式 Node。ExactSolid、MeshSolid 与 Field3D<K> 之间不存在隐式可赋值关系。
导入 STL 或任意 BufferGeometry 必须先得到 RawMesh;只有验证或修复操作满足 MeshSolid 后置条件后,才可以产出 MeshSolid。
Assembly 中的实例必须引用已存在的 part/assembly root 和显式 Transform3D。Assembly 实例图必须无环。对 Assembly 做 Boolean、体积或制造检查前,必须显式选择 flatten、fuse 或逐实例策略。
4.5 Field 类型与子类型
Section titled “4.5 Field 类型与子类型”Field 的统一符号约定为:内部 < 0、表面 = 0、外部 > 0。Field 表达式图本身必须是有限、纯数据且可静态估算的,但其数学定义域可以是全空间。适配使用正内负外的内核时,adapter 必须翻转符号并在 provenance 中记录;调用方不得自行猜测。
三种 Field 契约为:
Field3D<TrueSDF>:值的绝对值在声明误差内等于到零面的欧氏最短距离;值类型必须是Length,并满足符号约定。Field3D<ConservativeDistance>:符号正确,且绝对值不高估到零面的距离;Operation 可以另行声明 Lipschitz 上界。适合安全步进,但不是精确距离。Field3D<GeneralImplicit>:只保证符号和零等值面语义;值可以是Length或Real,不得被距离步进器当作 SDF 使用。
子类型关系为:
Field3D<TrueSDF> <: Field3D<ConservativeDistance> <: Field3D<GeneralImplicit>提升可以隐式发生,降级转换禁止隐式发生。Operation 必须在 Catalog 中声明 Field kind 的传播规则。例如刚体变换保持 kind;正确缩放场值的均匀缩放可保持 kind;非均匀缩放、warp、平滑 Boolean 默认降级为 GeneralImplicit,除非 Operation descriptor 提供更强且可验证的契约。
Field 输出 Port 必须声明:
- kind;
- value type;
- 符号约定;
mathematicalDomain:allSpace或显式有界 domain;surfaceBounds:若能证明零面的有限Box3D包围盒则提供,否则为null;- 已知 Lipschitz bound,未知时为
null; - 梯度能力:
analytic、automaticDifferentiation、finiteDifference或none。 normalizationOrder:已证明时为正整数,否则为null;依赖正规化的 offset/shell capability 必须要求 足够的已证明 order,禁止从TrueSDF类型名自行猜测。
evaluationClip 是一次预览、测量或采样 job 的有限求值裁剪范围,属于 Evaluation/job identity,不改变 Field 的数学语义。meshingBounds 是 Field → Mesh conversion 的必需、有限 Box3D input,属于模型语义并进入 modelHash。数学上无界或 surfaceBounds = null 的 Field 合法,但任何有限成本的求值都必须显式提供 evaluationClip,任何权威 meshing 都必须显式提供 meshingBounds;不得依赖隐藏默认包围盒。
当前最小闭合实现见 Field IR v0.1 与
field-ir.schema.json。它只实现
sphere/box/union/intersection/difference,不是完整 Phase 2 Field language。sphere 发布
normalizationOrder=1;box 因边/角不可微保留 null;Boolean 按本节规则降级为 GeneralImplicit 且 order
为 null。每个 node 的派生 contract 与 root contract 都进入 fieldId,runtime 必须重算并拒绝篡改。
4.6 Value
Section titled “4.6 Value”Node input、Parameter、Root、Constraint value 和事务值均使用同一个 Value tagged union。一个 Value object 必须且只能包含下列 discriminator 之一:
{ "const": { "type": "Length", "value": "10", "unit": "mm" } }{ "parameter": "p.width" }{ "expression": "e.depth" }{ "port": { "node": "n.profile", "port": "profile" } }{ "semanticRef": "s.outerEdges" }{ "constraint": "c.horizontal" }{ "body": "body.main" }{ "list": [{ "parameter": "p.a" }, { "parameter": "p.b" }] }{ "record": { "x": { "const": { "type": "Real", "value": "1" } } } }list 的所有元素必须满足目标 List<T> 的元素类型。record 只能赋给 Operation Catalog 中具名的 record type,禁止作为绕过静态类型的任意 object。
Expression 使用受限的 ExprTerm:它的叶子只能是 Value 中的 const、parameter 或 expression,并额外允许第 6.2 节的 call。PortRef、SemanticRef、ConstraintRef、list 和 record 不得直接出现在本版 Expression 中。