diff --git a/docs/roadmap/module-releases.md b/docs/roadmap/module-releases.md index 13eb41c..136e998 100644 --- a/docs/roadmap/module-releases.md +++ b/docs/roadmap/module-releases.md @@ -1,6 +1,7 @@ # Roadmap: release individual Go modules -Status: planned feature; scope decisions resolved. +Status: planned feature; scope and ownership decisions resolved. The declaration +source for standalone builds remains an [open decision](#open-decisions). ## Purpose @@ -81,18 +82,23 @@ and complete tag are available throughout candidate handling and public evidence **Work:** Add an optional repository-relative module selection to the public request and profile, with root defaults. Resolve it against the captured -repository and committed module declaration once at the operation entry point. +repository and source appropriate to the operation once at the operation entry +point. Check, publication, and delivery use committed module declarations. +Standalone-build declaration sourcing follows the open decision below. Pass the resolved identity through the operation's validation, publication, build, and delivery collaborators. Standalone operations use the same resolution logic. Derive tags using Go's standard module conventions, including -major-version directories: a `/v2` module stored -at `integrations/ckconfig/v2` uses `integrations/ckconfig/v2.0.0` for `v2.0.0`. +major-version directories: a `/v2` module stored at `integrations/ckconfig/v2` +uses `integrations/ckconfig/v2.0.0` for `v2.0.0`. The same module stored at `integrations/ckconfig` uses that complete tag too. Support both physical layouts and distinguish the module directory from its tag prefix. Carry the resolved identity through facade conversions, internal requests, callbacks, results, and CLI diagnostics. Keep semantic-version validation separate from full-tag handling. Exact field names belong in API design. +Keep shared identity resolution separate from each operation's prerequisites. +Populate resolved identity in public evidence as resolution succeeds, including +when a later step fails. ### 2. Apply one validation scope @@ -104,12 +110,13 @@ file-size checks, Markdown, and product-check context all correspond to the selected module and its relevant release materials. **Work:** Give the existing shared validation path both repository context and -module scope. Run Go commands in the module directory with the existing offline -and workspace-disabled environment. Select committed file inputs once under the -agreed boundary convention and apply that selection to each content check. -Retain repository access for resolving Markdown destinations and existing -committed-file references. A link to another module may be checked for existence -or its target heading without scanning that module's unrelated documents. +module scope. Run Go commands in the module directory with the existing +offline and workspace-disabled environment. Select committed file inputs once +under the agreed boundary convention and apply that selection to each content +check. Build one ordered input set and retain the full repository lookup +separately for resolving Markdown destinations and existing committed-file +references. A link to another module may be checked for existence or its +target heading without scanning that module's unrelated documents. Update module-distribution inspection to examine the selected release's inputs. For example, an unrelated sibling's filesystem replacement should not fail the @@ -145,13 +152,15 @@ ReleaseKit's supported operations. prebuilt-asset delivery all operate on the selected module. Hosted pages use its complete tag and module-local note; binaries report its semantic version. -**Work:** Extend build and delivery requests and profile mapping with the shared -module identity. Resolve main packages and module-owned build paths from the -module directory. Prepare build dependencies there, and preserve existing offline -artifact compilation and version smoke checks. Carry module identity through -build results and receipts so prebuilt delivery verifies the selected module, -version, tag where applicable, candidate commit, settings, and artifact hashes. -Keep ordinary local builds usable without requiring a published tag. +**Work:** Extend build and delivery requests and profile mapping with the +shared module identity. Resolve main packages and module-owned build paths +from the module directory. Prepare build dependencies there, and preserve +existing offline artifact compilation and version smoke checks. Reuse +operation-local Go settings between validation and subsequent builds when +their environment inputs match. Carry module identity through build results +and receipts so prebuilt delivery verifies the selected module, version, tag +where applicable, candidate commit, settings, and artifact hashes. Keep +ordinary local builds usable without requiring a published tag. Use the full tag for tagged-checkout verification, Gitea release lookup and creation, and source links. Use the semantic version for binary version injection @@ -162,6 +171,10 @@ same commit. A page-only profile continues to require no application binary. Use the new module-bound receipt format for prebuilt delivery. Consumers regenerate receipts through the updated build operation as part of the clean cutover described below. +Normalize build settings once for build execution, receipt binding, and +comparison. Receipt loading owns structure and identity validation; delivery +owns the local content-verification pass before hosted requests. Build-time +hashing records produced bytes independently. ### 5. Support module-aware CI delivery @@ -181,6 +194,11 @@ verified tagged checkout. Resolve the physical module directory and profile before tool bootstrap, and keep the selection consistent with the derived tag. Verify the event commit before resolving that mapping and use the tagged source's selected module files on retries. +Use the same small consumer selection declaration for the launcher and CI. +Bootstrap selects the module and profile; ReleaseKit verifies their consistency +with the derived identity. Reuse the verified checkout after tool bootstrap +with fresh read-only source checks. Standalone `ci-deliver` owns preparation +when it is needed. For ordinary root tags, use the root profile and module bootstrap defaults. Consumers using that pattern supply no module/profile mapping declaration. Preserve temporary bootstrap metadata and existing credential handling. Cover @@ -216,27 +234,33 @@ the behavior of root modules with nested modules. **Target:** Representative public API and CLI workflows establish that the selected module is validated and only its intended tag is published. -**Work:** Extend existing behavioral tests using local repositories and remotes. -Cover root defaults; nested-module failure while the root suite passes; equal -versions across modules; major versions with and without physical major-version -directories; full-tag reuse; and failed or unknown publication with the correct -recovery identity. Exercise optional -checks with violations inside and outside the selected scope, parent selection -excluding independent nested modules, and cross-module Markdown references. -Cover omitted, replacement, and empty shared-file lists; optional default files; +**Work:** Extend existing behavioral tests using local repositories and +remotes. Cover root defaults; nested-module failure while the root suite +passes; equal versions across modules; major versions with and without +physical major-version directories; full-tag reuse; and failed or unknown +publication with the correct recovery identity. Exercise optional checks with +violations inside and outside the selected scope, parent selection excluding +independent nested modules, and cross-module Markdown references. Cover +omitted, replacement, and empty shared-file lists; optional default files; missing explicit files; committed-tree lookup; duplicate inputs; and explicit files in another module. Verify selection errors when optional file checks are -disabled, and that shared-file selection preserves enabled checks and Go scope. -Verify that repository guards still observe changes outside the selected module -and that module selection does not repeat the standard suite. Reuse existing -failure tests where they already protect unchanged behavior. Add representative -nested-module build/version-injection, new-format receipt ownership and cutover, -Gitea page/asset, and CI tag/profile/tool-selection coverage. Use local HTTP servers for delivery and -isolated synthetic module proxies for bootstrap tests. Verify that retries use -the original module selection and full tag after the default branch changes. -Verify a representative simple root-module API call, profile, launcher, and CI -workflow using the new interface's defaults. Confirm that routine use adds no -required configuration fields, mapping declarations, or consumer decisions. +disabled, and that shared-file selection preserves enabled checks and Go +scope. Verify that repository guards still observe changes outside the +selected module and that module selection does not repeat the standard suite. +Reuse existing failure tests where they already protect unchanged behavior. +Add representative nested-module build/version-injection, new-format receipt +ownership and cutover, Gitea page/asset, and CI tag/profile/tool-selection +coverage. Use local HTTP servers for delivery and isolated synthetic module +proxies for bootstrap tests. Verify that retries use the original module +selection and full tag after the default branch changes. Verify a +representative simple root-module API call, profile, launcher, and CI workflow +using the new interface's defaults. Confirm that routine use adds no required +configuration fields, mapping declarations, or consumer decisions. Give +identity derivation, scope selection, and path conversion focused tests at +their owners. Use representative assembled workflows and reuse existing +failure coverage where the underlying behavior remains shared. Verify +preserved empty lists, contextual findings for equal blobs at different paths, +failure identity, and artifact-verification ownership. Update GoDoc, CLI/configuration references, check/publication/build/delivery guides, adoption examples, CI templates, and recovery guidance together. Supply migration @@ -262,6 +286,81 @@ Subsystems consume the resolved module and tag. Repository-state, tagged-source, and artifact verification continue against that identity through their existing guards. +### Operation prerequisites and identity + +Shared resolution supplies module and tag identity to each operation. +Candidate checking and publication retain clean source on the primary branch, +committed release notes, and their existing unused-tag checks. Delivery +retains clean tagged-source verification and supports historical releases and +detached checkouts. Ordinary builds retain their support for modified source +and operate independently of release-note and publication prerequisites. + +Composite operations pass resolved identity to their internal collaborators. +Standalone operations use the same resolver at entry. Declaration sourcing for +ordinary builds is the open decision at the end of this document. + +### One validation input set and full repository lookup + +Construct file inputs when enabled checks or explicit shared-file validation +need them. Compute module boundaries and the ordered, deduplicated input set +once using committed metadata. File checks consume that set. Keep the full +repository lookup available for targeted reads and reference resolution, with scoped reader +ownership and cancellation preserved. + +Deduplicate inputs by path. Reuse parsed results by blob identity while retaining +each source path's findings and relative destinations. This preserves the +existing selective caches and avoids retaining all inspected raw content. + +### Version and tag boundaries + +Keep semantic version and complete tag distinct in internal requests and evidence. +Version injection, artifact filenames, smoke checks, and note titles use the +semantic version. Git publication, recovery, and hosted release identity use +the complete tag. URL construction belongs to each protocol owner, which encodes +the literal tag for its route. Verify slash-containing tags in API and source +links. + +### Failure evidence + +Populate available module, version, tag, and commit evidence as resolution +progresses. Later failures retain that evidence alongside the operation's +existing phase, endpoint, tag-object, and outcome fields as available. Shared +facade conversions preserve these fields and the underlying error causes. + +### Go environment ownership + +Lazily discover effective Go settings for the selected module and reuse them +within the operation's validation and build phases when environment inputs are +unchanged. Ownership and reuse are operation-local. Dependency preparation keeps +its separate network-capable environment. Page-only delivery retains its path +without Go-tool discovery or application dependency preparation. + +### Build settings, receipts, and asset verification + +Normalize build settings once and reuse that representation for execution, +receipt binding, and comparisons. The new receipt format binds module identity +alongside existing source and artifact evidence. Loading validates structure, +identity, and file declarations. Delivery owns the content-verification pass +before hosted requests, for both API and CLI callers. + +Build-time hashing records the produced bytes; delivery-time verification +establishes that the selected files still match them. Candidate and managed +delivery output stays outside the whole repository. Ordinary output paths use +the selected module's path base. + +### CI bootstrap and checkout ownership + +For module-mapped workflows, use one small committed consumer selection +declaration shared by the launcher and CI. Bootstrap verifies the triggering +tag and commit, selects the physical module and profile, and builds the tool +from that module's configuration. ReleaseKit verifies selection against the +derived identity. + +The workflow prepares the checkout before tool bootstrap. Subsequent delivery +reuses that checkout with fresh read-only source checks. Standalone CI delivery +performs preparation when needed. Share verification behavior across these +entry paths, keeping root defaults and tagged-source selection on retries. + ### Simple single-module experience Ordinary root-module consumers use the new interface's defaults: omitted module @@ -306,7 +405,8 @@ and Go tests, vet, and package compilation retain the selected module's scope. In Go, a nil slice selects the defaults; a non-nil empty slice selects none. In JSON, omission or `null` selects the defaults; `[]` selects none. Preserve -this distinction through profile mapping and facade conversions. Exact field +this distinction through profile mapping and facade conversions, including +slice copying and profile serialization. Resolve the defaults once. Exact field names belong in API design. Paths are repository-relative literal file paths. This initial selection @@ -328,6 +428,10 @@ module-owned validation and build paths, including file-size exclusions, and configured product-command execution at the selected module. Keep diagnostic file paths repository-relative and expose both directories to product commands. Markdown destinations remain relative to their source documents. +Normalize selections and resolve path bases at a shared boundary. Translate +file selections and exclusions to canonical repository-relative paths before +checks consume them. Use module-based filesystem paths for execution and output, +and retain repository-relative diagnostic paths through conversions. Root profiles use the repository-root module by default. Nested-module launchers use the provided repository context for shared scripts. These conventions keep @@ -355,3 +459,31 @@ outside the implementation scope. Migration means guidance supplied in the next release's documentation. That guidance explains the required consumer changes and the root-module validation scope change; implementation completion covers the new interface directly. + + +## Open Decisions + +### Declaration source for standalone builds + +Candidate checks, publication, and tagged delivery resolve identity from +committed source. Ordinary builds currently permit modified source, including +module-file edits. Select how their identity resolver reads the module +declaration. + +**Recommendation:** Read the selected module's working-tree `go.mod` for +standalone builds. Keep candidate and delivery operations tied to committed +declarations. This makes a local build's identity correspond to the files Go +actually compiles and supports development of a changed module path or a new +module directory before commit. The resolver's source is selected by the +operation, with shared derivation logic and existing source-verification +observations. Delivery continues to require a build verified against its +committed tagged source. + +**Viable alternative:** Resolve standalone-build identity from the committed +`go.mod`, while allowing ordinary source-file edits during compilation. This +provides uniform committed identity across operations and simplifies declaration +access. It supports builds of modified code when the module declaration is +unchanged. Its cost is that module-path changes and newly created module +directories need a commit before identity can reflect them, and local identity +can differ from the declaration used by Go. Document that limitation explicitly +if this alternative is selected.