From 6ae005ed3a9625eda69c9619d914f0f2f59ea2ac Mon Sep 17 00:00:00 2001 From: Eric Rakestraw Date: Mon, 2 Nov 2026 03:46:24 +0000 Subject: [PATCH] Plan the ConfigKit v1 resource migration --- docs/roadmap/configkit.md | 115 ++----- docs/roadmap/implementation.md | 603 +++++++++++++++++++++++++++++++++ 2 files changed, 638 insertions(+), 80 deletions(-) create mode 100644 docs/roadmap/implementation.md diff --git a/docs/roadmap/configkit.md b/docs/roadmap/configkit.md index 39c14a3..fcb4a8c 100644 --- a/docs/roadmap/configkit.md +++ b/docs/roadmap/configkit.md @@ -3,6 +3,9 @@ Status: accepted direction; implementation pending. This roadmap describes future behavior, not the currently supported configuration format. +The companion [implementation plan](implementation.md) owns the ordered sprint +steps and validation assignments. + ## Purpose Adopt `go.maximumdirect.net/configkit` v1.0.0 and simplify authoring by using @@ -234,88 +237,40 @@ same item-import pattern with `destination: [backends]` and can define backend variants using sibling `extends`. Inline resource lists are equally valid; one-file-per-item and directory layout are conveniences, not requirements. -## Work And Sequencing +## Acceptance And Compatibility -### 1. Establish The ConfigKit v1 Baseline +The integrated target supports inline lists and imported items at the root and +in arbitrarily named collections. Equal local IDs in separate namespaces remain +independent. Registered identities govern strict composition, inheritance, +layering, and final typed values through ConfigKit. PromptKit retains its domain +validation, presence-aware settings, partial profiles, and exact runtime lookup. -Migrate the module, toolchain, affected APIs, and source controls while temporarily -retaining resource mappings. Update fixtures and examples and validate that -configuration loading, presence, inheritance, inspection, and execution retain -their intended behavior. This isolates dependency migration failures from the -later shape change; the intermediate state need not be separately released. +Inherited and replaced prompt fields retain their contributing resource context. +Sensitive provider values remain protected in inspection at index-based paths. +Source builders preserve supplied record order and duplicate IDs for loading. +Namespaces, discovery, inspection, preparation, concrete-request validation, +smoke diagnostics, and execution consume the same captured resource indexes. +These behaviors have focused offline coverage without duplicating ConfigKit's +generic suite or promising incidental history formatting or list positions. -Review module sums and the resolved dependency graph, and update -[attribution](../oss/attribution.md) to the selected upstream revision and notices. -ConfigKit's own release-tooling migration does not by itself require changing +The [format reference](../formats.md), [consumer migration guide](../consumers/configuration-migration.md), +[Go consumer guide](../consumers/pkg-promptkit.md), source-adapter documentation, +GoDoc, and maintained examples describe the integrated target when it lands. +Migration guidance covers the new module/types, Go minimum, controls, import +requiredness, identified lists, explicit-ID source builders, sibling inheritance, +removed prompt labels, specification headers, and index-based inspection paths. +Attribution identifies the selected ConfigKit revision and applicable notices. + +Deliver this as one coordinated breaking pre-v1 minor upgrade under the existing +[release policy](../policy/release.md), so applications and collection authors +migrate once. Historical release notes remain intact. Scriptorium coordination +does not make its release or internal implementation a PromptKit dependency. +ConfigKit's own release-tooling migration does not require a change to PromptKit's release tooling or publication workflow. -### 2. Convert The Configuration Adapter And Public Values - -Change root and collection resource decoding to identified records, register all -six root/dynamic identity rules, and advance the optional specification checker. -Adapt validation and runtime indexing to read IDs from records. Remove prompt -version metadata throughout the relevant public and internal values. - -Review every path-dependent operation as mapping keys become list indexes: -presence capture, profile/backend defaults, prompt input metadata, sensitive -provider fields, errors, and effective resource lookup. Resolve `content_file` -against the effective field's contributing source after inheritance and upsert. -Retain one ConfigKit load and the existing effective-value handoff; source history -must not become a second resolver. - -Update `BackendSource`, `ProfileSource`, and their public configuration values to -use explicit-ID slices and encode profile inheritance as an identity reference. -Update namespace views, listing, inspection, prepared execution, and smoke-test -selection as needed to consume the same captured runtime indexes. Do not change -their selection or execution semantics merely to mirror the new configuration -representation. - -### 3. Exercise The Integrated Target - -Use focused behavioral coverage for the changed boundaries: - -- Root and arbitrarily named collections load inline lists and imported items; - equal local IDs in separate namespaces remain independent. -- Duplicate IDs within a resource list fail, including final values introduced - through supported application resolution. Exercise the registrations through - PromptKit without duplicating ConfigKit's complete generic test suite. -- Profile and backend variants inherit settings while preserving child identity, - explicit zero/false/null behavior, and ordinary domain validation. -- Layered upsert replaces a whole record; explicit list replacement and empty - contributions follow ConfigKit semantics. -- Inherited and replaced prompt resources retain the correct source context; - provider credentials remain redacted at the new effective paths. -- Optional version-2 headers and headerless fragments load; unsupported declared - versions and obsolete resource shapes fail through their owning validators. -- Public source builders, namespace lookup, inspection, preparation, validation, - smoke tests, and execution still work with the converted catalogs. -- Source builders preserve supplied record order and duplicate IDs for loading; - profile parent-ID strings produce the expected sibling inheritance references. - -Run the existing suite, relevant vet checks, and maintained offline consumer -examples under Go 1.27. Tests require no live provider calls. Reuse existing -coverage where it already proves the behavior; do not turn incidental history -formatting or list positions into stronger guarantees. - -### 4. Publish One Coherent Migration - -Update the [format reference](../formats.md), [consumer migration guide](../consumers/configuration-migration.md), -[Go consumer guide](../consumers/pkg-promptkit.md), source-adapter documentation, -GoDoc, and maintained examples as implementation lands. Explain the module/type -change, Go minimum, `config:` controls, import requiredness, resource lists, -the source builders' map-to-slice conversion and explicit `ID` fields, -mapping-to-record `extends` conversion, removed prompt labels, specification -headers, and index-based inspection paths together. - -Plan a breaking pre-v1 minor release under the existing -[release policy](../policy/release.md). Prefer delivering both implementation -stages together so downstream applications and collection authors migrate once. -Keep historical release notes intact. Coordinate Scriptorium's dependency and -configuration updates without making its release or internal implementation a -PromptKit dependency. - -The target format replaces the old resource mappings; this scope does not add -dual-format decoding, source rewriting, catalog discovery conventions, or a -compatibility module. Preserve operator choices already supplied by ConfigKit. -Once implementation is complete, move durable behavior into its canonical -owners and retire this temporary roadmap under repository practice. +The target replaces the old resource mappings without adding dual-format +decoding, source rewriting, catalog discovery conventions, or a compatibility +module. Intermediate implementation states need not compile or be coherent; +the companion plan targets one end-to-end sprint without intermediate human +review or external publication gates. Durable behavior belongs in its canonical +owners when complete; this roadmap remains temporary coordination material. diff --git a/docs/roadmap/implementation.md b/docs/roadmap/implementation.md new file mode 100644 index 0000000..ae57caa --- /dev/null +++ b/docs/roadmap/implementation.md @@ -0,0 +1,603 @@ +# ConfigKit v1 And Identified Resources Implementation Plan + +Status: ready for implementation. + +Implement the accepted [feature roadmap](configkit.md) as one end-to-end sprint. +Each sequentially numbered stage is one prompt-sized assignment for a Luna +coding agent. The roadmap owns intent and policy; this plan owns delivery steps. + +## Baseline And Working Rules + +The reviewed baseline is `07a55e45f2a3c68918c12fe5caa3e814ee00227c`, with Go +1.26.0, ConfigKit v0.8.0 at the old module path, keyed resource mappings, and +descriptive prompt-version labels. No implementation changes accompany this +plan. The local ConfigKit checkout's v1.0.0 tag resolves to +`c88aac990b23f48a31f9046b830d4d0954f57f53`; its release note and configuration +contract were reviewed for the decisions below. + +Upstream references are the [v1 migration note](https://forge.maximumdirect.net/base-layer/configkit/src/commit/c88aac990b23f48a31f9046b830d4d0954f57f53/docs/releases/v1.0.0.md) +and [configuration contract](https://forge.maximumdirect.net/base-layer/configkit/src/commit/c88aac990b23f48a31f9046b830d4d0954f57f53/docs/config.md). +The local `../ConfigKit` checkout can supply the same tagged documentation for +development; it is not a committed dependency replacement or a test prerequisite. + +Before each assignment, use [development orientation](../development.md) and +read the applicable [agent](../policy/agents.md), +[architecture](../policy/architecture.md), [testing](../policy/testing.md), +[documentation](../policy/documentation.md), [OSS](../policy/oss.md), or +[release](../policy/release.md) policy. Preserve the accepted +[configuration-boundary ADR](../adr/0001-configuration-boundary.md). + +- Complete stages in order. Intermediate stages may fail compilation or tests + belonging to later stages. Record those known dependencies and continue; + do not add compatibility shims, duplicate fixtures, or temporary architectures + merely to make each checkpoint green. The completed sprint must be coherent. +- Dependency/API migration precedes the list migration to isolate the kinds of + changes, not to require a separate release or a fully migrated intermediate + test suite. Convert each substantive fixture to its final form once where + practical. +- Use focused validation when the affected package can run. When it cannot, + review the changed code and defer execution to the identified later stage. + Do not report deferred checks as passing. There are no intermediate human + approval, downstream release, catalog publication, or live-provider gates. +- After a completed nonempty unit, record its completion and checks beneath its + stage and commit under the agent policy. Do not create empty commits. Update + exact GoDoc as declarations change; final documentation stages reconcile the + wider narrative. +- Keep scope to the roadmap. PromptKit's module path, generation behavior, + capacity policy, runtime overrides, and application ownership remain intact. + This sprint does not authorize tagging, pushing, or changes in other projects. + +## Delivery Decisions + +### Dependency, Controls, And Headers + +Select `go.maximumdirect.net/configkit v1.0.0` directly and declare +`go 1.27.0`. Use a locally available Go 1.27-or-newer toolchain that meets the +consumer minimum, with the same selected toolchain for maintainer tooling and +checks. Do not pin the consumer minimum to its incidental patch release. +Keep the existing ReleaseKit selection and publication workflow unless a +concrete build incompatibility requires attention; ConfigKit's upstream tool +dependency alone is not a reason to migrate PromptKit's release machinery. + +Rename actual source-root `configkit:` controls to `config:`; leave nested +application data and `configkit:"secret"` tags alone. Replace removed import +`optional` fields with `required` values. Use `required: true` where a maintained +example or fixture needs a file to exist; do not set a global required-import +default. A test of missing optional imports must keep that intended behavior. + +Keep `SourceVersionModeIfPresent`. The existing `VersionRule` checks exact text +`2` rather than `1`; upstream parsing permits string `"2"` or strict decimal +integer `2` and rejects unsupported types. Headerless documents remain valid. +Source-local headers, collection `release_version`, and ConfigKit software +versions are separate concepts. A standalone prompt item's root `version` is +only a source header; there is no remaining prompt-version label. + +### Typed Resources, Paths, And Identity + +Use slices of resource structs for root and collection `Backends`, `Profiles`, +and `Prompts`, with `ID string` bound as `yaml:"id"` on each internal record. +Keep `Collections` as `map[string]collectionConfig`. Preserve the other field +types and allowed domain values except for removal of the prompt label. +ConfigKit consumes `extends`; internal resource structs need no parallel +inheritance field or relationship interpreter. + +Register these six destination rules on the one loader definition: + +| Destination | Registration | Identity | +| --- | --- | --- | +| Root `backends`, `profiles`, `prompts` | One `SequenceIdentityAt(configkit.Keys(kind), "id")` per kind | Direct `id` | +| `collections//backends`, `profiles`, `prompts` | One `SequenceIdentityMatching` per kind using literal `collections`, `SequenceAnyMappingKey()`, and literal kind | Direct `id` | + +Use `configkit.SequenceSelector` with `SequenceLiteralKey` segments for each +dynamic selector. A literal `"*"` namespace is not the wildcard selector. +Register once without discovering source documents or enumerating namespaces. +Missing destinations need no artificial empty value or declaration. + +Separate three things throughout the adapter: + +- effective path: resource-list base plus `.Index(i)`, then the actual field; +- local identity: `record.ID`, validated with existing exact local-ID rules; +- runtime identity: existing namespace qualification of that local ID. + +Use the index path for presence, normalization/default records, validation, +origins, and sensitivity. Use the full identity for execution-owned maps. +Mutate slice elements in place during resolution; avoid accidentally normalizing +only a range-variable copy. Preserve the retained ConfigKit tree as lists. +Build indexes in bounded passes over final records rather than repeatedly +searching lists by ID during execution. Keep existing inventory sorting; this +is not a promise that every operation is linear or that list order drives runs. + +ConfigKit owns duplicate-identity checks, composition, final registered-identity +checks, and sibling inheritance. PromptKit owns accepted shapes, string-ID +syntax, domain settings, final references, and prompt materialization. Do not +prevalidate sources or re-resolve history. Non-string/null/missing IDs fail +through the existing typed/schema/domain boundary as appropriate; there is no +filename fallback, trimming, or new namespace constraint. + +### Layering And Resource Context + +Within one strict tier, duplicate IDs fail. Across tiers, registered sequences +default to upsert, replacing a matching record in full. Explicit append/replace +remain upstream operations; an empty append/upsert adds nothing, while explicit +replacement with `[]` clears the list. Do not recreate the old fieldwise merge +between same-ID records. Mapping overlay within inherited records is still +ConfigKit behavior, and backend-to-profile setting completion stays PromptKit +behavior; neither is removed by whole-record upsert. + +All three resource kinds can use `extends: {id: parent}` within the same list. +Parents are ordinary validated resources, children retain their own identities, +and only surviving records supply parents. Self-extension cannot recover a +displaced lower-tier record. Keep partial profiles valid until request +completion; do not introduce abstract records or prompt-specific inheritance +restrictions. + +Resolve each effective `content_file` through its final index-based field origin +and contributing `SourceContext`, including inherited fields and moved/replaced +records. Keep the existing construction-wide lazy metadata snapshot, synchronous +content capture, handle closure, and captured runtime lookups. Origins are +resource-resolution information from the handoff, not a source-history audit. + +### Public Builders And Removed Labels + +The final builder signatures are: + +```go +func ProfileSource(label string, profiles []ProfileConfig) configkit.Source +func BackendSource(label string, backends []BackendConfig) configkit.Source +``` + +Add `ID string` to both public config structs. Preserve existing optional field +types, including `ProfileConfig.Extends *string`; when non-nil, encode it as +`extends: {id: *config.Extends}` rather than a scalar reference. Omission remains +omission. Both builders emit explicit-ID record lists in supplied order, retain +duplicates for ConfigKit to reject on loading, preserve existing ownership of +provider maps/diagnostic values, and do not independently validate definitions. +No map overload, new backend inheritance convenience, or public prompt builder +is required. Backend/prompt inheritance is available through configuration. + +Remove prompt-version fields, parameters, copying, formatting, and JSON +`prompt_version` members throughout domain, application, and facade values. +Keep `PromptIdentity` as an ID-only struct and retain the existing listing return +type rather than redesigning it as a string slice. Preserve prompt hashes as +opaque equality values; removing a hashed field can change them. Keep collection +release labels, ConfigKit version evidence, session IDs, and unrelated version +identifiers. No replacement label or consumer compatibility alias is needed. + +## Stage 1: Adopt The Module, Toolchain, And Renamed APIs + +Scope: `go.mod`, `go.sum`, imports, and the existing ConfigKit adapter/facade. + +1. Select Go 1.27 or newer locally, set the consumer minimum to 1.27.0, and + replace the old ConfigKit requirement with the new module at v1.0.0. Prepare + dependency sums through ordinary Go tooling. Do not commit workspace files or + filesystem replacements. +2. Update imports in production, tests, and examples. Migrate `Definition.Secret` + to `Definition.Sensitive`, `Resolution.InputInfo` to `Resolution.EntryInfo`, + and resolution recording calls to `RecordNormalization`/`RecordDerivedDefault` + as used. Recorded mutations must still perform their assignments; recording + methods do not assign values. Typed `Secret` references remain unchanged. +3. Audit public inspection wrappers and their tests against the upstream release + note's complete rename table: version evidence, empty import selections, + fallback destination flags, import defaults, layer names, and history-limit + diagnostics. Change symbols/expectations actually used here, not unrelated + identifiers by global text substitution. +4. Update the ConfigKit attribution entry to the selected commit above, the new + source repository, and its verified COPYRIGHT/LICENSE notices. Review resolved + module changes, including any additional tooling dependency, proportionately. + +Validation: check the module diff and imports; attempt focused adapter builds +when source controls permit. Record any toolchain/dependency-access failure +accurately. Do not use local substitution as the delivered dependency state. + +## Stage 2: Migrate Source Controls And Import Expectations + +Scope: actual configuration controls in fixtures, programmatic sources, and +maintained example assets; application resource shape can still be transitional. + +1. Rename source-root controls to `config` in main documents, imported files, + collection entries, test strings, and programmatic maps. Inspect context for + each change rather than replacing every occurrence of `configkit`. +2. Convert removed `optional` fields and make intended required imports explicit. + Preserve tests whose purpose is optional selection. Keep directory patterns, + recursion, destinations, import opt-in, and filesystem roots as selected by + the caller; do not invent glob `**` semantics or directory discovery rules. +3. Update source-evidence assertions for ConfigKit v1 names and `main` layer + spelling. Test meaningful source attribution rather than preserving historical + source order, complete rendering, or incidental history-event counts. + +Validation: use the existing source-helper/import tests when runnable; otherwise +record remaining resource-shape dependencies. Leave source headers for Stage 3. + +## Stage 3: Introduce Identified Record Shapes And Header Version 2 + +Scope: schema types and loader definition in `internal/configuration/load.go`. + +1. Convert the six root/collection resource fields to slices and add record IDs. + Remove `promptConfig.Version`; retain document `Version` and collection + `ReleaseVersion`. Do not decode both mapping and list formats. +2. Add all six identity registrations exactly as described above. Advance the + optional checker to exact specification version 2 without changing its mode. +3. Adapt `resourceSet`/`resourceSets` to expose slices and their existing base + paths. Preserve root and arbitrary collection traversal without pre-scanning + inputs. Keep namespace syntax validation at the effective configuration. +4. Update one small adapter fixture to the final shape to exercise registered + root and dynamic destinations; do not migrate the entire suite in this stage. + +Validation: inspect the registration selectors and schema; when runnable, load +one headerless root list and one version-2 collection. Resolution/validation +callers are completed in the following stages. + +## Stage 4: Preserve Field Presence And Resolution At List Paths + +Scope: backend/profile field capture, normalization, and defaulting in +`internal/configuration/load.go` and their focused tests. + +1. Iterate records by index, retaining the local ID for full-ID state-map keys. + Replace resource `.Key(id)` paths with `.Index(i)` for effective fields. +2. Adapt `captureFields` and related helpers to query `EntryInfo` before defaults + and normalization. Preserve absent, null, explicit zero/false/empty, inherited, + and backend-completed settings using the current semantics. +3. Adapt `resolveBackends` and `resolveProfiles` to update the actual slice + elements and record precise field mutations. Keep existing endpoint, + credential-name, diagnostic-setting, and queue-capacity rules. +4. Convert the existing focused default/presence fixtures. Update a same-ID + layered fixture to whole-record upsert rather than adding a hidden merge to + keep its previous expectation. + +Validation: owning tests demonstrate explicit zeros/nulls, backend completion, +and recorded normalization at the correct list entries. No new readiness rule. + +## Stage 5: Validate Final Records And Build Execution Indexes + +Scope: `validateEffective`, `indexedBackends`, `indexedProfiles`, and +`internal/configuration/targets.go`. + +1. Validate local IDs and settings at final index-based paths. Build the set of + full backend IDs from final records for ordinary profile-reference checks. + Keep namespace/local-ID syntax, model strings, and deferred prompt/default + readiness semantics unchanged. +2. Build backend/profile indexes using each record's ID and namespace. Update + capacity-policy and execution-target assembly to use those indexes and the + Stage 4 presence state. Do not inspect history or add a second ConfigKit load. +3. Keep final inventories sorted and collection membership independent of list + position. Do not conflate local IDs in separate namespaces or resource kinds. +4. Convert target-focused fixtures and retain runtime override, provider-map, + credential omission, concurrency, and queue-policy behavior. + +Validation: target tests cover a root resource, namespaced resources sharing a +local ID, and partial-profile completion. Upstream duplicates must fail before +an execution map can silently overwrite a record. + +## Stage 6: Materialize Prompts From Effective List Entries + +Scope: prompt resolution/capture in `internal/configuration/prompts.go` and +prompt-input presence capture in `load.go`. + +1. Iterate final prompt records using their IDs for runtime keys and their list + indexes for metadata paths, message paths, and validation errors. Remove the + raw prompt-label parameter from materialization; remaining internal label + plumbing is removed in Stage 9. +2. Adapt input-description/content-type presence capture and prompt defaulting + to the new paths. Continue compiling captured message/session templates and + validating effective output contracts only. +3. Resolve file-backed fields from their contributing origin and SourceContext + after imports, inherited prompt definitions, upsert, and index movement. + Share the existing lazy metadata snapshot across all resources, and preserve + content-handle closure and post-construction capture. +4. Convert/extend the existing native and in-memory filesystem tests with + inherited prompt content and a replaced record from another directory. Use + distinctive synthetic file contents to prove which source contributed it. + +Validation: owning prompt tests prove correct content and input metadata after +inheritance/replacement, including file edits not changing a constructed engine. +Do not normalize a whole list solely to update a field and lose its origins. + +## Stage 7: Preserve Inspection And Sensitive-Value Handling + +Scope: `internal/configuration/inspection.go`, configuration inspection/diff +facade tests, and path-specific metadata expectations. + +1. Adapt provider-extra sensitivity matching for root and collection resource + list indexes, retaining the existing sensitive key policy and nested values. + Use ConfigKit v1's `Sensitive` hook and schema tags where already applicable. +2. Convert inspection queries and fixtures from resource-key paths to concrete + index paths. Retained effective output stays in list shape; runtime IDs are + not synthetic inspection mapping keys. +3. Preserve redaction in effective output, explanations, failure diagnostics, + metadata, and diffs through existing owning coverage. Include a replaced or + inherited sensitive record at a different index where it adds protection. +4. Retain the existing thin ConfigKit wrappers. Do not add inspection methods + merely because upstream v1 offers them, or invoke inspection during a run. + +Validation: converted inspection/diff tests find the expected values/origins and +do not disclose synthetic credentials. Relax only assertions tied to deliberate +upstream history/diagnostic changes, not meaningful redaction expectations. + +## Stage 8: Convert Public Source Builders To Explicit-ID Slices + +Scope: `profiles.go`, `backends.go`, source-builder GoDoc, and owning construction +tests. Other callers are migrated in later stages. + +1. Implement the exact public signatures and fields in Delivery Decisions. + Emit slice records with explicit `id`; preserve caller order and duplicates. +2. Encode non-nil profile `Extends` as an identity mapping. Preserve omitted + options, explicit false/zero values, provider-map copying, and diagnostic + configuration ownership. Leave value validation to loading. +3. Convert owning builder tests to slices. Check ordered output and that duplicate + records reach loading and are rejected rather than silently deduplicated. + Retain a public profile-variant test through real ConfigKit inheritance. + +Validation: the public construction/source-builder tests demonstrate the new +input shape and ownership. Do not add map compatibility or builder-only ID rules. + +## Stage 9: Remove Internal Prompt-Version Propagation + +Scope: domain values, prompt requirement snapshots, hashes, use cases, and +observation recording; facade cleanup follows in Stage 10. + +1. Remove prompt `Version`/`PromptVersion` from domain definitions, identities, + prepared/run/inspection/requirement/smoke values and internal snapshot types. + Remove corresponding parameters, assignments, and label-only clone helpers. + Preserve helpers still needed for collection labels or other optional values. +2. Update prompt hashing, render/requirement snapshots, runner preparation, + prepared-execution cloning, profile-independent inspection, smoke selection, + and observation recording to use prompt identity without a label. +3. Remove internal tests exclusively about absent/empty/inherited prompt labels. + Keep their independent snapshot-ownership and hash/metadata protections by + exercising retained fields, not by deleting the wider regression coverage. + +Validation: focused domain/use-case tests when runnable and symbol searches for +remaining label plumbing. Do not promise old hash values or remove source-version +checks, collection release labels, or session metadata. + +## Stage 10: Remove Public Prompt Labels And Serialized Fields + +Scope: `types.go`, `listing.go`, `requirements.go`, `observations.go`, +`smoke_diagnostics.go`, `convert.go`, formatting, and owning JSON tests. + +1. Remove public prompt-version fields and their conversions, including + `PromptIdentity.Version`; preserve the ID-only struct and listing method shape. +2. Remove `prompt_version` JSON fields from prepared/results, observation, and + diagnostic values wherever present. Update redacted formatting and exact + GoDoc to avoid referring to removed metadata. +3. Adapt existing JSON contract tests to verify the field is absent from the + affected representative public values. Retain the existing unrelated + serialization, ownership, and sensitive-data checks. + +Validation: compile the facade when remaining fixtures permit and run JSON +contract tests. Search production code for stale prompt labels, separating +unrelated version fields from the removed feature. + +## Stage 11: Verify Identified Composition And Inheritance + +Scope: `internal/configuration/load_test.go`, `targets_test.go`, and focused +configuration fixtures not yet converted. + +1. Convert remaining loader fixtures to explicit-ID lists and identity-reference + `extends`. Keep malformed-shape cases malformed for their intended reason. +2. Cover all six identity registrations without duplicating the generic upstream + matrix: root kinds plus dynamic collection kinds, duplicate strict peers, + arbitrary namespaces including a literal `*` or numeric-looking namespace, + and equal local IDs in different kinds/namespaces. +3. Through the real PromptKit loader definition, test final registered-identity + enforcement using a package-local test seam for supported application + resolution if needed. Reuse/extract the loader definition rather than writing + a parallel test-only registration list or adding a public resolver API. +4. Cover surviving parent/child inheritance for profiles, backends, and prompts; + child identity; missing/cyclic/self parents via upstream error propagation; + valid ordinary parents; and partial profiles completed by requests. +5. Cover whole-record layered upsert, explicit append/replace, empty upsert versus + clearing replacement, and replaced lower-tier invalid domain values not being + separately validated. Preserve failure on upstream syntax/structural errors. + +Validation: real-loader tests assert effective behavior and structured diagnostic +identity/paths as appropriate, not complete upstream error wording or ordering. + +## Stage 12: Complete Header, Origin, And Adapter Fixture Coverage + +Scope: remaining `internal/configuration` prompt, inspection, listing, and +source-context tests and `internal/engine` configuration fixtures. + +1. Finish fixture conversion without recreating label-specific tests. Preserve + local import roots, explicit-null cases, input metadata, static syntax, + snapshot ownership, and sorted inventory behavior. +2. Cover headers `2` and `"2"`, headerless entry/fragments/items, rejected + declared version 1 and malformed declared types, and rejection of the old + resource mapping shape. Do not require every document to declare a header. +3. Keep nested application `config` data distinct from source controls. Use the + existing schema's allowed/rejected shapes; do not create a new application + field just to demonstrate upstream control extraction. +4. Close any missing source-origin or sensitive-path cases identified in + Stages 6–7. Reuse those owning tests instead of repeating their matrix here. + +Validation: run the configuration and internal-engine packages together when +they compile. Correct production defects before adjusting meaningful assertions. + +## Stage 13: Migrate Public Configuration, Inventory, And Scope Tests + +Scope: root construction, sources, inspection/diff, inheritance, profile +inspection, listing, and namespace contract tests. + +1. Convert YAML, programmatic mappings, and builder callers to final lists and + explicit IDs. Remove prompt labels without changing the purpose of each test. +2. Change same-ID customization fixtures deliberately: use distinct inherited + variants for field customization, or retain same-ID records when whole-record + replacement is the behavior under test. Do not silently change replacement + into inheritance in tests intended to protect precedence. +3. Preserve full-ID listings/filtering, global namespace/collection inventories, + metadata-only collections, independent namespaces, shared scoped-engine + ownership, and unchanged exact stored references. +4. Confirm the public facade accepts new-module ConfigKit inputs and exposes + new-module inspection values; old-path type aliases/adapters are not needed. + +Validation: run the affected external-package contract tests using real ConfigKit +composition and offline sources. Do not add index/list-position guarantees. + +## Stage 14: Migrate Internal Execution And Rendering Fixtures + +Scope: remaining `internal/usecase`, `internal/prompt`, `internal/domain`, and +internal observation fixtures affected by resource lists or removed labels. + +1. Convert source-backed fixtures and builder callers. Remove direct internal + struct labels and assertions only about the removed metadata; retain prompt + ID, body/output, session, usage, and substantive observation assertions. +2. Reuse current runner, requirements, prepared-execution, and smoke-selection + tests to confirm captured full identities remain their selection input. + Keep tests using direct execution-owned values independent of YAML where + they already protect that separate boundary. +3. Preserve renderer behavior, structural repairs, transient retries, + cancellation, and resource snapshots through their existing owning tests. + Do not redesign those mechanisms or introduce runner-time list searches. + +Validation: run the affected internal packages with final values and synthetic +sources. Resolve remaining label-related compilation errors in these packages. + +## Stage 15: Migrate Public Preparation And Execution Contracts + +Scope: root ordinary/prepared execution, concrete-request validation, +requirements, and capacity contract fixtures. + +1. Convert remaining YAML, programmatic definitions, and builder callers for + Run, Prepare, PrepareExecution/RunPrepared, ValidateRequest, and + InspectRequirements. Retain their established substantive outcomes. +2. Keep runtime overrides, artifact/schema ownership, appended messages, + cancellation, prepared-handle isolation, and shared capacity coverage at the + boundaries that already own it. Update frozen-rendering/source fixtures + without reintroducing prompt-label metadata. +3. Distinguish intentional whole-record replacement from inherited variants in + request-level fixture layering; do not weaken test expectations to accommodate + a broken adapter or add new upstream-availability requirements. + +Validation: run the focused root preparation/execution/requirements tests using +existing injected clients or controlled HTTP transports, with no live provider. + +## Stage 16: Migrate Public Diagnostics And Observation Contracts + +Scope: root smoke diagnostic, observation, prepared-observation, and adapter +boundary fixtures not completed by Stage 10's serialization changes. + +1. Convert diagnostic backend/profile/prompt sources and observation fixtures to + the final shape. Keep exact configured references, selection precedence, + tri-state findings, timing/usage, partial cancellation, and disclosure checks. +2. Preserve observation event order and metadata that remain contractual while + removing only the prompt label. Reuse existing retry/repair and injected-client + evidence tests rather than repeating their transport matrices. +3. Confirm scoped smoke diagnostics and ordinary runs resolve from the same + captured indexes and retain their existing client/capacity ownership. + +Validation: run these public contract tests offline; diagnostic operations in +tests use controlled transports, not actual backend endpoints or API keys. + +## Stage 17: Update Maintained Examples And Benchmarks + +Scope: the three `examples/go-library` workflows, their assets, and configuration- +dependent benchmarks and shared test helpers still using the old representation. + +1. Convert preparation collections/fragments, run prompt assets, and observation + prompt assets to identified lists. Include the item-import workflow using + `placement: sequence-item` and a headerless resource file under an explicit + collection input. Keep synthetic IDs/models and source-relative content. +2. Update Go builder callers to ordered explicit-ID slices and imports to the + new module. Keep the examples' distinct purposes and expected execution + outcomes; only update `scripts/check-examples.py` if an intentionally changed + output shape requires it. +3. Migrate benchmark fixture generators and remaining common test helpers. + Preserve the construction-wide origin-metadata optimization and the existing + benchmark's usefulness; do not add allocation/time pass thresholds or a new + benchmarking release gate. + +Validation: run all three examples through the semantic checker once runnable. +Use a short focused construction benchmark if needed to investigate a suspected +repeated-scan regression, not to claim unmeasured performance improvements. + +## Stage 18: Document Formats And Internal Handoff + +Scope: `docs/formats.md`, `docs/internal/sources.md`, and other current internal +documents whose descriptions changed. + +1. Document specification 2, optional per-source headers, collection mappings + containing identified resource lists, exact ID rules, and preserved provider + model strings. Remove prompt-label fields; retain collection release labels. +2. Describe sibling identity inheritance across the three kinds, ordinary parent + validation, partial profiles, and same-ID whole-record replacement. Link to + ConfigKit v1 for generic import/control/collection semantics rather than + copying its full reference or imposing additional authoring restrictions. +3. Explain final index-based presence/resource-context interpretation, captured + runtime indexes, sensitivity, and operator-only inspection. Update current + upstream references and obsolete mapping examples without rewriting accepted + ADR decision content or historical release notes. + +Validation: compare every current format example with the actual implemented +schema and owning tests. Exact Go declarations remain the API contract owner. + +## Stage 19: Document One Coherent Consumer Migration + +Scope: `docs/consumers/configuration-migration.md`, the Go consumer guide, README, +remaining exported GoDoc, and toolchain/release preparation guidance. + +1. Add the v0.16-era mapping-to-list upgrade to the migration guide while retaining + useful older identity/deployment guidance. Show explicit IDs, sibling identity + references, same-ID whole-record replacement, and source-builder map-to-slice + conversion with a distinct variant where customization is intended. +2. Explain the new import path and incompatible Go type identities, Go 1.27.0 + minimum, actual root controls, optional imports/`required: true`, header 2, + removed prompt labels/JSON fields, changed inspection paths, and opaque hash + changes. Include the standalone-item header-versus-former-label distinction. +3. Update the current consumer/README examples and links to maintained artifacts. + Align toolchain/build guidance with the new minimum and the existing selected- + toolchain release procedure; do not introduce a separate release-tool upgrade, + CI wait, consumer publication check, or new platform support promise. +4. Identify this as one breaking pre-v1 minor migration. Actual version selection, + release-note creation, tagging, and publication remain normal separately + authorized release preparation. Do not make Scriptorium publication a sprint + gate or modify Scriptorium in this task. + +Validation: render/read affected GoDoc; check local document links and snippets +against implemented APIs. Keep current documentation free of obsolete contracts; +old syntax may remain explicitly labeled in migration explanations and history. + +## Stage 20: Verify The Integrated Sprint And Record Completion + +Scope: acceptance review and residual corrections, not another feature stage. + +1. Trace every target section of the feature roadmap to implementation and + proportionate existing tests: new dependency/types, source controls/header, + all six identity rules, builder order/duplicates, inheritance/upsert, effective + field paths, file origins, sensitivity, removed labels, and preserved runtime + operations. Close actual gaps at their owning boundary. +2. Search current production code, tests, examples, module metadata, and current + docs for stale old-path imports, genuine old controls, prompt labels, keyed + resource fixtures, and version-1 headers. Classify intended migration examples, + historical release notes, unchanged tags, and unrelated version fields rather + than demanding zero textual matches. +3. With the selected Go toolchain and prepared dependencies, run: + + ```sh + GOTOOLCHAIN=local GOWORK=off go test -race ./... + GOTOOLCHAIN=local GOWORK=off go vet ./... + GOTOOLCHAIN=local GOWORK=off python3 scripts/check-examples.py + git diff --check + ``` + + Format changed Go files and validate affected local Markdown links. Review + the final module graph/sums and absence of committed workspace/local + replacements. These are sprint checks, not an extra publication command or + new permanent release gates. Reuse successful checks for unchanged content. +4. Verify the only intended API breaks are those selected by the roadmap and + upstream type migration. In particular, do not add ID normalization, required + headers/imports, profile readiness, abstract parents, source auditing, or + execution-order semantics. Review final status/diff for unrelated material. +5. Record completion and validation in this plan and mark the feature roadmap + complete. Commit the final nonempty unit; leave retirement and publication to + normal release preparation. Report remaining failures honestly if the full + target has not been reached. + +Validation: the acceptance trace, integrated checks above, and reviewed final +diff establish sprint completion; intermediate checks alone do not. + +## Open Questions + +None required to begin the sprint. The accepted roadmap settles module identity, +resource representation, layering/inheritance, source-builder inputs, header +policy, removed labels, and the coordinated breaking upgrade. Implementation +details above serve those decisions without adding consumer guarantees.