informed-decision/workplans/INFD-WP-0001-founding-specs-and-approver-ui-ownership.md
tegwick ee2cca579c Establish INTENT, Stage 1 GOAL, and founding workplan
Claim ownership of the browser-facing approver UI that approval-engine
deliberately does not contain. approval-engine's INTENT names an approvals
inbox under Non-Goals, and docs/keycape-service-registrations.md records that
the human approver client's client_id and callback URI "must come from its
owner once it exists" — leaving key-cape's KEY-WP-0013-T02 blocked on an
unassigned component.

- INTENT.md: Decision Memo concept, the binding/awareness split and the two
  hashes, ownership and non-ownership against the named estate repositories,
  and a provisional PEP-shaped layer placement flagged for a gate-house ruling
  rather than asserted.
- GOAL.md: Stage 1 is the L3 approval approver surface — the narrowest real
  consumer with a live blocking dependency — plus the written answer to who
  owns the approver UI.
- workplans/INFD-WP-0001: founding documents, the gate-house layer/ownership
  ruling, the four specs (PRD, UseCaseCatalog, ArchitectureBlueprint,
  EvidenceModel), schema and canonicalizer promotion out of history/ with the
  isolation vectors under test, the key-cape client registration, and a
  walking skeleton that includes return and discuss.

history/ is preserved unmodified as provenance.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01V3W1dQG7GFFM9d94jFx7iR

Assistant: claude-code
Assistant-Model: opus
Assistant-Process: 1565372@bnt-lap001
Assistant-Session: 16bb2f25-b34c-49ef-8e94-5fec3567a568
2026-09-09 10:47:36 +02:00

13 KiB
Raw Blame History

id type title domain repo status owner topic_slug created updated origin origin_ref
INFD-WP-0001 workplan Founding specs and approver-UI ownership infotech informed-decision proposed claude netkingdom 2026-09-09 2026-09-09 founding history/20260909-initial-exploration/InitialExploration.md

INFD-WP-0001 — Founding specs and approver-UI ownership

Establish informed-decision as a governed repository in the NetKingdom estate, settle who owns the browser-facing approver UI that approval-engine deliberately does not contain, and produce the specification set that Stage 1 implementation will be built against.

The trigger is concrete and dated. On 2026-09-08 key-cape (KEY-WP-0013-T02) asked approval-engine for the human approver client's client_id and callback URI. approval-engine correctly declined to invent them and recorded in docs/keycape-service-registrations.md that the human approver flow "belongs to whichever browser-facing approver UI presents approval:approve tokens to this engine. That component is not in this repo." APPROVAL-WP-0002-T01 remains progress partly because of it. This workplan closes that gap by naming the owner and shipping the contract.

Status is proposed, pending review against the current approval-engine, access-engine, key-cape, gate-house and audit-core contracts, and against the deployment estate. T02 is the gate: if gate-house places this component differently, T03T05 are rewritten before they are written.

Scope boundary for this workplan: specification and contract, plus one walking skeleton. Full L3 product build is residual and belongs to INFD-WP-0002.

Establish the founding documents

id: INFD-WP-0001-T01
status: done
priority: high

Write the repository's stable statements of purpose and current stage, derived from the founding exploration rather than reinvented.

Acceptance: INTENT.md states purpose, the Decision Memo concept, ownership and non-ownership against the named estate repositories, design principles, wrongness conditions and success criteria; GOAL.md states the Stage 1 outcome, exclusions, invariants and definition of done; README.md orients a new reader in under a minute; history/20260909-initial-exploration/ is preserved unmodified as the provenance record.

Completed 2026-09-09: INTENT.md, GOAL.md and README.md written. SCOPE.md is deliberately deferred to T06 — a scope file written before the layer ruling and the specs would describe an imagined boundary, which is the drift SCOPE.md exists to prevent.

Settle layer placement and approver-UI ownership with gate-house

id: INFD-WP-0001-T02
status: todo
priority: high

