chadtmiller.com/knotless
git that lives in your Atmosphere account
1
10
The appview keeps secrets sealed to a runner
Closedchadtmiller.com added 4 commits
Folded into Owners give their runners secrets with knotless secret, which carries these commits too and is ahead of it in the queue: landing both would squash an empty change on top.

What changes
knotless-serve answers three new methods, each with a service token for itself from the caller's PDS:
dev.knotless.putSecret: an owner leaves one of its repositories' runners a secret, sealed to that runner'sdev.knotless.runnerKey. The repository is named by its key, not its name, so a rename keeps its secrets. One of the same repository, runner and name is replaced.dev.knotless.deleteSecret: by name, by runner, both, or all of a repository's; answers how many went.dev.knotless.listSecrets: the owner sees every one, names, runners and refs, never a value; a runner sees those sealed to it, with the sealed value; anyone else, none.knotless::secretscalls them, and knotless's login asks for them in itsrpc:scope, so an older session asks again at its next login. The appview forgets an account's secrets, as owner or runner, with the rest of its data.docs/reference/api.md,docs/design/access.mdanddocs/design/security.mdsay so.Why
The third part of the design on the issue. The appview holds sealed values because spaces need a spaces-alpha PDS most owners don't have, and spaces don't encrypt anyway; public sealed records would stay on the firehose for good.
Part of A repository owner can't give the hosted runner a secret
Built on
run/runner-key(knotless-run keeps a key for secrets, and publishes it), whose docs section these link to.How it was checked
tests/forge.rssecrets_reach_only_their_runner: put, replace, list as owner (no values), as runner (its own, with values), as a stranger (none), delete by name, runner and all, and each bad input refused with 400. Left to CI.Shortcomings
Nothing calls these yet besides the test:
knotless secretand the runner reading them come next. The appview checks only that the caller is the owner, not that the repository names the runner; the runner checks that before it runs anything.🤖 Generated with Claude Code