Add per-role HTTP method scoping to minted tokens (#2)
ci/woodpecker/tag/release Pipeline was successful

## Why

Every token this engine mints is as powerful as the apps it can reach, so a read-only integration can still write to the *arr. arrproxy now accepts a method scope at mint time, and the engine has no way to ask for one.

## How

- Add an optional `methods` role field, uppercase-normalized and de-duplicated.
- Reject a method outside GET/HEAD/POST/PUT/PATCH/DELETE/OPTIONS at role write.
- Forward the role's scope on the arrproxy mint request and echo it in the creds response.
- Omit the field when a role has no scope, so unscoped roles behave exactly as before.
- Cover normalization, rejection, pass-through and the unscoped case.

Requires arrproxy >= v0.5.0 deployed.

Reviewed-on: #2
Co-authored-by: unkin-agent <unkin-agent@unkin.net>
Co-committed-by: unkin-agent <unkin-agent@unkin.net>
This commit was merged in pull request #2.
This commit is contained in:
2026-08-30 14:45:04 +10:00
committed by BenVincent
parent c3205dde45
commit b1b11330a6
8 changed files with 329 additions and 4 deletions
+5 -2
View File
@@ -63,8 +63,11 @@ func newClient(config *arrstackConfig) (*arrproxyClient, error) {
// mintTokenRequest is the payload for POST /api/admin/tokens. The subject MUST
// carry the "vault:arrstack:" prefix or arrproxy rejects the request.
type mintTokenRequest struct {
Subject string `json:"subject"`
Apps []string `json:"apps"`
Subject string `json:"subject"`
Apps []string `json:"apps"`
// Methods limits the token to those HTTP methods. Omitted when empty so
// arrproxy versions predating method scoping see the request unchanged.
Methods []string `json:"methods,omitempty"`
Label string `json:"label"`
TTLSeconds int64 `json:"ttl_seconds"`
}