Take the ownership question to gate-house as doctrine rather than asserting a catalog row. The proposal to argue: informed-decision owns the browser-facing approver surface, the presentation record and the evidence of informedness; it is PEP-shaped under statute §6.4 and companion §5 because it is browser-facing and causes a protected side effect on the far side of a decision; it supplies exactly one PIP-like fact — what was presented — as a claim, and never evaluates it.

Raise explicitly, and do not paper over:

  • §17 has no request-claim schema owner assigned. A view_hash-bearing presentation claim must yield to that schema when it exists rather than inventing a permanent local shape.
  • approval-engine's claim already carries "a digest over the same canonical binding the decision point already computes". Whether view_hash is that digest, a sibling of it, or a distinct presentation attestation is a real question and the wrong answer creates two competing canonicalizations of the same act. This is the single highest-risk unknown in the workplan.
  • A surface that renders both the question and the answer is adjacent to the self-dealing objection that kept the object out of access-engine. State why it is not the same failure: this repository holds no state a decision reads as authority.

Acceptance: an intake is filed with gate-house; a ruling or a recorded decision exists; layer.yaml is written from the ruling and matches the catalog row, not this workplan's prose; INTENT.md and GOAL.md are amended if the ruling differs from the proposal; the view_hash-versus-binding-digest relationship is recorded as a decision, not left implicit. Blocking for T05 and T07.

Product Requirements Document

id: INFD-WP-0001-T03
status: todo
priority: high

Write docs/specs/ProductRequirementsDocument.md for Stage 1: the L3 approval approver surface, scoped to one real consumer.

Must cover: the personas (approver holding a mandate, requester, observer/auditor); the disposition vocabulary and which verbs are legal on which step kinds; the required-highlight acknowledgment gate; the pre-sign/awareness split as it appears in the UI; the evidence bundle as an export; accessibility and locale (DE/EN, given the Umlaufmappe framing); and the explicit non-requirements from GOAL.md — no mandate graph, no QES, no notification transport.

State the anti-requirements as first-class: no dark patterns, no dwell timers, no keystroke analytics, and a UI that makes unmistakable that the whole instrument is bound rather than only the acknowledged highlights.

Acceptance: every requirement traces to either a GOAL.md definition-of-done item or a named external contract; each requirement is testable; the document names what it is deliberately not requiring and why.

Use Case Catalog

id: INFD-WP-0001-T04
status: todo
priority: medium

Write docs/specs/UseCaseCatalog.md covering the full depth spectrum L0L5, with Stage 1 scope marked, so that scale invariance is testable as a design property rather than a claim in a vision statement.

For each level: actor, trigger, requested act, binding level, the verbs that must be available, the evidence produced, and the estate repository that is the counterparty. Include the L0 login banner and the L2 ADR accept in full even though they are out of Stage 1 build scope — their purpose here is to constrain the schema so the object cannot fork later.

Include the negative cases: accept on a Kenntnisnahme step (illegal by design), a bind attempt with unacknowledged required highlights, an agent attempting a disposition, and a tenant switch requiring a new bind.

Acceptance: every use case maps onto the single Decision Memo schema with no level-specific object; each negative case names the invariant it protects; the catalog states for each level which estate repository would consume it.

Architecture Blueprint

id: INFD-WP-0001-T05
status: todo
priority: high

Write docs/specs/ArchitectureBlueprint.md. Depends on T02 — the layer ruling determines what this component is permitted to be.

Must cover: the component boundary and its position in the security layer model; the call graph to key-cape (OIDC authorization-code + PKCE for humans), approval-engine (bearer approval:approve, never approval:consume), access-engine (decision, never rendered here) and audit-core (evidence emission); the storage posture for memos, presentations and dispositions; the deployment shape including the Ingress and external origin that approval-engine explicitly does not have; and the failure modes — what the surface does when approval-engine, key-cape or audit-core is unavailable.

Fail-closed is the default and must be stated per dependency. A surface that degrades into showing a memo it cannot bind is acceptable; a surface that degrades into binding without evidence is not.

Acceptance: no component in the diagram renders an authorization decision; the token audiences, scopes and principal types match approval-engine's docs/keycape-service-registrations.md exactly; every external dependency has a stated unavailable-stance; the blueprint names which parts are Stage 1 and which are placeholders.

