Reconcile lifecycle documentation

This commit is contained in:
2026-08-10 23:18:29 +00:00
parent feba7b9d74
commit 801adb385d
9 changed files with 137 additions and 19 deletions

View File

@@ -279,6 +279,15 @@ For each `pipeline.scriptorium.artifacts.<name>`:
Narratio adds `session_id=narratio-session-<session_id>` to every Scriptorium request for sticky upstream LLM routing. If an artifact config sets `vars.session_id`, Narratio replaces that value before invoking Scriptorium. Use a different variable name if a prompt needs the raw Narratio session ID as content. Narratio adds `session_id=narratio-session-<session_id>` to every Scriptorium request for sticky upstream LLM routing. If an artifact config sets `vars.session_id`, Narratio replaces that value before invoking Scriptorium. Use a different variable name if a prompt needs the raw Narratio session ID as content.
Without `--artifacts`, analyze executes enabled configured artifacts. With an
explicit `--artifacts` list, the exact named configured artifacts are the
one-invocation execution set even if their `enabled` values are false; the list
does not automatically include dependencies. Named artifacts must therefore be
configured with valid executable fields, and their configured dependencies must
already be available to analyze. This override affects analyze planning only;
publish uses the list only to filter configured
`narratio.artifact.<name>` output rules.
For each artifact input `pipeline.scriptorium.artifacts.<name>.inputs.<input_name>`: For each artifact input `pipeline.scriptorium.artifacts.<name>.inputs.<input_name>`:
| Field | Type | Required | Rule | | Field | Type | Required | Rule |

View File

@@ -45,6 +45,15 @@ ID.
- `available`: local file exists and validates; - `available`: local file exists and validates;
- `provenance`: availability source. - `provenance`: availability source.
Configured definitions are always registered. Without an explicit selection,
the effective analyze set contains enabled definitions. With `--artifacts`, the
exact named configured definitions become the effective set for that invocation,
regardless of their `enabled` value; dependencies are not added implicitly.
Availability is separate from executability: a non-executable configured output
may be reused from a canonical non-empty file, while an executable definition
is generated by analyze. Extraction entries are registered from configuration
and become available only after compatible extraction evidence is hydrated.
Current provenance values: Current provenance values:
- `generated.current_analyze_run` - `generated.current_analyze_run`
@@ -81,6 +90,10 @@ Previous-session sources (`narratio.previous_session.artifact.*`):
- prefer manifest-backed previous-input paths; - prefer manifest-backed previous-input paths;
- fallback to existing previous-cache filesystem paths. - fallback to existing previous-cache filesystem paths.
Source absence is evaluated by the consuming artifact input. An optional input
is omitted from that invocation; a required input fails resolution. This is
separate from a stage's lifecycle outcome.
Validation by content type: Validation by content type:
- transcript JSON built-ins: JSON with top-level `segments` array; - transcript JSON built-ins: JSON with top-level `segments` array;

View File

@@ -8,13 +8,15 @@ Execute selected configured Scriptorium artifacts in dependency order and materi
- configured artifacts from `pipeline.scriptorium.artifacts` - configured artifacts from `pipeline.scriptorium.artifacts`
- optional selected artifact keys supplied through the stage environment - optional selected artifact keys supplied through the stage environment
- built-in/configured/previous-session source references in artifact inputs - built-in, configured, extraction, and previous-session source references in
artifact inputs
Supported source families: Supported source families:
- built-ins: `narratio.transcript.*`, `narratio.bounds.session` - built-ins: `narratio.transcript.*`, `narratio.bounds.session`
- prepared stable inputs: `narratio.input.players`, `narratio.input.party`, - prepared stable inputs: `narratio.input.players`, `narratio.input.party`,
`narratio.input.glossary` `narratio.input.glossary`
- configured artifacts: `narratio.artifact.<key>` - configured artifacts: `narratio.artifact.<key>`
- extraction lanes: `narratio.extraction.<key>`
- previous-session cache: `narratio.previous_session.artifact.<key>` - previous-session cache: `narratio.previous_session.artifact.<key>`
## Outputs ## Outputs
@@ -24,11 +26,22 @@ Supported source families:
## Key Behavior ## Key Behavior
- skips with metadata when Scriptorium config is missing or no executable artifacts remain. - when Scriptorium is absent or no configured artifact is executable, completes
- builds runtime artifact catalog (built-ins + configured artifacts). successfully with no outputs and records explanatory metadata. This is not an
explicit self-skip: both manifests record success, satisfy publish's
prerequisite, and an ordinary later run reuses the result until forced.
- builds a runtime artifact catalog containing built-ins, configured artifacts,
and configured extraction lanes. Extraction availability is hydrated only
from compatible successful extraction evidence.
- uses enabled configured artifacts by default. An explicit `--artifacts`
selection is a one-invocation override: it makes exactly the named configured
artifacts executable even when disabled, and does not automatically include
dependencies. A selected artifact's dependencies must instead already be
available to the catalog.
- marks non-executable configured artifacts as reusable when output files already exist. - marks non-executable configured artifacts as reusable when output files already exist.
- validates selected artifact dependency order (cycle-safe topo ordering). - validates selected artifact dependency order (cycle-safe topo ordering).
- resolves required/optional inputs per artifact source definition. - resolves required/optional inputs per artifact source definition.
- omits an unavailable optional input; an unavailable required input fails.
- resolves prepared stable input sources from `inputs/*.yml` materialized by `prepare`. - resolves prepared stable input sources from `inputs/*.yml` materialized by `prepare`.
- resolves previous-session sources from local `previous/` cache only. - resolves previous-session sources from local `previous/` cache only.
- runs optional render-debug, then artifact execution. - runs optional render-debug, then artifact execution.

View File

@@ -25,7 +25,10 @@ Exact remote placement and the operator workflow belong in
## Key Behavior ## Key Behavior
- stage can self-skip when publish disabled or run upload disabled. - when publishing or run upload is disabled, completes successfully with no
outputs and records explanatory metadata. This is not an explicit self-skip:
both manifests record success, and an ordinary later run reuses that result
until publish is forced.
- validates prerequisite stage success and object-store availability. - validates prerequisite stage success and object-store availability.
- derives a deterministic run-archive allowlist from the validated run - derives a deterministic run-archive allowlist from the validated run
`manifest.json`: declared run-local outputs, logs, generated configs, and the `manifest.json`: declared run-local outputs, logs, generated configs, and the

View File

@@ -20,7 +20,9 @@ Render Markdown transcript artifacts from normalized JSON transcripts via Seriat
- resolves inputs manifest-first, then canonical fallback. - resolves inputs manifest-first, then canonical fallback.
- writes run-local outputs first, then materializes canonical session outputs. - writes run-local outputs first, then materializes canonical session outputs.
- records input provenance, output paths, adapter metadata, logs, and generated config refs. - records input provenance, output paths, adapter metadata, logs, and generated config refs.
- skips with stage metadata when `pipeline.render.enabled=false`. - when `pipeline.render.enabled=false`, completes successfully with no outputs
and records explanatory metadata. This is not an explicit self-skip: both
manifests record success, and enabling render later requires a forced run.
## Failure Semantics ## Failure Semantics

View File

@@ -92,6 +92,14 @@ Execution rules:
repeated self-skip with the same reason and no outputs is stable and does not repeated self-skip with the same reason and no outputs is stable and does not
perpetually rerun downstream work. perpetually rerun downstream work.
An explicit self-skip is a durable `skipped` stage outcome that later runs
reconsider. It differs from successful no-output execution: disabled `render`
and `publish`, and absent or no-executable `analyze`, record `succeeded` with
metadata and no outputs. Ordinary later runs reuse those successful results;
force the affected stage after enabling or configuring it. Optional artifact
inputs are omitted only from the consuming artifact invocation and do not make
the stage self-skip.
Single-stage execution: Single-stage execution:
```bash ```bash

