diff --git a/docs/site/src/content/docs/changelog.mdx b/docs/site/src/content/docs/changelog.mdx index 6bb67c1b0..8ec93c20d 100644 --- a/docs/site/src/content/docs/changelog.mdx +++ b/docs/site/src/content/docs/changelog.mdx @@ -16,7 +16,7 @@ documents. Per-product release notes live in each product repository; the entries below link to the relevant product pages on this site rather than duplicating release notes. -## Unreleased +## v0.41.0 beta-53 - BREAKING: the published `registry-stack-client` Python package requires Python 3.11 or later: its `Requires-Python` is `>=3.11` (was `>=3.10`), its wheels are built against the Python 3.11 @@ -64,12 +64,20 @@ relevant product pages on this site rather than duplicating release notes. release/scripts/check-glibc-floor.sh; release/scripts/render-installer-libc-preflight.py, INSTALLERS. */} -- The Base Registry Engine (BReg), Registry Casework, Registry Scheduling, and Evidence installers - start every Linux binary they verified before they select the release, as they already did on - macOS. An installer checks the glibc floor of the release it was published with, so an installer - asked for an earlier release could select binaries built for a newer glibc than the host carries; - those binaries then failed at first run. The installer now refuses that release, names the binary - that did not start, and leaves the installed toolset selected. See +- Workflow `actions/setup-go` steps that compile AWS-LC-FIPS from source use Go 1.27.2, where they + used 1.24.4. Go remains a build tool and is not shipped. The distinct canonical Linux builder + still uses the snapshot-pinned Go package in its Debian 13 builder image. + +{/* Evidence: .github/workflows/release-candidate.yml, actions/setup-go steps; + release/notes/dependency-vetting-aws-lc-fips.md, Build prerequisites; + release/scripts/test_release_workflow_structure.py, GO_VERSION. */} + +- The four BReg, Registry Casework, Registry Scheduling, and Evidence installers start every staged + Linux binary with `--version` before they select the release, as they already did on macOS. An + installer checks the glibc floor of the release it was published with, so an installer asked for + an earlier release could select binaries built for a newer glibc than the host carries; those + binaries then failed at first run. The installer now refuses that release, names the binary that + did not start, and leaves the installed toolset selected. See [known limitations](../explanation/known-limitations/). {/* Evidence: crates/registry-breg/install.sh; crates/registry-casework/install.sh; @@ -79,6 +87,191 @@ relevant product pages on this site rather than duplicating release notes. release/scripts/test_nightly_release.py, test_linux_binary_that_cannot_start_never_replaces_the_installed_toolset. */} +- BREAKING: BReg revision reads no longer accept the v0.38.0-and-earlier provenance that journaled + an immediate action under its effect identifier. A detail read, or a list page containing such a + revision, answers `503 source.unavailable`. v0.41.0 reads only predecessor state created by a + v0.40.0 apply, which already journals the entity's canonical operation identifier and needs no + change. An older deployment must first follow the v0.40.0 fresh-database migration, then upgrade + that v0.40.0 predecessor state. + +{/* Evidence: products/breg/CHANGELOG.md, "revision history no longer reads a revision journaled + under an immediate action's effect identifier". */} + +- BREAKING: BReg refuses a database without subject access-log storage before it binds a listener. + Every apply from v0.38.0 onward installed that storage, including when the package declares no + `accessLog`, so predecessor state created by a v0.40.0 apply needs no change. v0.41.0 does not + upgrade older state in place: an older deployment must first follow the v0.40.0 fresh-database + migration, then upgrade that v0.40.0 predecessor state. + +{/* Evidence: products/breg/CHANGELOG.md, "a database without the subject access-log storage is no + longer verified or served". */} + +- BReg's Rust, Node.js, and Python clients accept additive object members in metadata and valid + Problem envelopes. Unsupported must-understand capabilities disable only the affected binding, + and unsupported descriptive metadata omits only the affected statistical dataset, descriptive + change-request capability, selector, or spatial capability. An unknown temporal mode retains its + inert `temporal` descriptor because null means the collection is non-temporal. Valid unknown + Problem codes retain their HTTP status and trace ID without inferred semantics; malformed known + fields and envelopes still fail as protocol errors. + +{/* Evidence: products/breg/CHANGELOG.md, "metadata readers ignore unknown object members", + "Well-formed unsupported metadata vocabulary", and "clients handle valid unknown Problem + codes". */} + +- `bregctl dev` derives the local runtime's principal and purpose claim mappings from the compiled + project and refuses an unservable mixed mapping before it retains development state. + `caseworkctl source add` uses the same-version `bregctl explain access` result to generate the + `casework-reader` profile with the BReg project's one compiled `principalClaim`, preserves exact + test-bound client variants, and accepts equivalent trailing-slash spellings of the Casework + review endpoint. + +{/* Evidence: products/breg/CHANGELOG.md, the three `bregctl dev` claim-mapping entries; + products/casework/CHANGELOG.md, `caseworkctl source add` and source pairing entries. */} + +- The native citizen self-registration acceptance project combines ThunderID SMS signup, + account-owned BReg applications, Casework review, and transactional Person creation, account + linking, and program enrollment through configured BReg actions. It proves an adopter + composition across existing product boundaries and adds no built-in business model or runtime. + +{/* Evidence: products/breg/acceptance/citizen-self-registration/README.md; + products/breg/acceptance/citizen-self-registration/tests/run-live.py; + release/notes/v0.41.0.md, "Acceptance projects and release operation". */} + +- Registry Casework task templates can use `authorizationMode: deferred` with a lifetime of up to + seven days. Immediate grants keep their 900-second ceiling. A deferred review grant is bound to + the task's assignment generation and ends when assignment or terminal state changes; deferred + grants cannot carry Evidence bounds. Casework migration 0022 installs the grant-window constraints + and assignment-generation trigger, validating the affected tables under an exclusive lock. + +{/* Evidence: products/casework/CHANGELOG.md, `authorizationMode: deferred` and migration 0022. */} + +- The shared Registry Platform task-grant status transport now supplies BReg and Scheduling with + `TaskGrantStatusConfig`, endpoint validation, status credentials, exact binding checks, and the + default Casework status scope and route. BReg accepts optional `statusScope` and `statusPath`, and + its development tooling can bind declared Casework task authorities into the generated runtime. + +{/* Evidence: products/platform/CHANGELOG.md, `registry-platform-oidc` task_grant module and + `TaskGrantStatusConfig`; products/breg/CHANGELOG.md, `statusScope`, `statusPath`, and + `bregctl dev` taskGrantStatus entries. */} + +- BREAKING: BReg treats a `401` or `403` from the Casework task-grant status endpoint as an outage, + answering `503 service.unavailable` where it answered `412 precondition.failed`. A `404` still + refuses the grant with `412`. The shared transport identifies itself as `registry-task-status` + instead of `registry-breg-task-status`. Update alerts for a revoked or misconfigured status + client, and update access-log user-agent matches. + +{/* Evidence: products/breg/CHANGELOG.md, "task-grant status check before a governed write". */} + +- BREAKING: BReg validates each `taskGrantStatus` entry when it reads the runtime file and reports + `breg.runtime.invalid-task-grant-status` at `/taskGrantStatus`, where activation reported + `breg.runtime.invalid-binding`. The endpoint and client members now use their URL, external + identifier, resource URI, and issuer types at that boundary. A configuration that v0.40.0 + activated already meets the member rules. Update scripts that match the earlier diagnostic code. + +{/* Evidence: products/breg/CHANGELOG.md, "runtime checks each `taskGrantStatus` entry". */} + +- BREAKING: Registry Casework removes `casework migrate` and `caseworkctl db`. Use `caseworkctl plan + --runtime-config FILE` followed by `caseworkctl apply --runtime-config FILE`. It also removes the + `casework.package.retired-manifest` refusal. v0.40.0 already refused these commands and packages + with the retired manifest, so no valid v0.40.0 package needs rebuilding for this cleanup. Rebuild + an older retained package with `caseworkctl package` instead of matching the removed code. + +{/* Evidence: products/casework/CHANGELOG.md, `casework migrate` and + `casework.package.retired-manifest`. */} + +- BREAKING: `caseworkctl dev` removes a database volume only when it carries the session ownership + label. Every v0.40.0 session labels its volume. Before you remove an older unlabeled + `casework-dev-` volume, inspect and back up its contents. Removing the volume with + `docker volume rm` permanently destroys its data. Follow the + [v0.41.0 release note](https://github.com/registrystack/registry-stack/blob/v0.41.0/release/notes/v0.41.0.md#retired-command-and-compatibility-paths). + +{/* Evidence: products/casework/CHANGELOG.md, "removes a database volume only when the volume + carries the session's ownership label". */} + +- BREAKING: the Casework BReg source adapter refuses a legacy bare continuation cursor that names + no request entity. Every cursor stored by v0.40.0 names its entity, so a v0.40.0 database needs no + migration. + +{/* Evidence: products/casework/CHANGELOG.md, "source adapter refuses a stored discovery cursor". */} + +- BREAKING: `caseworkctl dev` reports five configuration refusals with exit status 1, where it + reported `caseworkctl.operational-failure` and exit status 3: + `caseworkctl.dev.integrations-invalid`, `caseworkctl.dev.shared-client-mismatch`, + `caseworkctl.dev.shared-task-authority-mismatch`, + `caseworkctl.dev.source-binding-invalid`, and + `caseworkctl.dev.borrowed-principal-invalid`. A borrowed issuer session also refuses + `principalClaim: sub`, because that claim names the issuer owner's subject. Use a stable claim in + every Casework access profile, register it for each client in both projects' `dev-clients.yaml`, + and update scripts that match the earlier status and code. + +{/* Evidence: products/casework/CHANGELOG.md, "reports five configuration refusals" and "refuses a + session that borrows another project's issuer". */} + +- BREAKING: `CaseworkTaskAssertionSource` classifies a Casework `4xx` assertion refusal other than + `408` or `429` as `invalid-credential`, where it classified every failure as `unavailable`. + Request a new approval instead of retrying an expired, revoked, or absent grant. + +{/* Evidence: products/casework/CHANGELOG.md, `CaseworkTaskAssertionSource`. */} + +- BREAKING: `evidencectl build` is now an unknown command. Use `evidencectl package` with the project + directory as its positional argument and retain the same `--target` and `--output` options. + `evidencectl init` and `evidencectl new` no longer accept the inactive `--generate-keys` option; + remove it because a local project already creates disposable keys. + +{/* Evidence: products/evidence/CHANGELOG.md, "drops two spellings it had stopped acting on". */} + +- BREAKING: Registry Scheduling requires a top-level `taskGrantStatus` in every runtime file. List + one to 32 task authorities whenever the deployment requires current status or revocation checks, + and for deferred work. `taskGrantStatus: unchecked-final-fifteen-minutes` checks only the grant's + remaining lifetime because the signed token does not identify its original mode. It admits any + grant with at most 900 seconds remaining without checking revocation, including the final 900 + seconds of a deferred grant. Use it only when the deployment accepts that stale-authority window. + An omitted member is refused at startup with `scheduling.runtime.missing-task-grant-status`. + +{/* Evidence: products/scheduling/CHANGELOG.md, the `taskGrantStatus` behavior and missing-member + refusal; products/scheduling/RUNTIME-CONFIG.md, `taskGrantStatus` offline path. */} + +- BREAKING: Registry Scheduling removes three refusals for pre-v0.40.0 inputs. `scheduling migrate` + is an unknown command; activate with `schedulingctl plan` and `schedulingctl apply`. + `scheduling.package.retired-manifest` is replaced by the ordinary package-content refusals, so + rebuild with `schedulingctl package`. `schedulingctl.activation.earlier-release` is replaced by + `schedulingctl.store-unavailable`, so start from a new database when the retained policy uses the + pre-v0.40.0 identity. A database activated by v0.40.0 needs no reset. Direct Rust consumers must + remove `RuntimeError::RemovedCommand`, `RuntimeError::exit_code`, + `runtime::removed_command_refusal`, `RuntimeConfigError::RetiredPackageManifest`, + `config::RETIRED_PACKAGE_MANIFEST_FILE`, and `StoreError::EarlierRelease`. + +{/* Evidence: products/scheduling/CHANGELOG.md, "three refusals that named input only releases + before v0.40.0 wrote or accepted". */} + +- Registry Scheduling's `POST /v1/appointments/receipt` and Registry Messaging's + `POST /v1/messages/receipt` use the original `Idempotency-Key`, request body, and verified caller + identity to resolve the retained original success receipt. They do not return the request body or + repeat the mutation. Both routes use current ordinary read authority. Scheduling can recover the + receipt after the task grant ends. An unresolved receipt answers `409 receipt.unresolved`, which + does not prove that no effect occurred. The Rust, Node.js, and Python clients carry both routes. + +{/* Evidence: products/scheduling/CHANGELOG.md, `POST /v1/appointments/receipt`; + products/messaging/CHANGELOG.md, `POST /v1/messages/receipt`. */} + +- BREAKING (Rust API): `registry_scheduling_core::ProblemCode` and + `registry_messaging_core::ProblemCode` gain `ReceiptUnresolved`. Add that arm, or a wildcard arm, + to exhaustive matches. + +{/* Evidence: products/scheduling/CHANGELOG.md and products/messaging/CHANGELOG.md, + `ProblemCode` gains `ReceiptUnresolved`. */} + +- BReg and Casework local development pull the same pinned PostgreSQL image from + `public.ecr.aws/docker/library/postgres`. Messaging pulls that PostgreSQL mirror and Mailpit from + `ghcr.io/axllent/mailpit`. Development egress allowlists must admit `public.ecr.aws` and, for + Messaging, `ghcr.io`. Retained BReg and Casework containers using the earlier Docker Hub + PostgreSQL reference at the same digest remain accepted; BReg PostGIS sessions still use Docker + Hub's `postgis/postgis` image. + +{/* Evidence: products/breg/CHANGELOG.md, `bregctl dev start` PostgreSQL image; + products/casework/CHANGELOG.md, `caseworkctl dev start` PostgreSQL image; + products/messaging/CHANGELOG.md, `messagingctl dev` PostgreSQL and Mailpit images. */} + ## v0.40.0 beta-52 - BREAKING: v0.40.0 does not upgrade v0.39.0 configuration, packages, or databases in place, and diff --git a/docs/site/src/content/docs/operate/advanced/upgrade-and-retire.mdx b/docs/site/src/content/docs/operate/advanced/upgrade-and-retire.mdx index b9852d3bf..c1cedb5d0 100644 --- a/docs/site/src/content/docs/operate/advanced/upgrade-and-retire.mdx +++ b/docs/site/src/content/docs/operate/advanced/upgrade-and-retire.mdx @@ -28,10 +28,9 @@ rolling upgrade that mixes releases is not supported: [Upgrade Casework and BReg in lock-step](../../casework/#upgrade-casework-and-breg-in-lock-step). - **Adopter tooling is checked.** `evidencectl` refuses an `evidence` or `bregctl` binary of another version. -- **Clients are not checked, and break silently.** Clients send no version, and runtimes accept any - caller. The clients decode responses strictly, so a member one release adds can fail an older - client's decoding, and a member one release requires can be missing from an older runtime's - answer. Upgrade each client to the same release as the runtime it calls. +- **Clients are not checked.** Clients send no version, and runtimes accept any caller. Pre-1.0 + client and wire contracts can change incompatibly between releases, so upgrade each client to + the same release as the runtime it calls. - **BReg activation is not rolling.** Once `bregctl apply` activates a successor, every `breg` process still running the previous package fails readiness until it restarts onto the successor. Plan the restart as part of the activation, not after it. @@ -45,7 +44,6 @@ v0.39.0 wrote in place, and its release notes have you apply it to new databases {/* Evidence: Cargo.toml, [workspace.package] version (every crate uses version.workspace); crates/registry-casework-breg/src/lib.rs, same_release() and PeerVersionMismatch; crates/registry-evidencectl/src/evidence_binary.rs and source_add.rs, check_public_bregctl(); - crates/registry-breg-client/src/response.rs, deny_unknown_fields; docs/site/src/content/docs/operate/breg-changes.mdx, "Activate the successor"; release/scripts/rehearse-upgrade.py, FORWARD_PATH_FLOOR; release/notes/config-conventions/stack.md, "BREAKING: v0.40.0 does not upgrade v0.39.0 state @@ -61,6 +59,11 @@ reconciliation before that product's apply, and make the listed project and runt in its upgrade step. Rehearse the whole sequence on a restored copy first, as [Run a disaster-recovery drill](../back-up-and-restore/#run-a-disaster-recovery-drill) describes. +The v0.40.0 to v0.41.0 path upgrades the v0.40.0 databases in place. It does not restore support +for state or package forms that v0.40.0 already refused. On native Linux, require glibc 2.34 or +newer. The four product installers start every staged Linux binary before selecting the new +toolset, so a binary that cannot run leaves the installed toolset selected. + 1. **Back up every database.** Take the BReg and Casework `pg_dump`s, and the Scheduling and Messaging ones when they run. Copy those products' packages and runtime files, and keep the previous release's binaries. These backups are the only way back; see [Roll back](#roll-back). @@ -68,75 +71,78 @@ in its upgrade step. Rehearse the whole sequence on a restored copy first, as [Operational limits](../../../configure/evidence-oid4vci/#operational-limits). 3. **Pause and drain Evidence traffic** for every question that reads BReg, or pause the whole instance when you cannot drain one question at a time. Keep the previous Evidence candidate. -4. **Upgrade BReg.** For v0.39.0 to v0.40.0, the new `bregctl` does not upgrade a database the - earlier release wrote: `plan` and `apply` refuse the package the earlier release built as - `apply.package.refused`, naming `package.root`. Finish or cancel active ingestion runs on the - earlier release, and record the run metadata, committed counts, and receipts you need. Make - the project and runtime-file changes the release notes list, rebuild the project with the new - `bregctl test` and `bregctl package --test-receipt FILE --output BUILD`, and apply it to a new - database with `bregctl apply --initial --runtime-config FILE --package BUILD/package`. Nothing - the earlier database held carries over: not records, not spent idempotency keys, and not stored - runs, chunks, or receipts. An earlier checkpoint refuses to resume; import the data again - under a fresh checkpoint, as - [Load a governed entity through an import window](../../breg-data/#load-a-governed-entity-through-an-import-window) - describes. For a later release, make the project and runtime-file changes the release notes list, rebuild the - deployed project with no model change using the new `bregctl test` and `bregctl package - --test-receipt FILE --output BUILD` (a receipt from the earlier release is not accepted), point - `package.root` at `BUILD/package` (and `package.expectedDigest`, when set, at the package - digest it reports, `packageDigest` with `--format json`), check it against the live database with - `bregctl plan --runtime-config FILE --package BUILD/package` naming the same directory, apply - it with `bregctl apply --runtime-config FILE --package BUILD/package`, run `bregctl verify --runtime-config - FILE`, and restart every `breg` process on the new binary; `bregctl status --runtime-config - FILE` confirms what the database activated. A model change follows as its own successor; see - [Activate the successor](../../breg-changes/#activate-the-successor). When an `apply` stops - before it finishes, rerun it with the same `database.roles`: a retry under other roles is - refused as `apply.resume.roles-differ`, naming the roles the activation started with. A new package applied under `database.roles` other than the ones the active activation serves with is refused as `apply.successor.roles-differ` before maintenance; apply the active package under the new roles first, then the new package. A role change, the active package applied under other `database.roles`, cannot be assessed by `bregctl migration reconcile`: when one stops before it finishes, fix the cause and rerun the same apply, which resumes it. Casework reports each BReg source as unavailable from here until step 5 +4. **Upgrade BReg.** A database created by a v0.40.0 apply already has canonical action-revision + provenance and subject access-log storage, so v0.41.0 reads it in place. The `bregctl plan` + command later in this step reads and validates every `taskGrantStatus` entry. An entry v0.40.0 + activated remains valid, but a script that matched `breg.runtime.invalid-binding` for a + malformed entry must now match `breg.runtime.invalid-task-grant-status`. Update Casework + access-log rules for the + `registry-task-status` user agent and alert on `503 service.unavailable` when the status client + is misconfigured or revoked. Rebuild the deployed project with no model change using the new + `bregctl test` and `bregctl package --test-receipt FILE --output BUILD`; a test receipt from + v0.40.0 is not accepted. Point `package.root` at `BUILD/package`, and repin + `package.expectedDigest` when set. Run `bregctl plan --runtime-config FILE --package + BUILD/package`, apply with `bregctl apply --runtime-config FILE --package BUILD/package`, and + run `bregctl verify --runtime-config FILE`. Restart every `breg` process on v0.41.0, then use + `bregctl status --runtime-config FILE` to confirm the active package. A model change follows as + its own successor; see [Activate the successor](../../breg-changes/#activate-the-successor). + When an apply stops, fix the cause and rerun it with the same `database.roles`; changing roles + during recovery is refused. Casework reports each BReg source as unavailable until step 5 finishes. -5. **Upgrade Casework.** Settle pending attempts first, since an upgrade can strand them. When step - 4 changed the `registryRevision` a BReg source serves, check each such source with `caseworkctl - check PROJECT --against-breg-package DIR --source-id ID`, repin it with `caseworkctl source add - BREG_PROJECT --project PROJECT --source-id ID --apply`, package the Casework project again, and - point the runtime file's `package.root` at the new package (and `package.expectedDigest`, when - set, at its digest); see - [Check a BReg source's pinned revision](../../casework/#check-a-breg-sources-pinned-revision). - Stop every earlier `casework` process before the apply: one left running holds the audit - writer lock the new runtime needs, and can strand a source attempt when the apply changes a - source's binding generation. Run `caseworkctl plan --runtime-config FILE` and `caseworkctl apply --runtime-config FILE` with the - new binaries, then start `casework` and run `caseworkctl doctor --runtime-config FILE`; see [Plan, apply, and serve](../../casework/#plan-apply-and-serve). - For v0.39.0 to v0.40.0, the release notes have you apply Casework to a new database. -6. **Upgrade Evidence.** Re-import each BReg source whose export the release notes say changed, - then package a fresh candidate with the new `evidencectl package`, run `evidence check - --runtime-config FILE --require-runtime-dependencies` with the new binary (add - `--without-audit-lock` while the earlier instance still runs), stop the earlier `evidence`, - start the new one, and verify a fresh synthetic assertion. Then start the new `evidence-oid4vci`. -7. **Upgrade Scheduling**, when it runs. Stop the earlier `scheduling` runtime, or keep its - destination bindings until its hook deliveries drain. Unless the release notes have you start - from a new database, run `schedulingctl plan --runtime-config - FILE` and `schedulingctl apply --runtime-config FILE` with the new binary, then start - `scheduling`; `schedulingctl status --runtime-config FILE` confirms what the database activated. - For v0.39.0 to v0.40.0, the new `schedulingctl` does not upgrade a database the earlier release - wrote. Start from a new database, then run `schedulingctl - apply --runtime-config FILE` and `schedulingctl records apply --runtime-config FILE RECORDS` with the - files changed as the release notes list. Nothing the earlier database held carries over, - published windows, holds, and appointments included. -8. **Upgrade Messaging**, when it runs. Stop new submissions, let in-flight senders finish - retrying submissions whose answers they lost, then stop every earlier `messaging` runtime. Give - graceful shutdown time to finish sends already in flight. After every old runtime stops, refresh - the Messaging `pg_dump`; this stopped, pre-apply snapshot includes the old runtime's final sends - and is the rollback backup. For v0.39.0 to v0.40.0, the new binaries refuse the earlier runtime - file and a package the earlier release built: make the project and runtime-file changes the - release notes list, build the package again with the new `messagingctl package PROJECT --output - DIRECTORY`, and point `package.root` at the new directory (and `package.expectedDigest`, when - set, at the digest it reports). The release notes have you run the plan and apply that follow - against a new database, because no schema version rewrites the dispatch job states the earlier - release stored. Run `messagingctl plan --runtime-config FILE`, then `messagingctl - apply --runtime-config FILE` with the new binary. Confirm the activation with `messagingctl status - --runtime-config FILE`, start the new `messaging`, and require `GET /ready` to answer `200` before - you resume submissions. For v0.39.0 to v0.40.0, the new database holds no earlier idempotency - record, so finish this drain before you point callers at the new runtime; a later retry under - an earlier key can send its message twice. -9. **Resume traffic, and upgrade clients.** Roll out every application that embeds a Registry - Stack client at the same release before it calls the upgraded runtimes. +5. **Upgrade Casework.** Settle pending attempts first because an upgrade can strand them. When + step 4 changed a BReg source's `registryRevision`, check and repin that source as + [Check a BReg source's pinned revision](../../casework/#check-a-breg-sources-pinned-revision) + describes. `caseworkctl source add` now derives the generated `casework-reader` profile from the + BReg project's one compiled `principalClaim`; if it refuses mixed claims, align every entity + profile and action grant, including module-contributed grants and a `casework-reader` profile an + earlier `source add` generated, to one claim and repeat the command. Package the Casework + project again, point `package.root` at the package, and repin `package.expectedDigest` when set. + If a development session borrows another project's issuer, replace `principalClaim: sub` in + every Casework access profile with a stable claim such as `registry_principal`, then register + that claim for each client in both projects' `dev-clients.yaml`. Stop every v0.40.0 `casework` + process before the apply. Migration 0022 validates the task-grant tables under an exclusive lock + and installs the deferred-grant window constraints and assignment generation trigger. Run + `caseworkctl plan --runtime-config FILE`, then `caseworkctl apply --runtime-config FILE`; the + removed `casework migrate` and `caseworkctl db` commands are not aliases. Start `casework` and + run `caseworkctl doctor --runtime-config FILE`; see + [Plan, apply, and serve](../../casework/#plan-apply-and-serve). +6. **Upgrade Evidence.** Replace any `evidencectl build` invocation with `evidencectl package`, and + remove `--generate-keys` from `evidencectl init` or `evidencectl new`. Re-import a BReg source + when its export changed, then package a fresh candidate with the new `evidencectl package`. + Run `evidence check --runtime-config FILE --require-runtime-dependencies` with the new binary, + adding `--without-audit-lock` while the v0.40.0 instance still runs. Stop the earlier + `evidence`, start v0.41.0, and verify a fresh synthetic assertion. Then start the new + `evidence-oid4vci`. +7. **Upgrade Scheduling**, when it runs. Add the required top-level `taskGrantStatus` before you + run the v0.41.0 tooling. List the task authorities whenever Scheduling must check current status + or revocation, and when it accepts deferred work. The + `taskGrantStatus: unchecked-final-fifteen-minutes` path checks only remaining lifetime because a + signed token does not identify its original grant mode. It admits any grant with at most 900 + seconds remaining without checking revocation, including the final 900 seconds of a deferred + grant. Use it only when the deployment accepts that stale-authority window. + Run `schedulingctl check PROJECT --runtime-config FILE`, then stop the v0.40.0 runtime or keep its + destination bindings until hook deliveries drain. Run `schedulingctl plan --runtime-config + FILE` and `schedulingctl apply --runtime-config FILE` against the v0.40.0 database. Start + `scheduling`, then use `schedulingctl status --runtime-config FILE` to confirm the activation. + The removed `scheduling migrate` command and pre-v0.40.0 package and policy refusals provide no + compatibility path; a database activated by v0.40.0 needs no reset. +8. **Upgrade Messaging**, when it runs. Stop new submissions, let in-flight senders finish retrying + submissions whose answers they lost, then stop every v0.40.0 `messaging` runtime. Give graceful + shutdown time to finish sends already in flight. Refresh the `pg_dump` after every earlier + runtime stops, so the rollback backup includes their final sends. Rebuild the package when the + release notes require it, update `package.root`, and repin `package.expectedDigest` when set. + Run `messagingctl plan --runtime-config FILE`, then `messagingctl apply --runtime-config FILE` + against the v0.40.0 database. Confirm the activation with `messagingctl status --runtime-config + FILE`, start v0.41.0, and require `GET /ready` to answer `200` before you resume submissions. +9. **Upgrade clients, then resume traffic.** Move Python applications to Python 3.11 or later and + Node.js applications to Node.js 24.11.0 or later before installing the v0.41.0 client packages. + Update exhaustive Rust matches on the Scheduling or Messaging `ProblemCode` enums for + `ReceiptUnresolved`. Treat `CaseworkTaskAssertionSource` `invalid-credential` as a grant refusal: + request a new approval and stop retrying that credential. In BReg metadata, an unsupported + `requiredCapabilities` value disables only the affected binding and can make selection report + `required-capability`. Handle a valid unknown BReg Problem by its HTTP status and trace ID + without inferring code or extension semantics. Roll out every application that embeds a + Registry Stack client at v0.41.0 before it calls the upgraded runtimes, then resume traffic. {/* Evidence: docs/site/src/content/docs/operate/casework.mdx, "Upgrade Casework and BReg in lock-step" (BReg first, readiness fails in between); @@ -145,34 +151,20 @@ in its upgrade step. Rehearse the whole sequence on a restored copy first, as docs/site/src/content/docs/tutorials/deploy-evidence-from-breg.mdx, "Coordinate a breaking update"; crates/registry-casework/src/store.rs, StoreError::AttemptPending; crates/registry-breg/src/migration.rs, MigrationError::ResumeRolesDiffer; - crates/registry-breg/src/ingestion_store.rs, cancel_run(); - docs/site/src/content/docs/operate/breg-data.mdx, committedItems and the fresh checkpoint path; - crates/registry-bregctl/src/apply_lifecycle.rs, load_active_predecessor_package(); - crates/registry-bregctl/src/lib.rs, PlanSuccessReport, StatusSuccessReport, and - lifecycle_failure() for ApplyLifecycleError::CurrentPackage (apply.package.refused at - package.root); - crates/registry-breg/src/package.rs, RETIRED_PACKAGE_API_VERSION and - PackageError::RetiredApiVersion; - release/notes/config-conventions/stack.md, "BREAKING: v0.40.0 does not upgrade v0.39.0 state - in place" and "Breaking changes outside the program fragments" (the new BReg database holds - no idempotency record and no ingestion run, an earlier checkpoint refuses to resume; the new - Messaging database holds no idempotency record); - release/notes/config-conventions/casework.md, "BREAKING: a clock is tagged by `type`, and its - four values are kebab-case" (apply to a new database); + products/breg/CHANGELOG.md, v0.41.0 - 2026-10-13 entries; + products/casework/CHANGELOG.md, v0.41.0 - 2026-10-13 entries and migration 0022; + products/evidence/CHANGELOG.md, v0.41.0 - 2026-10-13 entries; + products/scheduling/CHANGELOG.md, v0.41.0 - 2026-10-13 entries; + crates/registry-schedulingctl/src/lib.rs, CheckArgs, ActivationArgs, and ApplyArgs; + products/messaging/CHANGELOG.md, v0.41.0 - 2026-10-13 entries; docs/site/src/content/docs/operate/messaging.mdx, "Plan, apply, inspect, and serve"; crates/registry-messaging/src/runtime.rs, shutdown_signal() and Listeners::serve_until(); - release/notes/config-conventions/messaging.md, "BREAKING: the runtime file's keys and - apiVersion are renamed" (the earlier runtime file and package are refused, the upgrade order) - and "BREAKING: the dispatch queue's job words are kebab-case" (no schema version rewrites a - stored job state); - crates/registry-messaging/src/config.rs, MESSAGING_RETIRED_API_VERSIONS and - PACKAGE_EXPECTED_DIGEST; crates/registry-messaging-core/src/package.rs, - MESSAGING_PROJECT_FORMAT; crates/registry-messagingctl/src/lib.rs, PackageArgs; release/notes/v0.36.0.md, "Upgrade Scheduling, Relay, and Discovery from v0.35.0" (apply before start, hook drain); - release/notes/config-conventions/scheduling.md, "BREAKING: a database an earlier release - wrote is not read"; crates/registry-scheduling/src/store.rs, retained_policy(); - crates/registry-schedulingctl/src/lib.rs, RecordsApplyArgs; + release/glibc-floor.env, REGISTRY_GLIBC_FLOOR; + crates/registry-breg/install.sh; crates/registry-casework/install.sh; + crates/registry-scheduling/install.sh; crates/registry-evidencectl/install.sh, + staged Linux --version checks; release/scripts/rehearse-upgrade.py rehearses each product alone, not this composition. */} ## Roll back diff --git a/docs/site/src/data/archive-lock.yaml b/docs/site/src/data/archive-lock.yaml index 05e95130e..a96622199 100644 --- a/docs/site/src/data/archive-lock.yaml +++ b/docs/site/src/data/archive-lock.yaml @@ -170,3 +170,7 @@ archives: bundle_sha256: b7d14cc48cadffab7f44f70bc8fc822811c70ef171b20ad36e2b46cf990d83a2 root_tree_sha256: b5f17867392d0c9c96866a7f3a76d158a71809be183fa12e2cdbf0278f518891 version_tree_sha256: 4a0bfdd82397e8abd76f710fb07743082a93a4861d43d37bb1345f5fe61f7a7d + v0.41.0: + bundle_sha256: 4f948c5abe4103dcd268905fde5d17527054f44a9e0616dd847664a53a9d1e54 + root_tree_sha256: f8bc9fc01dd69412b1f37156adb9d076b0ea1d92788d67c4586c691b649d3247 + version_tree_sha256: 63ec510c72629390da1b2eb54726c9b07e76c9330f9d8dbb2dd81222aa22e202 diff --git a/docs/site/src/data/docsets.yaml b/docs/site/src/data/docsets.yaml index 0225a9e20..713be0f6c 100644 --- a/docs/site/src/data/docsets.yaml +++ b/docs/site/src/data/docsets.yaml @@ -35,6 +35,40 @@ docsets: registry-breg-services: version: main source (unreleased) ref: HEAD + - id: v0.41.0 + label: v0.41.0 + path: /v/0.41.0/ + status: archived + availability: candidate + source: registry-stack-v0.41.0 + repo_docs_source: monorepo + published_at: 2026-10-13 + description: Registry Stack v0.41.0 beta-53 candidate documentation set. + products: + registry-stack: + version: v0.41.0 + ref: v0.41.0 + registry-manifest: + version: v0.41.0 + ref: v0.41.0 + registry-evidence: + version: v0.41.0 + ref: v0.41.0 + registry-casework: + version: v0.41.0 + ref: v0.41.0 + registry-scheduling: + version: v0.41.0 + ref: v0.41.0 + registry-render: + version: v0.41.0 + ref: v0.41.0 + registry-messaging: + version: v0.41.0 + ref: v0.41.0 + registry-breg-services: + version: v0.41.0 + ref: v0.41.0 - id: v0.40.0 label: v0.40.0 path: /v/0.40.0/ diff --git a/docs/site/src/data/repo-docs.yaml b/docs/site/src/data/repo-docs.yaml index 94dba17ab..c59c612af 100644 --- a/docs/site/src/data/repo-docs.yaml +++ b/docs/site/src/data/repo-docs.yaml @@ -98,6 +98,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [ dcat, bregdcat-ap, cpsv-ap, ogc-api-records, shacl, skos, json-schema, json-ld, odrl, sp-dci, w3c-did, prov-o, govstack-digital-registries ] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [ dcat, bregdcat-ap, cpsv-ap, ogc-api-records, shacl, skos, json-schema, json-ld, odrl, sp-dci, w3c-did, prov-o, govstack-digital-registries ] + last_reviewed: unreviewed description: Operator and integrator documentation for Registry Manifest. - src: products/manifest/docs/validate-and-render.md archive_src: docs/validate-and-render.md @@ -150,6 +153,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [ dcat, bregdcat-ap, cpsv-ap, ogc-api-records, shacl, skos, json-schema, json-ld, odrl ] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [ dcat, bregdcat-ap, cpsv-ap, ogc-api-records, shacl, skos, json-schema, json-ld, odrl ] + last_reviewed: unreviewed - src: products/manifest/docs/profile-fixtures.md archive_src: docs/profile-fixtures.md dest: products/registry-manifest/profile-fixtures @@ -198,6 +204,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [ sp-dci ] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [ sp-dci ] + last_reviewed: unreviewed - src: products/manifest/docs/reference.md archive_src: docs/reference.md dest: products/registry-manifest/reference @@ -249,6 +258,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [ dcat, bregdcat-ap, cpsv-ap, ogc-api-records, shacl, skos, json-schema, json-ld, cccev, odrl, w3c-did ] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [ dcat, bregdcat-ap, cpsv-ap, ogc-api-records, shacl, skos, json-schema, json-ld, cccev, odrl, w3c-did ] + last_reviewed: unreviewed - src: products/manifest/docs/itb-semic-validation.md dest: products/registry-manifest/itb-semic-validation label: ITB and SEMIC validation @@ -297,6 +309,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [ dcat, bregdcat-ap, shacl, skos, json-schema, json-ld ] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [ dcat, bregdcat-ap, shacl, skos, json-schema, json-ld ] + last_reviewed: unreviewed registry-evidence: label: Evidence Gateway remote: https://github.com/registrystack/registry-stack @@ -353,6 +368,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [ openapi, json-schema, sd-jwt-vc ] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [ openapi, json-schema, sd-jwt-vc ] + last_reviewed: unreviewed description: Operator and integrator documentation for Evidence Gateway, the minimum-disclosure assertion service. - src: products/evidence/CONCEPT.md dest: products/registry-evidence/concept @@ -402,6 +420,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [ cccev, json-schema, openapi, sd-jwt-vc ] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [ cccev, json-schema, openapi, sd-jwt-vc ] + last_reviewed: unreviewed description: Approved Version 1 product concept covering the boundary, data model, trust and privacy invariants, native API, and acceptance set. - src: products/evidence/reference/authoring-projects/CONFIG.md dest: products/registry-evidence/authoring-form @@ -451,6 +472,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [ json-schema, openapi, sd-jwt-vc ] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [ json-schema, openapi, sd-jwt-vc ] + last_reviewed: unreviewed description: Complete reference for the editable Evidence authoring project, its validation layers, local key material, and access policies. - src: products/evidence/reference/authoring-projects/SOURCE-EXPORT.md dest: products/registry-evidence/source-exports @@ -500,6 +524,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [] + last_reviewed: unreviewed description: Optional native source import, customized updates, provenance and interrupted transaction recovery. - src: products/evidence/reference/request-adapter/deployment-projects/SOURCE-CREDENTIAL-ROTATION.md dest: products/registry-evidence/source-credential-rotation @@ -549,6 +576,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [] + last_reviewed: unreviewed description: Rotate source credentials with explicit overlap, bounded OAuth caches and verified restart. - src: products/evidence/FIRST-CURL-TEST.md dest: products/registry-evidence/first-curl-test @@ -598,6 +628,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [] + last_reviewed: unreviewed description: Deterministic local curl checkpoint against the Evidence Gateway server with a mock source and an in-memory test JWKS. - src: products/evidence/SOURCE-TESTING.md dest: products/registry-evidence/source-testing @@ -647,6 +680,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [ sd-jwt-vc ] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [ sd-jwt-vc ] + last_reviewed: unreviewed description: Source-testing contract with the deterministic mock matrix, opt-in public demo smoke tests, and credential handling rules. - src: products/evidence/SD-JWT-VC-DEMO.md dest: products/registry-evidence/sd-jwt-vc-demo @@ -696,6 +732,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [ sd-jwt-vc ] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [ sd-jwt-vc ] + last_reviewed: unreviewed description: Deterministic local demo that issues one assertion in both later-verifiable formats and re-verifies the credential offline. - src: products/evidence/OPERATOR-CONTRACT.md dest: products/registry-evidence/operator-contract @@ -745,6 +784,9 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [ openapi, sd-jwt-vc ] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [ openapi, sd-jwt-vc ] + last_reviewed: unreviewed description: Supported deployment shape, requester authority and purpose duties, required configuration and secrets, and readiness, audit, and key obligations. - src: products/evidence/PERFORMANCE.md dest: products/registry-evidence/performance @@ -794,4 +836,7 @@ repos: - docsets: [ v0.40.0 ] standards_referenced: [] last_reviewed: unreviewed + - docsets: [ v0.41.0 ] + standards_referenced: [] + last_reviewed: unreviewed description: Measured baseline of the audit-durability throughput trade and the deferred work that would recover most of the cost. diff --git a/products/breg/CHANGELOG.md b/products/breg/CHANGELOG.md index 29952ff25..4b2f9ced6 100644 --- a/products/breg/CHANGELOG.md +++ b/products/breg/CHANGELOG.md @@ -2,6 +2,8 @@ ## Unreleased +## 0.41.0 - 2026-10-13 + - BREAKING: the published `registry-stack-client` Python package, which carries the Base Registry Engine client, requires Python 3.11 or later: its `Requires-Python` is `>=3.11` (was `>=3.10`), and its wheels are built diff --git a/products/casework/CHANGELOG.md b/products/casework/CHANGELOG.md index 586803093..84a330431 100644 --- a/products/casework/CHANGELOG.md +++ b/products/casework/CHANGELOG.md @@ -2,6 +2,8 @@ ## Unreleased +## 0.41.0 - 2026-10-13 + - BREAKING: the published `registry-stack-client` Python package, which carries the Registry Casework client, requires Python 3.11 or later: its `Requires-Python` is `>=3.11` (was `>=3.10`), and its wheels are built diff --git a/products/discovery/CHANGELOG.md b/products/discovery/CHANGELOG.md index 3746053a4..789af4433 100644 --- a/products/discovery/CHANGELOG.md +++ b/products/discovery/CHANGELOG.md @@ -2,6 +2,8 @@ ## Unreleased +## 0.41.0 - 2026-10-13 + - BREAKING: the published `registry-stack-client` Python package, which carries the Registry Discovery client, requires Python 3.11 or later: its `Requires-Python` is `>=3.11` (was `>=3.10`), and its wheels are built diff --git a/products/evidence/CHANGELOG.md b/products/evidence/CHANGELOG.md index 9eb50e3ad..d539518b1 100644 --- a/products/evidence/CHANGELOG.md +++ b/products/evidence/CHANGELOG.md @@ -2,6 +2,8 @@ ## Unreleased +## 0.41.0 - 2026-10-13 + - BREAKING: the published `registry-stack-client` Python package, which carries the Evidence client, requires Python 3.11 or later: its `Requires-Python` is `>=3.11` (was `>=3.10`), and its wheels are built against the Python 3.11 diff --git a/products/manifest/CHANGELOG.md b/products/manifest/CHANGELOG.md index 0bfb5d1d3..53f9710f7 100644 --- a/products/manifest/CHANGELOG.md +++ b/products/manifest/CHANGELOG.md @@ -7,6 +7,10 @@ This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.htm ## [Unreleased] +## [0.41.0] - 2026-10-13 + +- No user-visible product changes in this release. + ## [0.40.0] - 2026-10-11 ### Changed diff --git a/products/manifest/docs/release-notes.md b/products/manifest/docs/release-notes.md index a72cb85f2..84ee130db 100644 --- a/products/manifest/docs/release-notes.md +++ b/products/manifest/docs/release-notes.md @@ -2,6 +2,10 @@ ## Unreleased +## 0.41.0 + +- Registry Manifest has no user-visible changes in this release. + ## 0.40.0 - BREAKING: Registry Manifest reads metadata manifests and profile descriptors diff --git a/products/messaging/CHANGELOG.md b/products/messaging/CHANGELOG.md index 4cb897405..7126a6b2a 100644 --- a/products/messaging/CHANGELOG.md +++ b/products/messaging/CHANGELOG.md @@ -2,6 +2,8 @@ ## Unreleased +## 0.41.0 - 2026-10-13 + - BREAKING: the published `registry-stack-client` Python package, which carries the Registry Messaging client, requires Python 3.11 or later: its `Requires-Python` is `>=3.11` (was `>=3.10`), and its wheels are built diff --git a/products/platform/CHANGELOG.md b/products/platform/CHANGELOG.md index a08b4d6bb..19e2741a7 100644 --- a/products/platform/CHANGELOG.md +++ b/products/platform/CHANGELOG.md @@ -2,6 +2,8 @@ ## Unreleased +## 0.41.0 - 2026-10-13 + - `registry-platform-oidc` gains a `task_grant` module holding the exact task-grant status transport the Base Registry Engine and Scheduling share: `TaskGrantStatusEndpoint`, `TaskGrantStatusRegistry` (with an offline diff --git a/products/render/CHANGELOG.md b/products/render/CHANGELOG.md index 8ec55663a..60def6097 100644 --- a/products/render/CHANGELOG.md +++ b/products/render/CHANGELOG.md @@ -2,6 +2,10 @@ ## Unreleased +## 0.41.0 - 2026-10-13 + +- No user-visible product changes in this release. + ## v0.40.0 - 2026-10-11 - Runtime file flags use the help text "Runtime configuration file" and diff --git a/products/scheduling/CHANGELOG.md b/products/scheduling/CHANGELOG.md index 49f0f3402..08d735a2c 100644 --- a/products/scheduling/CHANGELOG.md +++ b/products/scheduling/CHANGELOG.md @@ -2,6 +2,8 @@ ## Unreleased +## 0.41.0 - 2026-10-13 + - BREAKING: the published `registry-stack-client` Python package, which carries the Registry Scheduling client, requires Python 3.11 or later: its `Requires-Python` is `>=3.11` (was `>=3.10`), and its wheels are built @@ -64,8 +66,9 @@ - BREAKING: a runtime file without `taskGrantStatus` is refused at startup with `scheduling.runtime.missing-task-grant-status`. v0.40.0 had no such member and accepted every unexpired task grant. A Casework immediate grant - never lasts longer than fifteen minutes, so the offline path refuses only a - deferred grant or a longer grant from another authority. After it acquires + never lasts longer than fifteen minutes. The offline path checks remaining + lifetime alone, so it also admits the final 900 seconds of a deferred grant + without checking revocation. After it acquires its locks, the capacity transaction rechecks the execution token's expiry as well as the grant's, on either path. Migration: list the task authorities under `taskGrantStatus`, or write diff --git a/release/manifests/registry-stack-beta-53.yaml b/release/manifests/registry-stack-beta-53.yaml new file mode 100644 index 000000000..e0bf68186 --- /dev/null +++ b/release/manifests/registry-stack-beta-53.yaml @@ -0,0 +1,48 @@ +stack: + release: beta-53 + version: 0.41.0 + source_repo: registrystack/registry-stack + source_tag: v0.41.0 + +artifacts: + registry-manifest: 0.41.0 + evidence: 0.41.0 + evidencectl: 0.41.0 + evidence-oid4vci: 0.41.0 + evidencectl-installer: 0.41.0 + registry-docs: 0.41.0 + discovery: 0.41.0 + discoveryctl: 0.41.0 + breg: 0.41.0 + bregctl: 0.41.0 + breg-mcp: 0.41.0 + breg-review: 0.41.0 + breg-installer: 0.41.0 + casework: 0.41.0 + caseworkctl: 0.41.0 + casework-installer: 0.41.0 + scheduling: 0.41.0 + schedulingctl: 0.41.0 + messaging: 0.41.0 + messagingctl: 0.41.0 + registry-render: 0.41.0 + registry-client-node: 0.41.0 + registry-client-python: 0.41.0 + +identifier_catalog: + path: products/identifiers/generated/catalog.v1.json + sha256: 17aa0bc6c94638e2b51393eac46ed6600c8af8e28c54c394a53154c5d99245d9 + entry_count: 241 + +external: {} + +warnings: + - code: client-runtime-floors + classification: breaking-change + detail: The unified clients require Node.js 24.11.0 or later and Python 3.11 or later. See release/notes/v0.41.0.md. + - code: task-grant-status-required + classification: breaking-change + detail: Scheduling runtime files require taskGrantStatus; BReg validates its entries when reading the file. Casework deferred grants and status failures require the configuration and client handling described in release/notes/v0.41.0.md. + - code: retired-compatibility-paths + classification: breaking-change + detail: Historical BReg state tolerance and Evidence, Casework, and Scheduling compatibility refusals are removed. Valid v0.40.0 state stays readable; command, diagnostic, and Rust API changes are listed in release/notes/v0.41.0.md. diff --git a/release/notes/v0.41.0.md b/release/notes/v0.41.0.md new file mode 100644 index 000000000..40bd2d642 --- /dev/null +++ b/release/notes/v0.41.0.md @@ -0,0 +1,320 @@ +# Registry Stack v0.41.0 + +Registry Stack v0.41.0 is the beta-53 release. It adds deferred Casework task +grants, fresh task-grant status checks in Scheduling, and original-receipt +reads in Scheduling and Messaging. Base Registry Engine clients accept +additive metadata and unknown Problem codes without granting unsupported +authority, and local BReg and Casework tooling agrees on principal claims. +The release also carries a native citizen self-registration and enrollment +acceptance project, lowers the standalone Linux glibc floor to 2.34, and moves +the client runtime floors to Node.js 24.11.0 and Python 3.11. + +## Compatibility and upgrade + +Use matching v0.41.0 runtimes, tools, and clients. This release reads state +v0.40.0 wrote; it does not restore an in-place path from an earlier release. +Back up databases, configuration, packages, keys, and audit streams before +upgrading, and preserve the same audit files. Follow +[upgrade and retire](https://docs.registrystack.org/operate/advanced/upgrade-and-retire/). +No migration tooling for older releases is provided. + +The entries below cover every BREAKING item since v0.40.0 in the +[product changelogs](https://github.com/registrystack/registry-stack/tree/v0.41.0/products). +The shared client floors apply to the BReg, Casework, Discovery, Evidence, +Messaging, and Scheduling namespaces of the unified packages. + +### Client runtime floors and Rust matches + +- BREAKING: `registry-stack-client` requires Python 3.11 or later, replacing + Python 3.10. `Requires-Python` is `>=3.11`, and the wheels use the Python + 3.11 stable ABI, `cp311-abi3`, replacing `cp310-abi3`. Upgrade the application + interpreter before installing the client and update any wheel filename + pinned in installation automation. Evidence development wheels have the + same floor; `editors/configure.py` also requires Python 3.11 or later. +- BREAKING: `@registrystack/client` and its three platform packages require + Node.js 24.11.0 or later, replacing Node.js 22.12.0. Move applications to + Node.js 24 LTS before upgrading the client. `editors/install.sh vscode` + likewise requires Node.js 24 or later to package the extension. +- BREAKING (Rust API): Scheduling and Messaging each add + `ProblemCode::ReceiptUnresolved` to an enum that is not `#[non_exhaustive]`. + Add a `ReceiptUnresolved` arm or a wildcard arm to exhaustive matches on + `registry_scheduling_core::ProblemCode` and + `registry_messaging_core::ProblemCode`, including their client re-exports + and the codes carried by client errors. + +### Task grants and current authority + +- BREAKING: Scheduling refuses a runtime file without top-level + `taskGrantStatus` as `scheduling.runtime.missing-task-grant-status`. + Every v0.40.0 runtime file needs this addition. Configure a list of one to + 32 task authorities, matched by the exact `sourceIssuer` in their grants, + for fresh status before every capacity commitment and idempotent replay. + There is no fallback: inactive, mismatched, unlisted, or incompletely bound + grants answer `403 operation.not-authorized`; an authority or credential + outage answers `503 service.unavailable`. Alternatively, explicitly set + `taskGrantStatus: unchecked-final-fifteen-minutes`. That choice performs no + revocation check and accepts only a grant with at most 900 seconds remaining + when the request enters. It checks remaining time, not the original grant + mode, so it also admits the final 900 seconds of an originally deferred grant + without checking revocation. Select this option only if that stale-authority + window is acceptable; configure authorities when current status is required. + An empty list is refused. See the complete + [Scheduling runtime configuration](https://github.com/registrystack/registry-stack/blob/v0.41.0/products/scheduling/RUNTIME-CONFIG.md). +- BREAKING: BReg treats a 401 or 403 from a task-grant status endpoint as an + outage, answering `503 service.unavailable` instead of + `412 precondition.failed`. A 404 still refuses the grant with + `precondition.failed`. Update alerts for a misconfigured or revoked status + credential and recognize the shared `registry-task-status` user agent in + Casework access logs, replacing `registry-breg-task-status`. The shared + transport bounds an attempt at ten seconds; BReg's five-second outer bound + still ends its check first. +- BREAKING: BReg validates each `taskGrantStatus` entry when reading the + runtime file. Invalid entries report `breg.runtime.invalid-task-grant-status` + at `/taskGrantStatus`, replacing activation-time + `breg.runtime.invalid-binding`. No already activated valid entry needs + editing. Update scripts that match the old diagnostic. `tokenEndpoint` is + typed as a URL; `clientId`, `clientAssertionAudience`, and `caseworkResource` + are external identifiers of 1 to 512 characters without control characters, + and `caseworkResource` is an absolute resource URI. `sourceIssuer` accepts + an absolute URN as well as a URL because the issuer is compared, not fetched. +- BREAKING: the Rust `CaseworkTaskAssertionSource`, also re-exported by the + unified client, classifies a Casework 4xx assertion response other than 408 + and 429 as `TokenError::Invalid`, kind `invalid-credential`, instead of + `unavailable`. This includes expired, revoked, or absent grants even if the + Problem body is malformed. Request a new approval and stop retrying that + credential. Responses 408, 429, and 5xx remain `unavailable`; transport + failures retain their transport kind. Assertion requests are still sent once. + +Casework task templates can opt into `authorizationMode: deferred`, with a +maximum `lifetimeSeconds` of 604800, or seven days. Omitted mode remains +`immediate`, with its 900-second ceiling. Deferred review grants pin the +assignment generation: release, reassignment, queue movement, absence-cover +change, decision, or completion ends the grant; reclaiming the task does not +revive it. Draft changes alone do not end it. Deferred templates cannot carry +Evidence bounds and are refused as `casework.task-template.deferred-evidence`. +Approval still names the template id and version; the preview, grant view, and +clients carry the mode and omit it for immediate grants. + +Apply Casework migration 0022 through `caseworkctl plan` and `caseworkctl apply`. +It replaces the two task-grant expiry constraints, adds the review task's +`assignment_generation` column and its update trigger, and validates three +tables under an exclusive lock without rewriting them. Allow for that lock +when choosing the upgrade window. + +BReg and Scheduling use the shared `TaskGrantStatusConfig` block in +`registry-platform-config` and status transport in `registry-platform-oidc`. +The optional `statusScope` and `statusPath` default to +`casework:grants:status` and `/v1/task-grants/{grantId}/status`. Set them only +for an authority with another scope or route. `statusScope` is one scope token; +`statusPath` starts with `/` and contains exactly one whole `{grantId}` segment. +Direct Rust consumers can map the shared block to `TaskGrantStatusEndpoint` +with `From` and validate its configuration without reading secrets or making +network requests. Product authorization and capacity ownership remain separate. + +### Base Registry Engine historical state + +- BREAKING: revision detail reads and list pages no longer read a revision + journaled under an immediate action's effect identifier. They answer + `503 source.unavailable`, even if the active package still declares that + effect. Only v0.38.0 and earlier wrote this provenance; subsequent releases + journal the entity's canonical operation identifier, such as + `records.person.create`. A database a v0.40.0 apply created needs no action. + Earlier revision rows are not read in place: apply to a new database, as + v0.40.0 already required. +- BREAKING: startup no longer verifies or serves a database without subject + access-log storage. Every apply from v0.38.0 onward installs that storage + whether or not the package declares `accessLog`, so a database v0.40.0 + created needs no action. Refusal occurs before listener binding and writes + nothing. Separate-role deployments report missing runtime-role grants; + single-role deployments report that the database is not ready for the + package. A database last applied before v0.38.0 requires a new database, + as v0.40.0 already required. + +### Retired command and compatibility paths + +- BREAKING: `evidencectl build` is now an unknown command, reported as + `evidencectl.usage` with exit 2 rather than `evidence.build.retired` with + exit 1. Replace it with `evidencectl package PROJECT --target TARGET + --output OUTPUT`. `evidencectl init` and `evidencectl new` also refuse + `--generate-keys` as a usage error. Remove the flag; it previously did + nothing, and local projects still generate their disposable keys. +- BREAKING: `casework migrate` and `caseworkctl db` are unknown subcommands + with exit 2 and no dedicated replacement sentence. JSON automation sees + `usage.invalid` instead of `usage.removed-command`. Use + `caseworkctl plan --runtime-config FILE` followed by + `caseworkctl apply --runtime-config FILE`. v0.40.0 already refused both + commands, so no successful v0.40.0 invocation changes. +- BREAKING: Casework removes `casework.package.retired-manifest`. A package + containing `casework.package.json` reports `casework.package.invalid` + when that file is unlisted, or `casework.package.unexpected-contents` when + `SHA256SUMS` lists it. An incorrect `package.expectedDigest` is reported + first as `casework.package.digest-mismatch`. Rebuild affected packages with + `caseworkctl package`. v0.40.0 already refused these retired packages. +- BREAKING: `caseworkctl dev` refuses to remove an unlabeled database volume, + even when the session's own container mounts it. Every v0.40.0 session labels + its volume, so those sessions need no change. If retaining an older unlabeled + `casework-dev-` volume, inspect and back up its contents before + removing it yourself with `docker volume rm`; removal destroys its data. +- BREAKING: the Casework BReg source adapter refuses a stored discovery cursor + that is a bare continuation without its request entity. Every cursor + v0.40.0 stored names that entity, so a v0.40.0 database needs no action. +- BREAKING: Scheduling removes three dedicated historical refusals. No input + v0.40.0 wrote or accepted is affected, and those older inputs remain refused: + - `scheduling migrate` is an unknown subcommand with exit 2. Activate with + `schedulingctl plan --runtime-config FILE` and + `schedulingctl apply --runtime-config FILE`; start with `scheduling serve`. + - A retired `scheduling.package.json` reports `scheduling.package.invalid` + at `/package/root` when unlisted, or + `scheduling.package.unexpected-contents` when listed in `SHA256SUMS`, + replacing `scheduling.package.retired-manifest`. Digest mismatch is still + checked first. Rebuild with `schedulingctl package`. + - A retained pre-v0.40 policy whose identity is under `scheduling` instead + of `project` reports `schedulingctl.store-unavailable`, exit 3, replacing + `schedulingctl.activation.earlier-release`. Start with a new database, + run `schedulingctl apply --runtime-config FILE`, then + `schedulingctl records apply --runtime-config FILE RECORDS`. + Direct Rust consumers must remove uses of `RuntimeError::RemovedCommand`, + `RuntimeError::exit_code`, `runtime::removed_command_refusal`, + `RuntimeConfigError::RetiredPackageManifest`, + `config::RETIRED_PACKAGE_MANIFEST_FILE`, and `StoreError::EarlierRelease`. + `schedulingctl plan` performs its read-only publication check only when no + schema version is pending; a v0.40.0-activated database has none pending. + +### Local BReg and Casework workflows + +- BREAKING: five `caseworkctl dev` configuration refusals now exit 1 instead + of 3 and report their own codes instead of `caseworkctl.operational-failure`: + `caseworkctl.dev.integrations-invalid`, + `caseworkctl.dev.shared-client-mismatch`, + `caseworkctl.dev.shared-task-authority-mismatch`, + `caseworkctl.dev.source-binding-invalid`, and + `caseworkctl.dev.borrowed-principal-invalid`. Update automation to inspect + exit 1 and the specific code. These configurations already failed before. +- BREAKING: a Casework development session borrowing another project's issuer + refuses a Casework access profile with `principalClaim: sub` as + `caseworkctl.dev.borrowed-principal-invalid`. In that session, `sub` is the + issuer owner's subject rather than the Casework principal. Use a stable + claim such as `registry_principal` in every Casework access profile and + register it for each client in both projects' `dev-clients.yaml`. + +`caseworkctl source add` now derives the generated `casework-reader` profile's +principal claim through same-version `bregctl explain access`, preserves exact +`testBindings` variants, and infers only a default service client as executor. +For a BReg project using `sub`, its generated reader relies on the issuer's +verified subject. Align an earlier generated `casework-reader` profile and every +entity profile and action grant, including module contributions, to one +`principalClaim`, then repeat `source add`. Mixed principal claims are refused +before files are written. The local human reviewer bridge still uses +`registry_principal`. Equivalent review endpoint spellings, including trailing +slashes, retain their authored form when they resolve to the same API. + +`bregctl dev` writes the compiled project's one principal claim into +`authentication.authorityClaims.principal` and includes +`authentication.authorityClaims.purpose: registry_purpose` only if a profile +requires purpose. Projects with no authenticated grant retain +`registry_principal`. It refuses incompatible claim mappings before retaining +first-start state. Use one principal claim that is neither `scope` nor the +purpose claim. Operated runtimes continue to configure these claims explicitly. +Local fixtures under a `sub` profile may use +`claims: {principal: "$localClientSubject"}` in their captured journey. +Local client files can also declare up to eight `taskGrantStatus` services and +machine-client grants for up to seven other audiences without expanding BReg +admission. + +## Original receipts and client compatibility + +Scheduling's `POST /v1/appointments/receipt` and Messaging's +`POST /v1/messages/receipt` recover the retained original success receipt using +the original `Idempotency-Key`, request body, and verified caller identity under +current ordinary read authority. They never repeat the mutation or claim +capacity. Scheduling can observe the outcome after the task grant ends; +Messaging neither spends nor requires the submission rate budget and never +answers 429 on this route. A missing, expired, changed, or refused receipt +answers `409 receipt.unresolved`, which does not prove that no effect occurred. +Rust, Node.js, and Python clients expose `appointment_receipt`, +`appointmentReceipt`, `message_receipt`, and `messageReceipt` in their language's +convention. Continue recovery before attempting a distinct write. + +BReg Rust, Node.js, and Python clients ignore unknown object members after +duplicate checks, retain strict checks for known fields, and disable only +bindings whose required capabilities they do not understand. Unsupported +statistical datasets, descriptive change-request capabilities, selectors, and +spatial capabilities are omitted individually; an unknown temporal mode keeps +its served descriptor because null already means non-temporal. Tombstone, +batch, and lifecycle selection can report `required-capability` instead of +`contract-mismatch`. Valid unknown Problem codes retain HTTP status and trace +ID without inferred code or extension semantics; malformed envelopes remain +protocol errors. Fixed actions also accept omitted optional reference inputs +on create and patch while still checking supplied references and required +inputs. + +## Linux installation and build tooling + +Standalone Linux binaries now require glibc 2.34 or later, lowered from 2.35, +for the RHEL 9 family and Amazon Linux 2023. Both Linux architectures use the +same Zig floor selection and independent ELF-symbol check. Native Node.js and +Python client artifacts keep their separate glibc 2.17 contract; the standalone +floor does not change that contract. + +The BReg, Casework, Scheduling, and Evidence installers start every staged Linux +binary with `--version` before selecting the new toolset. If any binary cannot +start, installation refuses that release and keeps the earlier toolset selected. +This also catches an installer asked to install an older release whose binaries +require a newer glibc than the host supplies. + +Workflow `actions/setup-go` steps install Go 1.27.2, replacing 1.24.4, for +AWS-LC-FIPS source builds. Go is a build tool, not a shipped runtime or adopter +prerequisite. The canonical +Linux builder still installs its snapshot-pinned Debian Go package; this release +does not change that recipe. Linux arm64 builds now select the same hash-pinned +Zig toolchain and glibc floor on Ubuntu 24.04 as the canonical amd64 build. + +BReg, Casework, and Messaging local development pull digest-identical PostgreSQL images +from `public.ecr.aws/docker/library/postgres`. Messaging also pulls Mailpit +from `ghcr.io/axllent/mailpit`. Update development egress allowlists for +`public.ecr.aws` and, for Messaging, `ghcr.io`. Retained BReg and Casework +containers using the earlier Docker Hub reference at the same digest remain +accepted; PostGIS sessions still use `postgis/postgis` on Docker Hub. + +## Acceptance projects and release operation + +The citizen self-registration acceptance project combines native ThunderID SMS +signup, account-owned applications, Casework review, and transactional Person +creation, account linking, and program enrollment through configured BReg +actions. It is an adopter proof using the products' existing boundaries, not a +built-in business model or a new runtime product. + +Publication now refuses to create the numbered tag until `registrystack-id` +main pins the exact release source and identifier catalog SHA-256. The release +still rebuilds its own candidate; nightly builds do not substitute for it. +The predecessor-state rehearsal covers BReg, Casework, Evidence, and Messaging +from v0.40.0. Scheduling state remains outside that rehearsal. + +Solmara Lab adaptation to the breaking changes is deferred. The approved 1.0 +stability promise is unchanged and does not take effect in this pre-1.0 release. + +## Security review notes + +The product-owned review notes cover fresh authority checks, deferred grant +invalidation, original receipt disclosure, principal mapping, and historical +state refusal: + +- [BReg](https://github.com/registrystack/registry-stack/blob/v0.41.0/products/breg/SECURITY-REVIEW-NOTES.md) +- [Casework](https://github.com/registrystack/registry-stack/blob/v0.41.0/products/casework/SECURITY-REVIEW-NOTES.md) +- [Scheduling](https://github.com/registrystack/registry-stack/blob/v0.41.0/products/scheduling/SECURITY-REVIEW-NOTES.md) +- [Messaging](https://github.com/registrystack/registry-stack/blob/v0.41.0/products/messaging/SECURITY-REVIEW-NOTES.md) + +The dependency policy also records the unsafe-libyaml advisory in the pinned +Typst tree with its scoped review triggers. Release image advisory exceptions +remain subject to exact-image evidence, their existing expiry, and candidate +enforcement. No advisory bypass is introduced by release preparation. + +## Support + +Security fixes ship in the latest v0.x release. Earlier minor releases receive +no backports, and v0.41.0 has no fixed-duration support window. Release +preparation requires more than six months of remaining upstream support for +pinned LTS dependencies, including compatibility smoke platforms. + +[Changes since v0.40.0](https://github.com/registrystack/registry-stack/compare/v0.40.0...v0.41.0). +This is a pre-1.0 Beta release for self-hosted institutional pilots.