Delegations

Revoke delegation

Revoke ONE delegation. The domain proof beneath it and every sibling delegation stay valid — that independent lifecycle is why the delegation is a separate record. The revocation reaches the revocation list, the Token Status List and the proof status endpoint. Idempotent.

post/api/v1/delegations/{id}/revoke

Request

  • Base URL: https://api.proof.holdings
  • URL: https://api.proof.holdings/api/v1/delegations/{id}/revoke
  • Auth: one of:
    • HTTP bearer
    • API key in cookie auth_token

Path parameters

idstring required

Delegation Mongo id or public handle (ph_dlg_<32 hex>)

Example:ph_dlg_0123456789abcdef0123456789abcdef

Request body

reason'user_request' | 'fraud' | 'key_compromise' | 'other'

Response

Delegation revoked — and a repeat revoke answers 200 with the same body, on this address AND on POST /proofs/{id}/revoke with the ph_dlg_* handle. Idempotent by contract, unlike a PROOF, which answers 400 already_revoked: the delegation contract has always advertised idempotency, while the proof code is published and read by integrators. The body carries the derived effective_status/is_valid beside the stored status, matching the reads

idstring required

MongoDB ObjectId

delegation_idstring nullable required

Stable public handle (ph_dlg_<32 hex>) — also the token's sub, and accepted by the proof status endpoint

principalstring required

The proven domain that authorized the delegate — derived from the control proof, never client input

scopestring[] required
control_proofstring required

The control proof handle this delegation points down to

status'active' | 'revoked' required

The owner's OWN record — whether they revoked this delegation themselves. Nothing else writes it: neither the control proof dying nor this delegation's own lifetime running out. Liveness is DERIVED and reported separately as effective_status. This stored field is also what ?status= filters on

revoked_atstring date-time nullable required
revoked_reasonstring nullable required
environment'production' | 'test' required
issued_atstring date-time required
expires_atstring date-time required

Never later than the control proof's own expiry at issuance (effective expiry is min of the two)

created_atstring date-time required
effective_status'active' | 'revoked' | 'expired' | 'suspended' required

DERIVED liveness, computed at read time from BOTH clocks that govern a delegation: the control proof it stands on (cascade rule a — revoked, suspended or expired flows through) and its own expires_at (rule b — effective expiry is the earlier of the two). Either one running out reports expired here while the delegation's own status stays untouched. This is the field to render — status alone would show a live badge on a delegation every verifier already rejects

is_validboolean required

True only when effective_status is active. It is a restatement of that field, not a second opinion: expiry is decided once, inside the derivation above

Example response

{
  "id": "507f1f77bcf86cd799439011",
  "delegation_id": "ph_dlg_0123456789abcdef0123456789abcdef",
  "principal": "postmark.com",
  "delegate": {
    "value": "pkg:npm/postmark-mcp"
  },
  "scope": [
    "send-email"
  ],
  "control_proof": "ph_ctl_0123456789abcdef0123456789abcdef"
}

Changes

No recorded changes to this operation across all 2 revisions of this API.