Sanduq is a set of Spec Kit extensions that run on your machine, in your checkout, with your accounts. This page says what that means, what runs without asking, and how to report a problem.
- The repository is trusted. Running Sanduq in a repository runs that repository's code: hook
scripts under
.specify/, the policy in.specify/workflow.yml, commands it names, and the installed skills. Do not run Sanduq in a repository you would not runmakeornpm installin. - Issue authors are trusted, or named. Workflow reads GitHub issues and their comments as
work and as decisions. Restrict who can answer with
decisions.authorized_usersin.specify/workflow.yml(schemas); without it, every commenter is one. - The machine and the accounts are yours.
ghruns with your login; agents run with your file permissions. Nothing in Sanduq separates two users on one machine or one checkout.
- Hooks. The Workflow installer merges a PreToolUse guard into
.claude/settings.jsonand.codex/hooks.json; the extensions' lifecycle hooks run around Spec Kit commands (hooks reference). The guard is advisory: it sees only the host's shell tools (Bash,PowerShell, Codex's shell tool), so a script, an alias or another tool bypasses it, and a hook error allows the call (guard hook). - Policy commands.
ci.gate.verify_commandand the affected-check commands in.specify/workflow.ymlrun as written (operations). - The Progress statusline. When installed, it runs the status line command that was configured
before it, and only while
.specify/progress/config.jsonis untracked and still names the command the install recorded; a tracked file or a changed command is ignored with a line indiagnostics.log. - Install backups. Each apply writes
.specify/workflow/backups/*/before.zipwith the exact bytes of every file it may change, including.claude/settings.json,.codex/config.tomland.codex/hooks.json, which can carry MCP server keys. They are excluded from git in that clone only and travel with any copy of the folder.
Delegated work runs another agent CLI through the delegate-task driver
(delegation). Two modes exist:
- Bypass (
permission: bypass, the driver's default): the worker runs any command without asking, in your checkout. Every external launch Sanduq makes passes--clean-envwith an explicit--keep-envallowlist, so the worker sees runtime basics, its own harness credentials and theSANDUQ_*variables, not the rest of your environment. The ledger records the kept names, never values. - Sandbox (
--sandbox): review and analysis routes start read-only.
A task worker never receives the workflow claim token. accept, adopt, reassign and
trust-reset need a nonce kept under your home folder, outside every worker's checkout, and refuse a
process that descends from a live delegated run even with its SANDUQ_* variables removed. Both
stop a worker that uses only what it was given; neither stops a worker running as your OS user
that reads the nonce file or escapes its process tree
(residual risk).
Workers and the dispatcher share one checkout and one set of permissions. Receipts and the
delegation ledger are self-asserted, and the ledger's tamper markers detect accidental edits only
(review decision DEC-11); a worker that wants to lie can. The CI gate checks that receipts are
present, passing and current, and that each receipt is the one the dispatcher last logged in the
feature's receipt-log.jsonl, so a direct edit of a receipt is flagged. A forger who also writes the
log line gets through. In its default advisory mode the gate warns without blocking
(limits). The control is the pull request review.
- GitHub access goes through the
ghCLI with your login.GH_TOKENandGITHUB_TOKENreach a delegated worker only on routes that need the GitHub adapter. - Driver run folders under
.delegate/runs/hold the task text and the harness's raw output. On finalisation the driver masks token shapes and credential-looking assignments instdout.logandstderr.log, andcollectdeletes finished runs older than 30 days (DELEGATE_PRUNE_DAYS,0disables). A nested.gitignorekeeps.delegate/out of git. The result block a harness writes is kept as it was written. - On Windows, the shared
ghtransport and Workflow's git runner resolve the tool fromPATHonly, and the dispatcher callstaskkillby itsSystem32path, so an executable committed in a checkout cannot shadow them. Other extensions' directgitcalls still use the bare name.
Use GitHub's private vulnerability reporting on this repository (Security tab, "Report a vulnerability"). If it is unavailable, open an issue that says only that you have a security report and the maintainer will contact you. Do not post details in a public issue or pull request.