View File

@@ -12,7 +12,7 @@ into this document. The line ranges below are stable references to the evidence
and acceptance criteria that the implementing agent must read for each stage. and acceptance criteria that the implementing agent must read for each stage.
This plan owns remediation progress; a separate `audit.md` tracker is not needed. This plan owns remediation progress; a separate `audit.md` tracker is not needed.
All stages are pending when this plan is created. All stages begin pending when this plan is created.
| Stage | Summary | Primary findings | Status | | Stage | Summary | Primary findings | Status |
| ---: | --- | --- | --- | | ---: | --- | --- | --- |
@@ -36,18 +36,18 @@ All stages are pending when this plan is created.
| 18 | Serialize restore transitions and make restored paths portable | RSK-006, RSK-008 | Completed | | 18 | Serialize restore transitions and make restored paths portable | RSK-006, RSK-008 | Completed |
| 19 | Bind audio cache reuse to remote object identity | RSK-007 | Completed | | 19 | Bind audio cache reuse to remote object identity | RSK-007 | Completed |
| 20 | Unify previous-source readiness and eliminate duplicate transfers | COR-010, EFF-001 | Completed | | 20 | Unify previous-source readiness and eliminate duplicate transfers | COR-010, EFF-001 | Completed |
| 21 | Tighten configuration parsing, values, and expectations | COR-012COR-015, TST-011, TST-014 | Pending | | 21 | Tighten configuration parsing, values, and expectations | COR-012COR-015, TST-011, TST-014 | Completed |
| 22 | Make product configuration truthful and own remote temp files | COR-024, RSK-009, ARC-004 | Pending | | 22 | Make product configuration truthful and own remote temp files | COR-024, RSK-009, ARC-004 | Completed |
| 23 | Stream WhisperX uploads and make the adapter race-safe | COR-016, EFF-002, TST-001 | Pending | | 23 | Stream WhisperX uploads and make the adapter race-safe | COR-016, EFF-002, TST-001 | Completed |
| 24 | Correct prepare/transcribe transition semantics | COR-017COR-019, TST-008 | Pending | | 24 | Correct prepare/transcribe transition semantics | COR-017COR-019, TST-008 | Completed |
| 25 | Enforce output-path authority and shared singleton resolution | ARC-006, DUP-006 | Pending | | 25 | Enforce output-path authority and shared singleton resolution | ARC-006, DUP-006 | Completed |
| 26 | Centralize typed extraction-bundle evidence | DUP-007 | Pending | | 26 | Centralize typed extraction-bundle evidence | DUP-007 | Completed |
| 27 | Bind extraction reuse to direct transcript identity | COR-020, TST-009 | Pending | | 27 | Bind extraction reuse to direct transcript identity | COR-020, TST-009 | Completed |
| 28 | Establish one effective artifact set and catalog bootstrap | COR-022, ARC-007, DUP-008 | Pending | | 28 | Establish one effective artifact set and catalog bootstrap | COR-022, ARC-007, DUP-008 | Completed |
| 29 | Make analyze resolution typed, optional, actionable, and deterministic | COR-021, COR-023, RSK-015, SIM-003, TST-010 | Pending | | 29 | Make analyze resolution typed, optional, actionable, and deterministic | COR-021, COR-023, RSK-015, SIM-003, TST-010 | Completed |
| 30 | Remove misleading contracts and align Audita ownership | ARC-001, ARC-005, SIM-004, COM-003, COM-006 | Pending | | 30 | Remove misleading contracts and align Audita ownership | ARC-001, ARC-005, SIM-004, COM-003, COM-006 | Completed |
| 31 | Enforce CI validation and streamline the assembled test suite | TST-012, TST-015 | Pending | | 31 | Enforce CI validation and streamline the assembled test suite | TST-012, TST-015 | Completed |
| 32 | Reconcile lifecycle/analyze documentation and close the remediation | COM-002, COM-005 | Pending | | 32 | Reconcile lifecycle/analyze documentation and close the remediation | COM-002, COM-005 | Completed |
## Governing decisions ## Governing decisions
@@ -1082,6 +1082,8 @@ documentation/example checks, verify clean generated/example state, inspect the
final diff and repository status, and mark this stage complete only when no final diff and repository status, and mark this stage complete only when no
required remediation remains. required remediation remains.
**Status:** Completed.
## Finding traceability inventory ## Finding traceability inventory
This inventory assigns exactly one primary implementation stage to each confirmed This inventory assigns exactly one primary implementation stage to each confirmed