Evidence model, schema promotion and canonicalization under test

id: INFD-WP-0001-T06
status: todo
priority: high

Promote the exploration artifacts from history/ into governed, tested repository assets, and write docs/specs/EvidenceModel.md.

Move decision-memo.schema.json to schemas/, canonicalize.py into the package, and the fixtures in vectors/ into the test suite. history/ stays untouched as provenance; the governed copies are the ones that change.

The four isolation properties from the exploration become tests that must stay green:

  1. shuffling object keys does not change either hash;
  2. editing an awareness field does not change view_hash;
  3. changing binding.target does change view_hash;
  4. selecting a role after login emits session.hat_selected and does not rewrite view_hash.

EvidenceModel.md covers what an evidence bundle contains, how it verifies offline, its relationship to audit-core's archive, and — carried over from approval-engine's reasoning rather than rediscovered — the honest statement that a hash chain proves records were not altered after arrival and cannot prove a record was never sent.

Write SCOPE.md as the last step of this task, once the layer ruling and the specs have fixed the real boundary.

Acceptance: schema, canonicalizer and vectors live outside history/ and are exercised in CI; the three published expected hashes reproduce byte-for-byte; EvidenceModel.md states the residual it does not close; SCOPE.md exists and describes the implemented-and-first-cut boundary, not the aspiration.

Publish the OIDC browser-client contract to key-cape

id: INFD-WP-0001-T07
status: todo
priority: high

Own and publish the two strings approval-engine could not supply: the human approver client's client_id and its full callback URI. Depends on T02 for the ownership ruling and on T05 for the deployment origin.

The registration is an authorization-code + PKCE public or confidential browser client — not client_credentials — and the resulting access token must carry aud=approval-engine, principal_type: human, tenant: tenant:platform and scope approval:approve. Redirect URIs match exactly at /authorize, so the origin must be a real deployed origin, decided in T05, not a placeholder.

Do not request approval:consume: approval-engine refuses it for human principals, and consumption belongs to the PEP that causes the side effect.

Acceptance: docs/keycape-client-registration.md publishes both strings and the expected token shape; the contract is sent to key-cape referencing KEY-WP-0013-T02, and to approval-engine referencing its docs/keycape-service-registrations.md follow-up; a token issued against the registration is accepted by approval-engine's verifier; KEY-WP-0013-T02 is unblocked. This is the task that discharges the gap that created this repository.

Walking skeleton — one approval, end to end

id: INFD-WP-0001-T08
status: todo
priority: medium

Prove the specs against reality with the thinnest possible L3 path: sign in via key-cape, list approvals awaiting this principal from approval-engine, render one as a Decision Memo with brief, packet and highlights, acknowledge the required highlights, and submit an approval entry with a stored presentation record carrying view_hash.

return and discuss are in this skeleton, not deferred. They are the differentiator; a skeleton with only approve/reject proves the wrong product.

Acceptance: one approval is approved by a real human through this surface against a deployed approval-engine; the approval entry is reconstructable from a stored presentation; a bind attempt with unacknowledged required highlights fails closed; return produces a structured reason and is distinguishable from decline in the record; no code path in this repository evaluates whether the act is permitted.

Gated externally on approval-engine APPROVAL-WP-0002-T01 reaching done and on the service being deployed with an origin this surface can reach.

Known risks

  • T02 is a hard gate. Writing the blueprint before the layer ruling risks building a component the statute does not permit in that shape.
  • Two canonicalizations. If view_hash and approval-engine's binding digest are not reconciled in T02, the estate ends up with two hashes over the same act and no rule for which one is authoritative.
  • Deployment origin is on someone else's critical path. T07 cannot complete without a real external origin, and this repository does not yet own an Ingress. This is the most likely cause of slip.
  • Scope pressure toward an approvals inbox. The fastest way to close KEY-WP-0013-T02 is to build a queue with two buttons. That would satisfy the dependency and abandon the thesis. T04 exists to make the cost of that visible.