Retire completed roadmaps and retain pending adoption work
This commit is contained in:
@@ -1,656 +0,0 @@
|
||||
# ReleaseKit v0.2.0 implementation plan
|
||||
|
||||
Status: Complete. Stages 1–15 are implemented and locally verified.
|
||||
|
||||
This plan replaces the completed foundation sequence. It implements the target
|
||||
state in [v0.2.0.md](v0.2.0.md), using the shared design in [model.md](model.md),
|
||||
[ADR 0003](../adr/0003-declarative-validation.md), and
|
||||
[ADR 0004](../adr/0004-module-selected-tooling.md). A Luna coding agent should
|
||||
execute one numbered stage per prompt, in order.
|
||||
|
||||
## Current baseline and completion scope
|
||||
|
||||
At baseline commit `3974a46`, the foundation and all six
|
||||
[remediation findings](remediation.md) were complete. `Check` and `Publish`
|
||||
shared candidate-request conversion and validation.
|
||||
`internal/validation` runs the default offline suite and owns diagnostics and
|
||||
candidate-tree access. Committed-file readers are offline; destination resolution
|
||||
handles symlinks, parent traversal, cancellation, and absolute in-checkout paths.
|
||||
The root error types and CLI presentation preserve findings and cause context.
|
||||
`buildinfo` retains its independent runtime dependency graph.
|
||||
|
||||
The stages in this plan complete the remaining v0.2.0 validation selections,
|
||||
module-selected CI bootstrap, and Audita migration. Audita's migration is
|
||||
recorded in commit `17421bc`. The final local audit covers the full Go suite,
|
||||
compiled API/dependency boundaries, maintained examples, documentation, and
|
||||
dependency notices. Architecture review, hosted deployment, release tagging,
|
||||
and decisions about further testing follow this implementation.
|
||||
|
||||
| Release-roadmap item | Implementation stages |
|
||||
| --- | --- |
|
||||
| 1. Shared validation API/profile model | 1–3, 5–11, 15 |
|
||||
| 2. Module-selected CI tool and Audita migration | 12–14 |
|
||||
| 3. One suite with race selection | 1 |
|
||||
| 4. Separate full vet | 2 |
|
||||
| 5. Package compilation | 3 |
|
||||
| 6. Expected publication endpoint | 4 |
|
||||
| 7. Go formatting | 5 |
|
||||
| 8. Markdown links and optional boundary | 9–11 |
|
||||
| 9. Independent distribution rules | 6–7 |
|
||||
| 10. Individual file size | 8 |
|
||||
|
||||
## Instructions for every stage
|
||||
|
||||
- Start with [development.md](../development.md) and applicable policies. Locate
|
||||
current symbols with the codebase graph and inspect the worktree. The named
|
||||
paths below describe the current baseline.
|
||||
- Introduce each public and profile setting with its working capability, as
|
||||
agreed. Update its GoDoc, configuration reference, consumer guidance, and
|
||||
relevant CLI/internal documentation in that same stage.
|
||||
- Use ordinary internal structs/functions and explicit facade conversions.
|
||||
Keep product assertions in `AdditionalChecks` and profile `checks`.
|
||||
- Select tests for the stage's actual risks under the
|
||||
[testing policy](../policy/testing.md). Use local Git repositories, Go
|
||||
packages, controlled command doubles, and HTTP fixtures. Default tests remain
|
||||
offline and independent of real credentials or sibling checkouts.
|
||||
- Verification lists describe required evidence, including existing tests.
|
||||
Give each behavior a test owner: parser/checker tests cover syntax and rules;
|
||||
candidate-tree and Git tests cover file access and resolution; conversion
|
||||
tests cover each API/profile selection; shared orchestration tests cover
|
||||
ordering, failure stopping, cancellation, and callback execution. Use
|
||||
representative integration cases to verify these boundaries work together.
|
||||
Add coverage where the change introduces a risk or leaves an evidence gap.
|
||||
- Prepare newly selected development dependencies before offline validation.
|
||||
Apply the [OSS policy](../policy/oss.md) when adding dependencies or adapting
|
||||
third-party material, including any required attribution and license texts.
|
||||
- Verify the focused outcome, stage its relevant changes, review the diff, and
|
||||
create a nonempty commit with a short plain English message. Preserve unrelated
|
||||
work, report the stage's outcome and verification, and stop until the next
|
||||
stage is requested. These stages require local work and automated checks;
|
||||
consumer changes in Stage 14 are committed in that repository.
|
||||
|
||||
## Design carried through the stages
|
||||
|
||||
### Public and profile declarations
|
||||
|
||||
The completed specification is facade-owned:
|
||||
|
||||
```go
|
||||
type ValidationSpec struct {
|
||||
Go GoValidationSpec
|
||||
GoFormat bool
|
||||
Markdown *MarkdownValidationSpec
|
||||
ModuleDistribution ModuleDistributionValidationSpec
|
||||
FileSize *FileSizeValidationSpec
|
||||
}
|
||||
|
||||
type GoValidationSpec struct {
|
||||
Race bool
|
||||
FullVet bool
|
||||
CompileTargets []Target
|
||||
}
|
||||
|
||||
type MarkdownValidationSpec struct {
|
||||
EnforceCheckoutBoundary bool
|
||||
}
|
||||
|
||||
type ModuleDistributionValidationSpec struct {
|
||||
WorkspaceFiles bool
|
||||
LocalReplacements bool
|
||||
}
|
||||
|
||||
type FileSizeValidationSpec struct {
|
||||
LimitBytes *int64
|
||||
Exclusions []string
|
||||
}
|
||||
```
|
||||
|
||||
Add `Validation ValidationSpec` and `ExpectedPushURL string` to `ReleaseRequest`.
|
||||
`Target` is the existing root-facade operating-system/architecture pair. Each
|
||||
stage adds only the fields it makes operational. The CLI owns corresponding
|
||||
JSON structs and converts them in `cmd/releasekit`; internal production packages
|
||||
use their own contracts.
|
||||
|
||||
| Go selection | Profile selection | Omitted/zero behavior |
|
||||
| --- | --- | --- |
|
||||
| `Go.Race` | `validation.go.race` | Ordinary native test suite |
|
||||
| `Go.FullVet` | `validation.go.full_vet` | Existing test-time vet |
|
||||
| `Go.CompileTargets` | `validation.go.compile_targets` | No package-compilation pass |
|
||||
| `GoFormat` | `validation.go_format` | No formatting check |
|
||||
| `Markdown` | `validation.markdown` | Nil/omitted/null disables the check; `{}` enables it |
|
||||
| `Markdown.EnforceCheckoutBoundary` | `validation.markdown.enforce_checkout_boundary` | Outside-checkout links reported as out of scope |
|
||||
| `ModuleDistribution.WorkspaceFiles` | `validation.module_distribution.workspace_files` | Rule disabled |
|
||||
| `ModuleDistribution.LocalReplacements` | `validation.module_distribution.local_replacements` | Rule disabled |
|
||||
| `FileSize` | `validation.file_size` | Nil/omitted/null disables the check; `{}` enables it |
|
||||
| `FileSize.LimitBytes` | `validation.file_size.limit_bytes` | Nil/omitted/null selects 1,000,000 bytes when enabled |
|
||||
| `FileSize.Exclusions` | `validation.file_size.exclusions` | No exclusions |
|
||||
| `ExpectedPushURL` | `expected_push_url` | Empty/omitted disables the publication expectation |
|
||||
|
||||
Profile compilation targets use `GOOS/GOARCH` strings. Require a complete pair
|
||||
because a partial target would otherwise silently select different compilation.
|
||||
Use the existing Go target/environment mechanisms; let the selected Go toolchain
|
||||
report unsupported targets. An artifact naming constraint does not determine
|
||||
package-compilation compatibility.
|
||||
|
||||
Byte limits are integer counts; zero is an explicit zero-byte limit, and negative
|
||||
counts are invalid. Exclusions are literal repository-relative file or directory
|
||||
paths; directory selections include committed descendants. Match path boundaries
|
||||
so excluding `assets` leaves `assets-other` selected. Ordinary relative path
|
||||
normalization is sufficient. An unmatched exclusion has no effect. Metacharacters
|
||||
remain literal Git path characters.
|
||||
|
||||
### Execution and ownership
|
||||
|
||||
The shared procedure is one native test suite, selected full vet, selected
|
||||
package-compilation targets, and selected file checks, followed by product
|
||||
checks and existing artifact builds/rechecks. File-check ordering is an internal
|
||||
procedure: formatting, workspace files, local replacements, file size, then
|
||||
Markdown. Stop after a failed check. A checker may return multiple findings;
|
||||
this plan does not require collecting failures from every selected check.
|
||||
|
||||
Resolve the Go environment once per validation operation and reuse it. Native
|
||||
race/vet work preserves the existing effective cgo/C-tool configuration. Static
|
||||
package compilation uses `CGO_ENABLED=0`. The existing offline module/toolchain
|
||||
controls remain owned by `internal/gotool`.
|
||||
|
||||
Pass settings through the root `candidateRequest`, `internal/candidate.Request`,
|
||||
`internal/publish.Request`, and `validation.Request`. Both operations and their
|
||||
CLI forms use the same decisions. Keep expected URL comparison in publication
|
||||
preflight. Existing capture/rechecks, endpoint guards, recovery, publication
|
||||
completion, and delivery outcomes retain their meaning.
|
||||
|
||||
Reuse the existing internal failures and facade conversion. Add stable identities
|
||||
`go-vet`, `package-compile`, `go-format`, `workspace-files`, `local-replacements`,
|
||||
`file-size`, and `markdown-links` as implemented. Supply paths, locations,
|
||||
targets, directives, and measurements as applicable. Preserve causes and
|
||||
cancellation through `errors.Is`/`errors.As`. CLI failures use existing exit
|
||||
classifications and complete contextual presentation.
|
||||
|
||||
File checks share one candidate inventory per validation operation and load blobs
|
||||
as needed. Inventory includes tracked vendor files and nested modules. Regular
|
||||
source blobs feed formatting and Markdown parsing. Workspace-file detection
|
||||
includes named symlink blobs; module parsing follows committed symlinks to
|
||||
candidate-contained regular declarations. Unavailable selected input produces
|
||||
an inspection error. File size measures regular and symlink blobs. Gitlinks have
|
||||
no parent-tree blob size, and their contents remain outside the inspected tree.
|
||||
|
||||
### Dependencies and Markdown convention
|
||||
|
||||
Use standard `go/format` for Go formatting. Its convention follows the Go
|
||||
standard library used to build ReleaseKit. Use `golang.org/x/mod/modfile` at
|
||||
`golang.org/x/mod v0.40.0` for complete module-declaration parsing. Use
|
||||
`github.com/yuin/goldmark/v2 v2.1.6` internally for Markdown AST parsing and source
|
||||
positions. Both selected module manifests support the existing Go 1.25 baseline;
|
||||
implementation should record their exact source revisions and notices under the
|
||||
OSS policy. References: [modfile](https://pkg.go.dev/golang.org/x/mod/modfile)
|
||||
and [Goldmark](https://github.com/yuin/goldmark/tree/v2.1.6).
|
||||
|
||||
PromptKit's current script supplies the starting heading/link examples. Preserve
|
||||
its basic anchor transformation: lowercase heading text, retain Unicode letters
|
||||
and numbers, underscore, hyphen, and spaces, then replace spaces with hyphens.
|
||||
Use visible heading text from the Markdown AST, including inline code text and
|
||||
excluding HTML tags/formatting delimiters. Support ATX and Setext headings. For
|
||||
repeated headings, append increasing numeric suffixes starting at `-1`, selecting
|
||||
an unused identifier when a generated suffix collides with another heading.
|
||||
Document these refinements to the starting script's behavior.
|
||||
|
||||
Recognize inline links, images, and full/collapsed/shortcut reference links through
|
||||
the parser. Code blocks and inline code supply examples rather than link nodes.
|
||||
Raw HTML destinations remain outside this Markdown-link capability. Undefined
|
||||
references rendered as ordinary text by the parser are not a new Markdown lint
|
||||
rule. Decode Markdown escapes/entities through the parser and percent escapes
|
||||
once when resolving URI path/fragment components. Compare decoded fragments in
|
||||
lowercase to preserve PromptKit's starting convention. Ignore URI query
|
||||
components for file existence. Empty paths target the source document; an empty
|
||||
fragment selects its top. Schemed and protocol-relative URIs receive no availability
|
||||
request. Fragment checking applies to regular Markdown destinations; other
|
||||
existing files/directories receive existence checking.
|
||||
|
||||
Use committed destination resolution and cached parsed documents/anchors.
|
||||
Missing destinations, unresolved cycles, and missing supported anchors fail the
|
||||
selected Markdown check. Actual outside-checkout destinations are reported as
|
||||
out of scope by default and fail with boundary enforcement. Submodule-content
|
||||
observations remain reported as out of scope under either setting: the boundary
|
||||
option concerns checkout escape and does not establish a submodule prohibition.
|
||||
Write nonfailure observations to the supplied output writer; a nil writer
|
||||
selects ordinary quiet library use. Diagnostics identify the source use site,
|
||||
location, and destination. Document source columns as one-based byte columns.
|
||||
|
||||
### CI tool bootstrap
|
||||
|
||||
Build using temporary copies of the released application's `go.mod` and `go.sum`,
|
||||
with Go's alternate `-modfile` and normal module preparation in those copies.
|
||||
Confirm that ReleaseKit is already selected before building its command. This
|
||||
preserves the application's version declaration and require/replace semantics
|
||||
while allowing missing tool-only indirect requirements/checksums to be prepared
|
||||
without dirtying immutable tagged source. It supports consumers whose application
|
||||
imports only lightweight `buildinfo`. Stages 12–14 implement this agreed approach.
|
||||
|
||||
## Stage 1: Introduce the specification with race selection
|
||||
|
||||
**Completion:** Complete. `ReleaseRequest.Validation.Go.Race` and profile
|
||||
`validation.go.race` select `-race` for the single native Go suite. Both
|
||||
candidate operations share the selection, and race failures retain the `go-test`
|
||||
identity without falling back to an ordinary suite.
|
||||
|
||||
**Outcome:** The first public/profile selection changes the one existing suite.
|
||||
|
||||
1. Add `ReleaseRequest.Validation`, `ValidationSpec.Go`, and
|
||||
`GoValidationSpec.Race`, plus equivalent CLI-owned JSON settings. Add explicit
|
||||
conversions through both candidate and publication request paths.
|
||||
2. Build the base invocation in `internal/validation`: preserve
|
||||
`go test -mod=readonly -count=1 ./...`, adding `-race` when selected. Reuse
|
||||
the native Go environment and report tool/prerequisite failures as `go-test`.
|
||||
3. Preserve additional-check and build ordering. Update exact API/profile
|
||||
references and add a minimal consumer example for the selection.
|
||||
|
||||
**Verification:** Default and selected invocations, exactly one suite, API/profile
|
||||
selection equivalence, both operations, unavailable race prerequisites with no
|
||||
silent fallback, preserved causes/cancellation, and failure before product
|
||||
checks/builds/tag creation. Use a small real race-enabled fixture on supported
|
||||
hosts and a controlled Go command for portable prerequisite-failure coverage.
|
||||
|
||||
## Stage 2: Coordinate a separate full vet pass
|
||||
|
||||
**Completion:** Complete. `ReleaseRequest.Validation.Go.FullVet` and profile
|
||||
`validation.go.full_vet` disable test-time vet for the one native test suite and
|
||||
run native `go vet -mod=readonly ./...` afterward. Vet failures retain the
|
||||
`go-vet` identity, and the selection is shared by the API and profile paths.
|
||||
|
||||
**Outcome:** Full vet replaces test-time vet overlap through one declaration.
|
||||
|
||||
1. Add `Go.FullVet` and `validation.go.full_vet` through the same conversion path.
|
||||
2. When enabled, add `-vet=off` to the one test invocation and run native
|
||||
`go vet -mod=readonly ./...` afterward using the same tool/environment.
|
||||
3. Attribute vet failures to `go-vet` and update canonical usage guidance.
|
||||
|
||||
**Verification:** Ordinary, race-only, vet-only, and combined selections; one
|
||||
suite; vet after successful tests; suppression of test-time vet only when
|
||||
selected; failure/cancellation stopping; default behavior and API/profile parity.
|
||||
Protect the selected command relationship without freezing incidental flag order.
|
||||
|
||||
## Stage 3: Compile packages for selected targets
|
||||
|
||||
**Completion:** Complete. `Go.CompileTargets` and profile
|
||||
`validation.go.compile_targets` select static package compilation after tests
|
||||
and vet. Failures use `package-compile` and include the selected target;
|
||||
artifact building remains separate.
|
||||
|
||||
**Outcome:** Source compatibility checks work independently of artifacts.
|
||||
|
||||
1. Add `Go.CompileTargets` and string-array profile targets. Convert to internal
|
||||
Go targets and validate complete pairs consistently for API and profile use.
|
||||
2. After test/vet, run `go build -mod=readonly -o <os.DevNull> ./...` in static
|
||||
mode for each selected target. The Go build null-output mode suppresses
|
||||
executable output, including a module with a single main package.
|
||||
3. Report failures as `package-compile`, including the selected target. Keep
|
||||
output names, linker version injection, smoke tests, receipts, and manifests
|
||||
in artifact building. Document compilation versus target execution.
|
||||
|
||||
**Verification:** Linux amd64/arm64, a supported additional Go pair, source-only
|
||||
library, single-main and multiple-main modules (including repeated executable
|
||||
basenames), target failure, unchanged candidate files, `CGO_ENABLED=0`, preserved
|
||||
ordering, and page-only delivery with compilation selected but no build targets.
|
||||
Reuse the existing Go environment tests for controls already protected there.
|
||||
|
||||
## Stage 4: Compare the optional expected push URL
|
||||
|
||||
**Completion:** Complete. `ReleaseRequest.ExpectedPushURL` and profile
|
||||
`expected_push_url` require an exact match with Git's resolved effective push
|
||||
URL before validation. Mismatches return `ErrUnexpectedPushURL` with expected
|
||||
and resolved values; `Check` ignores the publication-only expectation.
|
||||
|
||||
**Outcome:** Publication rejects a different effective destination before validation.
|
||||
|
||||
1. Add `ExpectedPushURL` and `expected_push_url`, with an empty value selecting
|
||||
existing behavior. Carry it only into the publication request.
|
||||
2. Immediately after resolving/capturing `endpoint.PushURL`, compare exact strings.
|
||||
Report expected and resolved values through a publication preflight error.
|
||||
Add `ErrUnexpectedPushURL` as a public sentinel using the existing shared-error
|
||||
ownership pattern so callers can use `errors.Is`.
|
||||
3. Keep later endpoint rechecks and reconciliation intact. Update GoDoc,
|
||||
publication guidance, and the profile reference.
|
||||
|
||||
**Verification:** Omitted/matching/mismatching values, Git `insteadOf` resolution,
|
||||
separate fetch/push URLs, exact spelling differences, mismatch before Go/callbacks
|
||||
or tag creation, and a local-only `Check` that ignores the publication expectation.
|
||||
Existing endpoint-change and uncertain-push tests keep their ownership.
|
||||
|
||||
## Stage 5: Check committed Go formatting
|
||||
|
||||
**Completion:** Complete. `ValidationSpec.GoFormat` and profile
|
||||
`validation.go_format` run `go/format` on regular Go blobs from the captured
|
||||
commit. Findings identify unformatted paths; parser and inspection failures
|
||||
retain their causes, and the check leaves repository contents unchanged.
|
||||
|
||||
**Outcome:** A declaration replaces tracked-file formatting loops.
|
||||
|
||||
1. Add `GoFormat` and `validation.go_format` with working executor integration.
|
||||
2. Load the shared captured inventory and apply `format.Source` to regular `.go`
|
||||
blobs. Compare original and formatted bytes, preserving repository contents.
|
||||
3. Return `go-format` findings for affected paths and preserve parser/inspection
|
||||
causes. Update usage and formatting-convention documentation.
|
||||
|
||||
**Verification:** Formatted and unformatted files, parse errors, vendor/nested
|
||||
source, unusual filenames, committed versus worktree bytes, disabled/default
|
||||
behavior, API/profile parity, and failure before later product/build work.
|
||||
|
||||
## Stage 6: Select committed workspace-file inspection
|
||||
|
||||
**Completion:** Complete. `Validation.ModuleDistribution.WorkspaceFiles` and
|
||||
`validation.module_distribution.workspace_files` report committed blob entries
|
||||
named `go.work` or `go.work.sum`, including nested paths and symlinks. The rule
|
||||
inspects the captured candidate independently of `GOWORK` and leaves the Go
|
||||
workspace environment and vendor behavior unchanged.
|
||||
|
||||
**Outcome:** One distribution rule works independently of the Go environment.
|
||||
|
||||
1. Add `ModuleDistributionValidationSpec.WorkspaceFiles` and the matching JSON
|
||||
group/field. The remaining rule is added in Stage 7.
|
||||
2. Inspect committed blob entries named `go.work` or `go.work.sum`, including
|
||||
nested and symlink entries. Report paths using `workspace-files`.
|
||||
3. Keep testing's existing workspace setting and consumer vendor choices in their
|
||||
current owners. Document the distinction between environment and distribution.
|
||||
|
||||
**Verification:** Either workspace filename, nested paths, symlink names,
|
||||
committed files with `GOWORK=off`, uncommitted files excluded from inspection,
|
||||
selection disabled, and shared API/profile execution. Use meaningful rule cases
|
||||
rather than retesting Git enumeration mechanics.
|
||||
|
||||
## Stage 7: Select filesystem replacement inspection
|
||||
|
||||
**Completion:** Complete. `Validation.ModuleDistribution.LocalReplacements` and
|
||||
`validation.module_distribution.local_replacements` parse committed `go.mod`
|
||||
declarations, including nested/vendor files and committed symlink declarations.
|
||||
Filesystem replacements report their declaration path, line, directive, and
|
||||
target as `local-replacements`; versioned replacements are permitted. Parse and
|
||||
inspection failures retain their causes, and this rule is independent of both
|
||||
workspace-file selection and `GOWORK`.
|
||||
|
||||
**Outcome:** The second distribution rule parses actual module declarations.
|
||||
|
||||
1. Add `ModuleDistribution.LocalReplacements` and the equivalent profile field.
|
||||
Prepare `golang.org/x/mod v0.40.0`, module sums, and required OSS notices.
|
||||
2. Parse committed `go.mod` files with `modfile.Parse`, including nested/vendor
|
||||
declarations. Resolve symlink declarations within the candidate; report an
|
||||
inspection error when their selected contents cannot be obtained locally.
|
||||
3. Identify filesystem replacements by the parsed replacement's absent version;
|
||||
permit versioned replacements. Report path, directive/source location, and
|
||||
target through `local-replacements`, preserving parse/inspection causes.
|
||||
4. Document independent distribution selections and their inspection scope.
|
||||
|
||||
**Verification:** Single and block directives, comments, quoted paths, relative
|
||||
and absolute filesystem targets, versioned replacements, nested declarations,
|
||||
valid/broken symlinks, parse failure, and all independent boolean combinations.
|
||||
The rule applies to candidate contents even when testing disables workspace use.
|
||||
|
||||
## Stage 8: Inspect individual committed file sizes
|
||||
|
||||
**Completion:** Complete. `Validation.FileSize` and `validation.file_size` enable
|
||||
a per-blob decimal-byte limit with a 1,000,000-byte default, strict greater-than
|
||||
comparison, and literal repository-relative file/directory exclusions. The check
|
||||
uses captured blob sizes, counts symlink link text, omits gitlinks, and reports
|
||||
one oversized file with its measurement. Nil disables the check, and historical
|
||||
or aggregate repository size is outside its scope.
|
||||
|
||||
**Outcome:** Optional limits and intentional path exceptions are operational.
|
||||
|
||||
1. Add `FileSizeValidationSpec`, `ValidationSpec.FileSize`, and matching JSON
|
||||
fields according to the declaration table. Validate nonnegative byte limits.
|
||||
2. Use shared blob sizes for regular files and symlink link-text blobs. Apply
|
||||
literal file/directory exclusions. On an oversized blob, return `file-size`
|
||||
with its path and existing `FileSizeMeasurement` fields; reporting one offending
|
||||
file per failure fits the current diagnostic model.
|
||||
3. Document decimal bytes, strict greater-than comparison, exclusions, and
|
||||
current-candidate scope. Preserve default disabled behavior.
|
||||
|
||||
**Verification:** Below/at/above limits, the exact 1,000,000-byte enabled default,
|
||||
zero/custom/negative limits, nil versus empty objects, directory/path boundaries,
|
||||
literal metacharacters, unmatched exclusions, small binaries, symlink sizes, and
|
||||
omitted submodule sizes. Historical and aggregate size do not become release gates.
|
||||
|
||||
## Stage 9: Implement internal Markdown parsing and anchors
|
||||
|
||||
**Completion:** Complete. Goldmark now records parsed links, images, reference
|
||||
uses, use-site locations, and collision-free heading anchors behind an internal
|
||||
per-candidate document cache. Its behavior remains unselected until the later
|
||||
validation-integration stage.
|
||||
|
||||
**Outcome:** A parser with source positions and documented anchor semantics is ready.
|
||||
|
||||
1. Add `github.com/yuin/goldmark/v2 v2.1.6`, prepared dependencies, and applicable
|
||||
OSS notices. Keep parser types inside internal implementation.
|
||||
2. Parse links/images, reference uses, headings, and source positions into small
|
||||
internal records. Derive visible heading text and apply the convention above.
|
||||
3. Cache parsed records/anchors per candidate document. Keep this stage internal;
|
||||
Stage 11 adds the public selection once complete checking works.
|
||||
4. Compare fixtures with PromptKit's starting examples. Record intended refinements
|
||||
in the roadmap until the public behavior lands, avoiding a second regex parser.
|
||||
|
||||
**Parser refinements:** PromptKit's starting script scans inline links, images,
|
||||
and ATX headings with regular expressions. The Goldmark parser also records
|
||||
resolved full, collapsed, and shortcut reference uses at each source use site.
|
||||
Heading anchors use decoded visible AST text, include inline code,
|
||||
exclude raw HTML tags, and support Setext headings. Parser-recognized CommonMark
|
||||
autolinks are recorded alongside inline and reference links. Repeated-heading
|
||||
suffixes skip identifiers already used by another heading.
|
||||
|
||||
**Verification:** Inline/reference forms and images, escaped/parenthesized
|
||||
and angle-bracket destinations, optional titles, code fences/inline code,
|
||||
Unicode/entity headings, ATX/Setext headings, repeated headings and suffix
|
||||
collisions, and source use-site locations including repeated reference uses.
|
||||
Undefined references and HTML prose remain governed by parser interpretation.
|
||||
|
||||
## Stage 10: Implement internal destination and fragment checking
|
||||
|
||||
**Completion:** Complete. The internal checker resolves committed destinations,
|
||||
checks supported fragments, preserves inspection errors, and reports distinct
|
||||
outside-checkout and submodule observations. Stage 11 exposes this checker
|
||||
through public and profile selections and the shared executor.
|
||||
|
||||
**Outcome:** Committed Markdown navigation is checked with boundary observations.
|
||||
|
||||
1. Resolve parsed local URI components through `CandidateTree.ResolveDestination`.
|
||||
Apply escaping/query/fragment rules above and use actual resolved identities
|
||||
for target-document anchor lookup.
|
||||
2. Check committed existence and supported heading fragments, recording source
|
||||
path/location/target. Produce `markdown-links` failures and distinct nonfailure
|
||||
observations for outside-checkout and submodule contents.
|
||||
3. Implement optional checkout-boundary enforcement internally. Preserve the
|
||||
distinction between external URIs, checkout escapes, and uninspected submodules.
|
||||
4. Reuse remediated symlink/cancellation/local-object behavior. Keep parsing,
|
||||
resolution, and rule evaluation in ordinary internal functions.
|
||||
|
||||
**Resolution refinement:** URI query components do not participate in path
|
||||
checking. Compare fragments after one percent-decoding pass and lowercase them
|
||||
to preserve PromptKit's starting anchor matching.
|
||||
|
||||
**Verification:** Valid/missing files and anchors, same-document/empty fragments,
|
||||
percent-escaped paths and fragments, query strings, directories and non-Markdown
|
||||
files, outside links with both settings, and submodule observations. Check how
|
||||
resolver results and inspection errors become Markdown findings, preserving
|
||||
causes and cancellation. Use representative committed-tree integration cases
|
||||
and verify unchanged candidate/worktree bytes. Existing candidate-tree and Git
|
||||
tests own detailed absolute-path, symlink-parent, cycle, neighboring-file,
|
||||
missing-object, and traversal-cancellation cases.
|
||||
|
||||
## Stage 11: Expose Markdown selection and complete validation integration
|
||||
|
||||
**Completion:** Complete. `ValidationSpec.Markdown` and
|
||||
`validation.markdown` select the shared committed-link checker through both
|
||||
public operations and CLI profile commands. Omitted/null settings disable the
|
||||
check; an empty object enables it, and the boundary option maps explicitly.
|
||||
Warnings use the shared output writer, while Markdown failures stop product
|
||||
checks and builds. GoDoc, profile, consumer, CLI, and internal documentation
|
||||
now describe the operational behavior.
|
||||
|
||||
**Outcome:** All agreed validation selections work through both public operations.
|
||||
|
||||
1. Add `MarkdownValidationSpec`, `ValidationSpec.Markdown`, and their JSON fields.
|
||||
Enable on a non-nil group/empty object and map the boundary boolean explicitly.
|
||||
2. Wire the checker and nonfailure observations into the shared executor/output
|
||||
writer. Reuse existing facade/CLI diagnostic formatting and exit classification.
|
||||
3. Document the newly operational Markdown selection in its canonical owners.
|
||||
Review earlier stages' GoDoc, configuration, check/publish guides, CLI reference,
|
||||
internal inventory, and examples for consistency across combined selections.
|
||||
4. Use self-contained fixtures representing Audita defaults/artifacts, ConfigKit's
|
||||
race/vet/compilation, and PromptKit's shared settings plus example assertions.
|
||||
Document how consumers remove duplicate generic commands when adopting settings.
|
||||
|
||||
**Verification:** Equivalent Go/profile declarations, nil/empty/null Markdown
|
||||
settings, warnings with successful results, boundary failures before product/build
|
||||
work, all-zero compatibility, representative combined selections, one suite and
|
||||
one additional-check callback. Run the compiled API/dependency check, including
|
||||
`buildinfo`'s standard-library/runtime-only dependency boundary.
|
||||
|
||||
## Stage 12: Build the CI tool from verified released module configuration
|
||||
|
||||
**Completion:** Complete. The maintained tag workflow verifies and checks out
|
||||
the event tag before reading module files, then confirms the ReleaseKit module
|
||||
selection and builds its CLI with temporary alternate module metadata outside
|
||||
the source tree. The delivery command retains the event arguments and exit
|
||||
status, and the cleanup trap removes its module copies and executable.
|
||||
|
||||
**Outcome:** The standard template has one tool-version declaration.
|
||||
|
||||
1. Revise `examples/woodpecker/tag-delivery.yml` into a compact bootstrap/delivery
|
||||
step. Use available Git to validate/fetch the explicit event tag, compare its
|
||||
peeled commit to the full provider object ID using existing case-insensitive
|
||||
object-ID semantics, check out that commit detached, and confirm HEAD and
|
||||
the existing clean tagged-source requirement. This ensures module files
|
||||
actually belong to the verified release before selecting the tool.
|
||||
Do this before reading/resolving the application module or executing Go.
|
||||
2. Apply the agreed CI tool bootstrap approach: create a disposable directory
|
||||
outside the source checkout, copy its `go.mod` and existing `go.sum`, and use
|
||||
an alternate `-modfile` for tool resolution/build.
|
||||
Run from the verified source with `GOWORK=off` and `GOTOOLCHAIN=local`.
|
||||
3. Confirm the ReleaseKit module is already selected by that module configuration
|
||||
using `go list -m`; then build its `cmd/releasekit` package without an `@version`
|
||||
suffix. Allow ordinary network-capable module preparation in the temporary
|
||||
metadata copies (`-mod=mod`). Respect selected require/replace relationships.
|
||||
4. Invoke the resulting native executable's existing `ci-deliver` with the event
|
||||
repository, commit, and tag. Keep delivery credentials in the existing delivery
|
||||
step and use an exit cleanup trap for temporary metadata and executable files.
|
||||
5. Remove the independent `RELEASEKIT_VERSION` workflow setting. Preserve current
|
||||
Go-image customization, destination/profile ownership, and delivery outcomes.
|
||||
Keep the bootstrap Git block small; the built tool retains its runtime guards.
|
||||
|
||||
**Verification:** Execute maintained template commands with a local tag/module
|
||||
fixture and instrument Go/transport operations. Prove wrong tag/commit stops
|
||||
before module resolution/build, a dirty module cannot select a different tool,
|
||||
the verified checkout selects the tool, module metadata and source remain
|
||||
unchanged, and the executable/temporary files are cleaned up. Tool metadata
|
||||
preparation is separate from offline candidate checks. Include a representative
|
||||
case that verifies invocation of the selected executable with the event arguments
|
||||
and propagation of its exit status. Existing delivery tests own hosted behavior.
|
||||
|
||||
## Stage 13: Verify upgrades, retries, and bootstrap variants
|
||||
|
||||
**Completion:** Complete. The tag workflow is exercised against a local module
|
||||
proxy with two tool versions, an older tagged configuration after the default
|
||||
branch upgrades, and a versioned replacement. Missing tool-only dependency
|
||||
checksums are prepared in temporary module metadata. The ReleaseKit source
|
||||
workflow verifies its tag before self-bootstrap and writes the executable
|
||||
outside the checkout. Delivery, configuration, and CLI guidance now distinguish
|
||||
tool bootstrap from application dependency preparation and describe
|
||||
immutable-source retries and installed-tool use.
|
||||
|
||||
**Outcome:** Tool selection follows the triggering release across supported uses.
|
||||
|
||||
1. Extend Stage 12's bootstrap fixtures with a local module proxy for two tool
|
||||
versions and tagged consumer module configurations. Execute the maintained
|
||||
workflow body against both.
|
||||
Keep live infrastructure outside the default test suite.
|
||||
2. Verify a retry of an older tag still selects that tag's module configuration
|
||||
when the default branch has upgraded. Include missing tool-only checksums and
|
||||
an existing versioned replacement to protect source-based resolution.
|
||||
3. Align `releasekit-source-delivery.yml` with source verification before self
|
||||
bootstrap and temporary output. Preserve self-bootstrap from `./cmd/releasekit`
|
||||
and separately installed-tool guidance using the existing command.
|
||||
4. Update delivery/configuration/CLI guidance and maintained templates together.
|
||||
Explain compatible Go environments, dependency preparation, immutable-source
|
||||
retries, and the distinct tool/app artifact preparation steps.
|
||||
|
||||
**Verification:** Two dependency versions, older-source retries, self bootstrap,
|
||||
and separately installed tool, using the shared bootstrap fixtures. Existing
|
||||
delivery and publication tests retain ownership of source-only pages, binary
|
||||
delivery, destination handling, and publication states. Add integration coverage
|
||||
for any new interaction introduced by bootstrap changes. An application without
|
||||
a declared ReleaseKit dependency uses the installed-tool integration.
|
||||
|
||||
## Stage 14: Migrate Audita's local CI integration
|
||||
|
||||
**Completion:** Complete. Audita commit `17421bc` makes both local and hosted
|
||||
bootstraps resolve ReleaseKit v0.1.0 from the consumer's module configuration.
|
||||
The existing Go image, `GITEA_RELEASE_TOKEN` secret, release profile, caller
|
||||
arguments, and native tool status are preserved. The local wrapper uses
|
||||
temporary alternate module metadata and cleans it up before executing the tool.
|
||||
Audita's runbook now describes the module-selected workflow.
|
||||
|
||||
**Verification:** Audita's `go test ./scripts -count=1`,
|
||||
`bash -n scripts/release.sh`, and real `bash scripts/release.sh version` passed;
|
||||
the wrapper reported `releasekit v0.1.0` and left source module files unchanged.
|
||||
ReleaseKit's `TestWoodpeckerTagDeliveryTemplate` and
|
||||
`TestWoodpeckerTagDeliveryUsesTaggedModuleVersion` passed with local Git and
|
||||
module-proxy fixtures. Both repositories passed their relevant diff checks.
|
||||
|
||||
**Outcome:** Audita's local wrapper and CI select the same module-declared tool.
|
||||
|
||||
1. Read `../audita` orientation/policies and inspect its worktree before editing.
|
||||
Adapt `.woodpecker/release.yml` to the maintained module-based template,
|
||||
preserving its Go image, Gitea secret name, and release profile.
|
||||
2. Retain its existing released ReleaseKit module selection for this migration;
|
||||
that version already supplies `ci-deliver`. Make any necessary adjustments to
|
||||
`scripts/release.sh` for the selected bootstrap metadata approach, preserving
|
||||
arguments and native executable exit behavior. Keep generated tool output
|
||||
outside the candidate source where needed.
|
||||
3. Verify the consumer's actual wrapper/workflow using local tagged fixtures and
|
||||
prepared module caches. Confirm matching tool selection, preserved arguments
|
||||
and exit status, and unchanged source files. Review the diff for preservation
|
||||
of the release profile and binary targets. Existing consumer and ReleaseKit
|
||||
tests retain ownership of source validation and hosted delivery behavior.
|
||||
4. Commit the focused migration in Audita with a plain English message. Record
|
||||
its commit and local verification in this plan's implementation status.
|
||||
|
||||
**Verification:** The actual adapted consumer declarations use one dependency
|
||||
version; local and CI bootstraps agree and retain existing caller arguments/status
|
||||
semantics. Keep integration fixtures self-contained in ReleaseKit's default suite.
|
||||
This migration uses an existing release and requires no intermediate publication
|
||||
or live Woodpecker/Gitea run to complete the stage.
|
||||
|
||||
## Stage 15: Audit the completed v0.2.0 implementation
|
||||
|
||||
**Completion:** Complete. All ten release-roadmap items map to implemented API,
|
||||
profile, execution, diagnostics, canonical documentation, and focused behavioral
|
||||
evidence. The audit confirms default zero-value behavior, independent
|
||||
module-distribution selections, one coordinated Go suite, source-only
|
||||
compilation/delivery, and expected-push preflight. Review found no unintended
|
||||
defaults, restrictions, or stronger guarantees. Audita's migration is recorded
|
||||
at `17421bc`.
|
||||
|
||||
**Verification:** `go test ./...` and `go run ./internal/apicheck` passed.
|
||||
Local Markdown destinations and fragments resolved across the documentation;
|
||||
dependency versions, source revisions, attribution entries, and license texts
|
||||
were checked. Maintained Woodpecker examples passed their offline fixtures.
|
||||
|
||||
**Outcome:** The entire scoped feature set is implemented and locally verified.
|
||||
|
||||
1. Match every row in the roadmap/stage table to implemented settings, execution,
|
||||
diagnostics, current documentation, and focused behavioral evidence. Verify
|
||||
all-zero compatibility, independent distribution choices, one coordinated Go
|
||||
suite, source-only compilation/delivery, and selected endpoint preflight.
|
||||
2. Review new code and tests for unintended defaults, restrictions, caps, or
|
||||
stronger guarantees. Preserve user choice and the existing facade boundaries.
|
||||
3. Run `go test ./...` and `go run ./internal/apicheck`. Add further integration
|
||||
coverage only for a concrete remaining risk. Check documentation links,
|
||||
fragments, whitespace, dependency notices, and maintained examples.
|
||||
4. Update statuses in this plan, the release roadmap, and the model roadmap to
|
||||
reflect actual completion, including the Audita migration evidence. Update
|
||||
canonical current-behavior owners as needed and remove stale prospective text.
|
||||
5. Commit the completed unit, report each stage's outcome and remaining work,
|
||||
and finish with a clean workspace while preserving any unrelated user changes.
|
||||
The subsequent architecture review and release/testing decisions follow here.
|
||||
|
||||
## Open Questions
|
||||
|
||||
None.
|
||||
Reference in New Issue
Block a user