Skip to content

Add init-time full-permission consent, wired to every harness - #4

Merged
gurnben merged 1 commit into
mainfrom
feat/full-permission-consent
Oct 21, 2026
Merged

gurnben merged 1 commit into
mainfrom
feat/full-permission-consent

Conversation

@gurnben

@gurnben gurnben commented Oct 21, 2026

Copy link
Copy Markdown
Member

Summary

The traust skills cannot run headlessly without unattended tool use — every harness gates bash and file writes behind per-call approval an unattended run cannot answer, so scans died on the first permission request. This PR adds init-time consent and wires it to every harness:

  • Consent at init: a wizard question (explaining exactly what is granted and that the harness's skills require it) or --full-permission for headless installs; recorded in the workspace state and surfaced in doctor. Consent survives re-inits.
  • Per-run resolution: effective mode = per-run --unsafe-full-permission flag OR recorded consent. The resolution lives in the runner, so the SDK Provider path honors state consent too.
  • Per-harness translation:
    • claude: --dangerously-skip-permissions
    • crush session mode: POST /v1/workspaces/{id}/permissions/skip {"skip":true} (the server's yolo); run fallback: --yolo
    • codex: --dangerously-bypass-approvals-and-sandbox
    • pi: full builtin toolset via --tools (pi gates by tool declaration, not per-call approval)
  • Visibility: pre-run notes state the active mode, the run journal records unsafe_full_permission, and the needs-input failure message now points at traust-cli init / the per-run flag.
  • Without consent nothing changes: permission/question requests fail closed (exit 2) with guidance. S9 isolation, budget bands, spend accounting and run journals apply in both modes.

Verification

  • Live end to end: the previously permission-blocked smoke run now executes its tools and completes (exit 0, READY) with consent recorded; scoped runs still fail closed naming the tool.
  • New tests: crush serve client sets permissions/skip only under consent (and never in scoped mode), runner honors state consent (note + journal), --yolo and pi full-toolset argv construction.
  • Full suite with race detector, vet, staticcheck clean.

Note: consent was also recorded in the local deployment's state (~/.traust/cli/state.json) so the next real scan works immediately.

💘 Generated with Crush

The traust skills cannot run headlessly without unattended tool use:
every harness gates bash and file writes behind per-call approval that
an unattended run cannot answer, so scans died on the first permission
request. The harness itself expects yolo mode / dangerously-skip-
permissions class flags.

init now asks for consent once (a wizard question explaining exactly
what is granted, or --full-permission for headless installs) and records
it in the workspace state. Runs resolve the effective mode from the
per-run flag OR the recorded consent — the resolution lives in the
runner, so the SDK Provider path honors it too — and translate it into
the right switch per harness: claude
--dangerously-skip-permissions, crush --yolo on the run fallback and
the server's permissions/skip endpoint in session mode, codex
--dangerously-bypass-approvals-and-sandbox, and pi's full builtin
toolset. The mode is surfaced in the pre-run notes, the run journal and
doctor, and consent survives re-inits.

Without consent nothing changes: permission and question requests fail
closed (exit 2) with guidance pointing at init. S9 isolation, budget
bands, spend accounting and run journals apply in both modes.

Verified live end to end: the previously blocked smoke run now executes
its tools and completes (exit 0) with consent recorded; scoped runs
still fail closed. Unit and integration tests cover both modes across
the crush serve client, the runner consent resolution and the fallback
argv construction.

💘 Generated with Crush

Assisted-by: Crush:rits/zai-org/glm-5-3
@gurnben
gurnben requested a review from a team as a code owner October 21, 2026 13:19
@gurnben
gurnben merged commit 6858c53 into main Oct 21, 2026
2 checks passed
@gurnben
gurnben deleted the feat/full-permission-consent branch October 21, 2026 13:22
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant