This commit is contained in:
2026-09-16 10:22:36 +08:00
parent 48cec45fee
commit 09a25cdc6b
5 changed files with 559 additions and 2 deletions
@@ -106,10 +106,17 @@ class AuthoringCompiler:
sketch_id = f"sketch_{source_positions[feature.name]:03d}"
sketches.append({"id": sketch_id, **self._runtime_sketch(feature.sketch.model_dump(mode="json"))})
output["sketch_id"] = sketch_id
if feature.intent is not None:
# Semantic annotation only: carried through for training data,
# never consumed by runtime geometry or validation semantics.
output["intent"] = feature.intent.model_dump(mode="json", exclude_none=True)
features.append(output)
document_meta: dict[str, Any] = {"unit": "mm"}
if doc.meta is not None:
document_meta.update(doc.meta.model_dump(mode="json", exclude_none=True))
runtime = {
"schema": "cad.runtime.v1", "schema_version": "1.0.0", "kind": "part",
"part_id": "compiled", "meta": {"unit": "mm"},
"part_id": "compiled", "meta": document_meta,
"bodies": [
{"id": body_ids[body.name], "name": body.name}
for body in doc.bodies
@@ -108,6 +108,33 @@ class SelectorIntent(AuthorModel):
return value
class FeatureIntent(AuthorModel):
"""Feature-level semantic annotation for training data.
Mirrors ``$defs/featureIntent`` in ``cdsl_schema.json``: purely
descriptive, never read by the compiler for geometry decisions.
"""
label: str | None = Field(default=None, pattern=r"^[a-z][a-z0-9_]{2,63}$")
summary: str = Field(min_length=1, max_length=80)
why: str | None = Field(default=None, min_length=1, max_length=400)
ties_to_requirement: str | None = Field(default=None, pattern=r"^[A-Za-z0-9_.:-]{1,80}$")
provenance: Literal["authored", "annotated", "imported"]
class DocumentMeta(AuthorModel):
"""Document-level semantic annotation (part description and function)."""
description: str | None = Field(default=None, min_length=1, max_length=60)
function: str | None = Field(default=None, min_length=1, max_length=200)
@model_validator(mode="after")
def require_at_least_one(self) -> "DocumentMeta":
if self.description is None and self.function is None:
raise ValueError("meta requires at least one of description or function")
return self
class AuthorFeature(AuthorModel):
name: str = Field(pattern=_NAME)
operation: str = Field(pattern=r"^[a-z][a-z0-9_]{0,80}$")
@@ -121,6 +148,10 @@ class AuthorFeature(AuthorModel):
default=None,
description="For sketch operations: exactly {workplane, profile}. Circle profiles use diameter_mm and center_mm.",
)
intent: FeatureIntent | None = Field(
default=None,
description="Optional semantic annotation for training; never consumed by geometry.",
)
class AuthorBody(AuthorModel):
@@ -133,6 +164,10 @@ class AuthoringDocument(AuthorModel):
units: str = Field(default="mm", pattern=r"^mm$")
coordinate_system: str = Field(default="right_handed", pattern=r"^[a-z][a-z0-9_-]{0,40}$")
assumptions: list[str] = Field(default_factory=list, max_length=64)
meta: DocumentMeta | None = Field(
default=None,
description="Optional document-level semantic annotation (description/function).",
)
bodies: list[AuthorBody] = Field(min_length=1, max_length=32)
acceptance_targets: list[dict[str, Any]] = Field(default_factory=list, max_length=128)