View File

@@ -436,7 +436,7 @@ Diagnostics:
```bash ```bash
ls -la /path/to/secrets_dir ls -la /path/to/secrets_dir
env | grep -E 'OBJECT_STORAGE|AWS|AUDITA|SCRIPTORIUM' env | sed 's/=.*//' | grep -E 'OBJECT_STORAGE|AWS|AUDITA|SCRIPTORIUM'
``` ```
Safe fix: Safe fix:

View File

@@ -5,6 +5,7 @@ import (
"os" "os"
"path/filepath" "path/filepath"
"regexp" "regexp"
"strconv"
"strings" "strings"
"testing" "testing"
@@ -65,6 +66,26 @@ func TestReleaseWorkflowRequiresValidation(t *testing.T) {
} }
} }
func TestRoadmapTraceabilityOwnersAreComplete(t *testing.T) {
root := repositoryRoot(t)
data, err := os.ReadFile(filepath.Join(root, "docs", "roadmap", "implementation.md"))
if err != nil {
t.Fatalf("read implementation roadmap: %v", err)
}
statuses := roadmapSummaryStatuses(t, string(data))
checked := 0
for _, owner := range roadmapTraceabilityOwners(t, string(data)) {
checked++
if statuses[owner] != "Completed" {
t.Errorf("traceability owner %d has status %q, want Completed", owner, statuses[owner])
}
}
if checked == 0 {
t.Fatal("roadmap traceability inventory has no owners")
}
}
func repositoryRoot(t *testing.T) string { func repositoryRoot(t *testing.T) string {
t.Helper() t.Helper()
root, err := filepath.Abs(filepath.Join("..", "..")) root, err := filepath.Abs(filepath.Join("..", ".."))
@@ -124,6 +145,53 @@ func relativeToRoot(root, path string) string {
return relative return relative
} }
func roadmapSummaryStatuses(t *testing.T, document string) map[int]string {
t.Helper()
statuses := map[int]string{}
for _, line := range strings.Split(document, "\n") {
fields := strings.Split(line, "|")
if len(fields) != 6 {
continue
}
owner, err := strconv.Atoi(strings.TrimSpace(fields[1]))
if err != nil {
continue
}
statuses[owner] = strings.TrimSpace(fields[4])
}
if len(statuses) == 0 {
t.Fatal("roadmap summary has no status entries")
}
return statuses
}
func roadmapTraceabilityOwners(t *testing.T, document string) []int {
t.Helper()
const inventoryHeading = "## Finding traceability inventory"
const nextHeading = "## Open Questions"
start := strings.Index(document, inventoryHeading)
if start < 0 {
t.Fatal("roadmap traceability inventory is missing")
}
inventory := document[start+len(inventoryHeading):]
if end := strings.Index(inventory, nextHeading); end >= 0 {
inventory = inventory[:end]
}
owners := []int{}
for _, line := range strings.Split(inventory, "\n") {
fields := strings.Split(line, "|")
if len(fields) != 4 {
continue
}
owner, err := strconv.Atoi(strings.TrimSpace(fields[2]))
if err == nil {
owners = append(owners, owner)
}
}
return owners
}
type woodpeckerWorkflow struct { type woodpeckerWorkflow struct {
Steps map[string]woodpeckerStep `yaml:"steps"` Steps map[string]woodpeckerStep `yaml:"steps"`
} }