prometeu-studio/discussion/lessons/DSC-0025-packer-pipeline-metadata-ownership/LSN-0039-runtime-header-boundary-and-tooling-owned-pipeline-metadata.md

4.3 KiB

id ticket title created tags
LSN-0039 packer-pipeline-metadata-ownership Runtime Header Boundary and Tooling-Owned Pipeline Metadata 2026-04-10
packer
metadata
runtime-contract
tooling
codec
assets-pa

Context

The packer had drift between implementation and spec around output.pipeline ownership. The runtime-facing artifact assets.pa was documented as if pipeline metadata should materialize under asset_table[].metadata.pipeline, while the implementation already treated at least part of that surface as tooling-oriented and excluded palette payloads from the runtime header.

This created the wrong architectural pressure: Studio and third-party tools could start depending on assets.pa for authoring/build provenance, and runtime-facing specs could silently absorb build-time structures that do not belong in the execution contract.

The discussion resolved that split explicitly and implemented it end to end in specs, packer materialization, and tests.

Key Decisions

Tooling Metadata Must Not Leak Into the Runtime Header

What: output.pipeline remains tooling-only metadata in asset.json and related sidecar outputs. The runtime-facing assets.pa header must not mirror output.pipeline by default. Runtime-owned metadata remains under explicit, normalized fields in asset_table[].metadata.

Why: assets.pa is the authoritative runtime artifact. If it starts carrying build provenance, editor-oriented structures, or reverse-sync payloads merely because they exist in the authoring manifest, the runtime contract becomes larger, noisier, and harder to evolve safely.

Trade-offs: Tools that want provenance cannot rely on one binary artifact alone. They must read asset.json and/or build/asset_table_metadata.json. That is a deliberate trade-off in favor of a cleaner runtime boundary.

Promotion Must Be Explicit, Not a Bulk Mirror

What: If pipeline-derived information is needed at runtime, it must be promoted into an explicit normative field under runtime-owned metadata. The packer must not reintroduce a generic mirrored pipeline object under another name.

Why: Bulk mirroring hides product decisions inside implementation convenience. Explicit promotion forces each field to justify its presence in the runtime contract.

Trade-offs: This adds small editorial and implementation work whenever a new runtime-facing derived field is introduced, but it keeps the contract intentional and testable.

Codec Serialization Must Stay in SCREAMING_SNAKE_CASE

What: Serialized asset entry codec values are locked to SCREAMING_SNAKE_CASE. The currently known NONE value remains serialized as NONE.

Why: The implementation already had a stable manifest/runtime representation through OutputCodecCatalog. Recording that casing in spec prevents future drift when more codecs are added.

Trade-offs: Future codec additions must preserve the established serialized style unless a new decision explicitly revises the contract.

Patterns and Algorithms

  • Use separate surfaces for separate consumers: assets.pa for runtime contract, asset_table_metadata.json for tooling-oriented provenance, and asset.json for authoring intent.
  • Build runtime metadata from explicit normalized fields first, then derive tooling sidecars from a superset when needed.
  • Keep the runtime header free of raw authoring/build objects even if the sidecar keeps them intact for Studio or inspection tools.
  • Lock serialized enum casing in spec as soon as the first value ships, even if the current catalog is minimal.

Pitfalls

  • Do not treat “already present in the manifest” as sufficient reason to serialize a field into the runtime header.
  • Do not let sidecar convenience become implicit runtime compatibility.
  • Do not partially filter a tooling object and leave an empty placeholder in runtime metadata unless that placeholder has explicit runtime meaning.
  • Do not leave enum casing as an implementation accident. If the manifest value matters, the spec must say so.

Takeaways

  • The runtime header is a contract surface, not a metadata dump.
  • Tooling provenance belongs in asset.json and build/asset_table_metadata.json, not in assets.pa.
  • Runtime-facing derived metadata must be promoted explicitly field by field.
  • Stable serialized casing rules should be fixed in spec before the value set grows.