Skip to content

API token: workflow scope, attestation enforcement, internal system tokens #3115

@migmartri

Description

@migmartri

Summary

Extend the API token model with three related, internal capabilities. None of these change the public proto / service API.

1. Workflow scope on API tokens

API tokens can already be scoped to an organization and, optionally, a project. Today the apitoken row persists project_id and the minted JWT carries project_id/project_name claims.

Extend this one level deeper: a token may optionally be scoped to a single workflow within a project. The workflow scope is persisted on the row and embedded in the JWT as workflow_id/workflow_name claims, mirroring the project pattern. Expressed in biz through a new APITokenWithWorkflow(*Workflow) functional option on APITokenUseCase.Create, with validation that the workflow belongs to the requested project.

2. Attestation-process enforcement for workflow-scoped tokens

When an attestation call (AttestationService.Init, Store, Cancel, GetUploadCreds, GetContract, attestation state) is authenticated with a workflow-scoped API token, the workflow resolved from the request must equal the workflow encoded in the token. Mismatches are rejected.

Two layers of enforcement:

  • Auth middleware verifies the JWT workflow_id claim matches the row's workflow_id (mirrors the existing project mismatch check).
  • A check in findWorkflowFromTokenOrNameOrRunID — the single chokepoint every attestation endpoint goes through — rejects when the resolved workflow differs from the token's workflow.

FindOrCreateWorkflow additionally forbids workflow-scoped tokens from creating or looking up other workflows.

3. Internal "system" tokens hidden from the API

Add an immutable is_system flag on the apitoken row. System tokens are minted by internal code paths (a new APITokenAsSystem() biz option) and continue to mint and validate JWTs normally, but are hidden from the public API:

  • APITokenService/List excludes them by default; opt-in via a new biz-level WithIncludeSystemTokens() filter.
  • Service-layer handlers that look up tokens by id/name (e.g. Revoke) return NotFound when the row is a system token.

The mint path is not exposed in the proto; only internal callers can create system tokens.

Scope

All changes are internal: builders, persistence layer, auth middleware, and the attestation service chokepoint. No proto, no service-level API change.

Metadata

Metadata

Assignees

Labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions