honker: PRD 1.8 draft r7 on r5 762a6711f (Jason Q191, mos-1149, sage-1623): the assistant and the chief of staff are separate roles and only the chief raises a grant request; REQ-GRANT-1 adds that no agent holds both; a note says what stops one holder claiming both at refactor 011d41ba6

This commit is contained in:
2026-10-20 20:10:08 -05:00
parent 762a6711ff
commit 47c2cb33c3
+29 -10
View File
@@ -13,12 +13,12 @@ notes N1 and N2 (duckworth-0058) on r2 at 60f5ca8fa, with Gizmoduck's enrollment
(gizmoduck-0067). Revision 4 makes Mos's rulings on duckworth-0057 (mos-1129, through Sage, sage-1538)
on r3 at d16ccdb91: only an Approve creates a grant, one decision for a grant that makes an account, and
the arbiter route for `host.sudo`. Revision 5 fixes two stale notes from Duckworth's r4 check
(duckworth-0061 N1), with no change to the requirement text.
(duckworth-0061 N1), with no change to the requirement text. Revision 7 is on r5 at 762a6711f, not r6
(Jason, Q191, through Mos mos-1149 and Sage sage-1623): the assistant and the chief of staff are separate
roles, and only the chief raises a grant request.
For Jason at approval: "The main agent or chief of staff" in Q10 is read as one role under two names,
the chief of staff. So only the chief raises a grant request, and your assistant passes your own request
to the chief. That reading is Mos's (mos-1124). To change it, say so when you approve, and REQ-GRANT-1
changes before the text goes into the PRD.
Only the chief of staff raises a grant request. The assistant, the user's main agent, never raises one.
It passes the user's request to the chief and can revoke a grant in its own organization.
Also for Jason at approval:
@@ -167,7 +167,8 @@ Under "Credentials", after REQ-CRED-3 (version 1.7):
> resolution covers the account and its credential, so the hard-waits list doesn't change. An
> `account.create` raise isn't a grant request and routes as version 1.7 has it. The broker checks
> only that the chief of staff raised the request. The chain of command before that is in the
> messaging lists and the role contracts, not a broker check.
> messaging lists and the role contracts, not a broker check. The assistant and the chief of staff are
> separate roles. No agent holds both, and the broker refuses a claim that would.
> - **REQ-GRANT-2.** The user approves or denies each grant request in the inbox. Approve is the only thing
> that creates a grant, and the code uses a grant only when it has a matching Approve record. No agent
> creates a grant. A grant written into the business file by hand makes nothing. Row 210's hand-written
@@ -289,10 +290,28 @@ Under "Risks and open questions", a new bullet:
- Which roles may request: Q188 says "Not all agents are capable or authorized to request directly. It
must follow the chain of command properly." The text makes the chief of staff the only role that raises,
the PM and the CTO ask it directly, and worker roles ask through their PM. Jason's words also name "the
main agent", but REQ-ASSIST-1 keeps the assistant out of directing agents, so it passes the user's
request to the chief rather than raising one. Mos accepted this (mos-1124 c) and reads "the main agent
or chief of staff" as one role under two names. That reading is Mos's, so the top of this draft puts it
to Jason at approval.
main agent". That is the assistant, a separate role from the chief of staff. Reading the two as one role
would give grant rights to both and overlap their authority (Jason, Q191). So the assistant never raises
a grant request: it passes the user's request to the chief (REQ-ASSIST-1) and can revoke a grant in its
own organization (REQ-GRANT-4). Jason accepted this at Q191 ("Q13: that looks better").
- What stops one holder claiming both roles today, at refactor 011d41ba6. Nothing names the pair. The
separation holds by construction, and no check or test asserts it:
- An instance has exactly one definition (`packages/business/src/business.mjs:118-120` in checkRoles).
An assistant is an instance of the definition `assistant` (`packages/business/src/vocabulary.mjs:134`)
and the chief of staff is an instance of `chief-of-staff` (`packages/bus/src/broker.mjs:164`, `:2137`).
- A run binds one instance. `bindLaunch` takes one `role` (`broker.mjs:451-456`), refuses a second bind of
the same run in the business (`duplicate-run`, `:479`), and refuses a rebind under another role
(`launch-record-mismatch`, `:499`). The launcher spawns one process per launch and binds it to one
instance (`packages/cli/src/launcher.mjs:438-449`).
- `role.claim` claims only the run's own bound role (`broker.mjs:1689-1734`). An assistant run claims its
thread in `thread_claims` and never writes `role_claims` (`:1693-1709`). The `role_one_holder` trigger
(`packages/bus/src/migrations/3b.sql:117-119`) allows one claim per role, and nothing limits the roles
one run holds, because a run has only one.
Not enforced: the run key is per business (`broker.mjs:478`), so nothing stops one run id being bound
in two businesses. Nothing ties two runs to two different processes or OS users beyond the launcher's
own record (the B7 residual). `credential.mint` is an action (`broker.mjs:34`) and a hard wait
(`:71`), but no check limits which role raises it. The landing step adds a broker refusal for a claim
that would put both roles on one holder, with a test for each path above.
- REQ-CRED-4 keeps row 210's conditions (origin/gizmoduck/row210-on-199-r2,
agents/gizmoduck/work/queue-210/DESIGN.md:376-392): the definition declares the kind, the grant names the
agent, an exact argv-prefix allowlist with wildcards refused, the key issued, and only a reviewed role