Skip to content

Service Account API — Approval Workflows

Service Accounts with the appropriate scope can manage Approval Workflows via the REST API. This enables infrastructure-as-code and GitOps workflows to provision and maintain approval workflow configuration programmatically.

All endpoints are prefixed /api/v1/service/approval-workflows and require a valid session token.

See Authentication for details on obtaining a session token.


Required Scope

Operation Required scope
List or get workflows approval_workflows — read
Create, update, delete, enable, or disable workflows approval_workflows — write

Scopes are granted per-service-account by a user with the admin or manager role via the Service Accounts management page. Write scope implicitly grants read access for the same resource.


List Workflows

GET /api/v1/service/approval-workflows
Authorization: Bearer <token>
Required scope: read

Supports optional query parameters:

Parameter Description
enabled Filter by true or false
page Pagination page (default: 1)
per_page Items per page, max 100 (default: 25)

Results are ordered alphabetically by name.


Get a Workflow

GET /api/v1/service/approval-workflows/{uuid}
Authorization: Bearer <token>
Required scope: read

Returns a single workflow by its UUID. Returns 404 if the workflow does not exist or belongs to a different tenant.


Create a Workflow

POST /api/v1/service/approval-workflows
Authorization: Bearer <token>
Required scope: write
Content-Type: application/json

Example request:

{
  "name": "Production Cert Approvals",
  "description": "Gate all production certificate generation",
  "trigger": "generate",
  "domain_patterns": ["*.prod.example.com", "api.example.com"],
  "bypass_on_renewal": false,
  "is_enabled": true,
  "approver_user_ids": [12, 34],
  "required_approvals": 1,
  "approval_timeout_hours": 48
}

Field reference:

Field Type Required Description
name string Yes Display name for the workflow
description string No Optional description
trigger string Yes generate, revoke, or both
domain_patterns array Yes One or more domain patterns (exact, wildcard, or *)
bypass_on_renewal boolean No Skip workflow for renewal operations (default: false)
is_enabled boolean No Whether the workflow is active (default: true)
approver_user_ids array Yes Array of user IDs from the same tenant
required_approvals integer No Number of approvals required before dispatch (default: 1)
approval_timeout_hours integer No Hours before a pending request auto-expires (null = no timeout)

All user IDs in approver_user_ids must belong to the same tenant as the authenticating service account. Cross-tenant user IDs are rejected with a validation error.


Update a Workflow

PUT /api/v1/service/approval-workflows/{uuid}
Authorization: Bearer <token>
Required scope: write
Content-Type: application/json

Update requests are partial — include only the fields you want to change. Fields not included in the request body are left unchanged.

Use the same field names and values as the Create endpoint.


Enable a Workflow

POST /api/v1/service/approval-workflows/{uuid}/enable
Authorization: Bearer <token>
Required scope: write

Enables a disabled workflow. Idempotent — returns the current state even if the workflow was already enabled.


Disable a Workflow

POST /api/v1/service/approval-workflows/{uuid}/disable
Authorization: Bearer <token>
Required scope: write

Disables an active workflow. Idempotent. Pending approval requests created before the workflow was disabled are not affected.


Delete a Workflow

DELETE /api/v1/service/approval-workflows/{uuid}
Authorization: Bearer <token>
Required scope: write

Permanently deletes the workflow. Existing approval requests created by the workflow are retained for audit purposes.


Response Format

All endpoints return a consistent response envelope:

{
  "success": true,
  "data": {
    "uuid": "550e8400-e29b-41d4-a716-446655440000",
    "name": "Production Cert Approvals",
    "description": "Gate all production certificate generation",
    "trigger": "generate",
    "domain_patterns": ["*.prod.example.com", "api.example.com"],
    "bypass_on_renewal": false,
    "is_enabled": true,
    "approver_user_ids": [12, 34],
    "required_approvals": 1,
    "approval_timeout_hours": 48,
    "created_at": "2026-06-22T00:00:00.000000Z",
    "updated_at": "2026-06-22T00:00:00.000000Z"
  }
}

Internal database IDs and tenant identifiers are never included in API responses. The uuid field is the stable public identifier for all workflows.


Audit Logging

All write operations via the Service Account API generate audit log entries distinct from user-initiated actions:

Audit event Triggered by
approval_workflow.service_account.created POST /
approval_workflow.service_account.updated PUT /{uuid}
approval_workflow.service_account.deleted DELETE /{uuid}
approval_workflow.service_account.enabled POST /{uuid}/enable
approval_workflow.service_account.disabled POST /{uuid}/disable

Each entry includes the service account UUID, service account name, the affected workflow UUID and name, and the caller's IP address.