NK-WP-0056: split T14 into T14 (service-client case type), T18 (executor approval client), T19 (real-service exercise)
All checks were successful
CI Smoke / host-smoke (push) Successful in 0s
CI Smoke / container-smoke (push) Successful in 1s

Founder decision 2026-10-31. T14 in progress. T06 depends on T18 and T19.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

Assistant: claude-code
Assistant-Model: opus
Assistant-Process: 5502@bnt-lap001
Assistant-Session: 68b3b02f-5d0f-4e71-8421-796f62e50196
This commit is contained in:
tegwick 2026-10-31 21:20:40 +01:00
parent b76456134c
commit 7b0a885137
2 changed files with 62 additions and 25 deletions

View file

@ -356,10 +356,12 @@
| task | NK-WP-0056-T11 | done | — | workplans/NK-WP-0056-bounded-executor-path.md |
| task | NK-WP-0056-T12 | done | — | workplans/NK-WP-0056-bounded-executor-path.md |
| task | NK-WP-0056-T13 | done | — | workplans/NK-WP-0056-bounded-executor-path.md |
| task | NK-WP-0056-T14 | todo | — | workplans/NK-WP-0056-bounded-executor-path.md |
| task | NK-WP-0056-T14 | progress | — | workplans/NK-WP-0056-bounded-executor-path.md |
| task | NK-WP-0056-T15 | todo | — | workplans/NK-WP-0056-bounded-executor-path.md |
| task | NK-WP-0056-T16 | wait | — | workplans/NK-WP-0056-bounded-executor-path.md |
| task | NK-WP-0056-T17 | done | — | workplans/NK-WP-0056-bounded-executor-path.md |
| task | NK-WP-0056-T18 | todo | — | workplans/NK-WP-0056-bounded-executor-path.md |
| task | NK-WP-0056-T19 | todo | — | workplans/NK-WP-0056-bounded-executor-path.md |
| intake | NK-IN-0001 | closed | blue | docs/intakes/activity-core-ops-sso-operators.md |
| intake | NK-IN-0002 | closed | blue | docs/intakes/activity-core-ops-sso-operators.md |
| intake | NET-IN-0001 | open | — | intakes/intakes.md |

View file

@ -694,11 +694,11 @@ Follow-up 2026-10-31 for T10/T06 reachability:
- audit-core has no ingress from `sso`.
- Both owners were asked for pod-scoped rules; see the rapp's `docs/platform-handoffs.md`.
## Executor approval identity and request phase
## Executor approval identity: service-client case type
```task
id: NK-WP-0056-T14
status: todo
status: progress
priority: high
assignee: claude-code
depends_on: [NK-WP-0056-T13]
@ -707,32 +707,67 @@ state_hub_task_id: "ec87ed9f-9604-5843-af08-bc771a58712d"
approval-engine only accepts an approval request whose `binding.actor` equals the caller's KeyCape token subject
(approval-engine `docs/bounded-execution-admission-carrier.md`). The executor therefore files its own request, the
founder approves it, and the executor then consumes it. Needed:
founder approves it, and the executor consumes it. For that it needs its own KeyCape confidential client.
- KeyCape confidential client `nk-bind-executor-approval`:
- `client_credentials` grant, audience `approval-engine`;
- scopes `approval:create`, `approval:read` and `approval:consume`;
- subject `service:nk-bind-executor`, tenant `tenant:platform`, tokens of at most 15m;
- prepared as a security case and client file, like the T09 journey client.
- Its client secret in OpenBao, through a railiance-platform CCR with a third executor read role (one role per
lane), instead of a stored bearer.
- Executor code:
- a fresh token exchange per approval call (as secrets-engine does);
- a `request` phase that creates the approval (`action: bounded-execution`, target admission id and digest,
`human_control: true`, `pdp_path: false`) and prints its id;
- the existing run phase then consumes it.
KeyCape has no generic service-client registration. Each existing client was registered by its own script
(`approval-clients-rollout.py`, `secrets-engine-openbao-client-rollout.py`). The canon route is a new security case
type, `oidc-service-client` 0.1, next to `oidc-browser-relying-party`:
**2026-10-31:** T17 showed that the founder cannot be presented an executor-filed approval today. The founder asked
for an alignment review of informed-decision, approval-engine and State Hub decisions
([review](../docs/proposals/2026-10-31-decision-services-alignment-review.md)). T14's request phase follows its
"present an existing approval" contract (S1 informed-decision, S2 here).
- `client_credentials` grant, resource audience, service subject, tenant, roles, scopes, a token lifetime of at most
15m;
- the client secret minted straight into OpenBao custody, readable only by KeyCape and the consuming service;
- `keycape-client.py` support for building the client from such a case;
- the first case: `nk-bind-executor-approval` (audience `approval-engine`; scopes `approval:create`,
`approval:read` and `approval:consume`; subject `service:nk-bind-executor`; tenant `tenant:platform`).
The split of T14 into T14, T18 and T19 is a founder decision (2026-10-31).
**Done when:**
- the client and the CCR are prepared;
- the request phase is tested against approval-engine's real source with synthetic KeyCape keys (the
secrets-engine exercise pattern);
- nothing is applied without founder approval.
- the type, its tests and the first case validate;
- `keycape-client.py` renders the service client and is tested;
- an acknowledgement packet is ready for the founder.
Nothing is applied.
## Executor approval client and request phase
```task
id: NK-WP-0056-T18
status: todo
priority: high
assignee: claude-code
depends_on: [NK-WP-0056-T14]
```
Executor code:
- a fresh KeyCape token exchange per approval call (as secrets-engine does), with the client secret read through
an executor OpenBao lane (the case's custody);
- a `request` phase that creates the approval (`action: bounded-execution`, target admission id and digest,
`human_control: true`, `pdp_path: false`) and prints its id;
- the existing run phase then consumes it.
Presenting the approval to the founder follows the alignment review's "present an existing approval" contract
([review](../docs/proposals/2026-10-31-decision-services-alignment-review.md), S1 informed-decision).
**Done when:** the request and run phases are tested on fakes, and the new image is pinned.
## Executor approval exercise against the real services
```task
id: NK-WP-0056-T19
status: todo
priority: medium
assignee: claude-code
depends_on: [NK-WP-0056-T18]
```
Run create, approve, consume, idempotent retry, a different digest, revoke-before-consume and a wrong scope against
approval-engine's real source and KeyCape's pinned image with synthetic keys (secrets-engine
`tools/exercise_approval_identity.py` pattern). Value-free receipt.
**Done when:** the exercise passes and its receipt is recorded.
## Executor audit sender
@ -817,7 +852,7 @@ priority: high
assignee: claude-code
needs_human: true
intervention_note: "Founder signs the admission for the single live pilot rotation."
depends_on: [NK-WP-0056-T01, NK-WP-0056-T03, NK-WP-0056-T04, NK-WP-0056-T05, NK-WP-0056-T10, NK-WP-0056-T13, NK-WP-0056-T14, NK-WP-0056-T15, NK-WP-0056-T16, NK-WP-0056-T17]
depends_on: [NK-WP-0056-T01, NK-WP-0056-T03, NK-WP-0056-T04, NK-WP-0056-T05, NK-WP-0056-T10, NK-WP-0056-T13, NK-WP-0056-T14, NK-WP-0056-T15, NK-WP-0056-T16, NK-WP-0056-T17, NK-WP-0056-T18, NK-WP-0056-T19]
state_hub_task_id: "6c3939f8-23a9-5f70-a3b1-94f4b291706b"
```