System Design Interview: How Would You Design a Request-Bound Delegated-Authority Verifier?
Prompt and scope
Design a delegated-authority verification layer for an agent, workload, or batch job acting for a person or organization to spend money, consume metered resources, disclose regulated data, or mutate production state. The system must prove bounded authority before processing a protected request. The prompt references an IETF HTTPAPI Internet-Draft from 2026; it remains work in progress, is not a final RFC, and is not a payment protocol.
What the interviewer is testing
- Separating identity authentication, delegated authorization, request integrity, and settlement.
- Designing 401 challenges, 403 denials, nonces, expiry, and request binding.
- Handling replay, cross-tenant reuse, proxies, key rotation, and auditability.
- Enforcing budgets, policy, and fail-closed boundaries before high-impact actions.
Questions to clarify before answering
- Is the protected action a data export, production write, downstream call, or budgeted consumption?
- Who operates the principal, issuer, delegated requester, and verifier?
- Must authority bind to the HTTP method, target URI, request digest, or only a resource scope?
- Is offline verification allowed, and how are nonce availability and clock skew handled?
- Should failure reject the request, require human approval, or downgrade to read-only?
30-second answer framework
Split the problem into four layers: existing identity proves who the requester is; delegation says for whom it acts, what it may do, and the limit; request binding restricts the proof to one request; policy decides whether execution is allowed now. Return a 401 challenge when no acceptable proof exists and 403 when the proof is understood but insufficient. Include issuer, requester, principal, expiry, nonce, method, URI, digest, and budget bounds. Execute only after verification, fail closed, and audit every denial.
Step-by-step deep dive
1. Define roles and trust boundaries
The principal is a person, organization, or service. The delegated requester is an agent, device, job, or workload. The issuer signs a proof for the principal, and the verifier sits at the protected resource or gateway. OAuth Token Exchange or another issuance system can obtain the proof; the verifier handles challenge and presentation, not consent or account linking.
2. Design the challenge and response
Without an acceptable proof, return 401, WWW-Authenticate: Delegation, and Cache-Control: no-store. Return 403 when the proof is syntactically valid but exceeds local policy. Problem Details can explain the failure, but explanatory fields must not relax the challenge.
HTTP/1.1 401 Unauthorized
Cache-Control: no-store
WWW-Authenticate: Delegation realm="api.example",
version=1, profile="budget", nonce="n-123", max-age=300The verifier controls nonce, profile, and expiry windows so a proof cannot be copied across requests.
3. Bind the proof to the future request
Bind at least the HTTP method, trusted origin, target URI, request digest, and expiry. If a proxy rewrites Host or path, reconstruct origin only from trusted gateway configuration; never trust an unvalidated X-Forwarded-*. Define canonicalization for method case, query ordering, and percent encoding.
{
"principal": "org-42",
"requester": "job-7",
"method": "POST",
"origin": "https://api.example",
"target_hash": "sha-256:...",
"nonce": "n-123",
"expires": "2026-08-04T05:00:00Z",
"limits": {"USD": 250}
}4. Set verification order and fail-closed behavior
Parse version and format, then verify signature, issuer trust, nonce freshness, time window, request binding, and local budget. Reject when a dependency is unavailable, CBOR is non-deterministic, a signature fails, or nonce state is lost. Verify identity credentials and delegation proofs as separate layers; one valid proof must not authorize an unrelated API key.
5. Prevent replay and cross-tenant reuse
Store nonces with a short TTL, atomic consumption, and tenant isolation. The request digest and target origin prevent copying one proof to another API. Reject reused nonces, bound clock skew, and use identical binding fields for preflight and the final request. High-risk actions can require a one-time proof and human approval.
6. Enforce budget and policy
A budget is an authority profile, not payment or settlement. Policy can limit amount, service units, data scope, environment, and downstream calls. Debit in the same transaction boundary as the action, or use a compensating reservation, so concurrent requests cannot jointly exceed the limit.
7. Operate keys and audit safely
Issuers publish rotatable keys and versions. Verifiers may cache them but must support revocation and emergency rotation. Audit principal, requester, target, policy result, proof ID, and denial reason; never log full tokens, private keys, or sensitive data. Track 401/403 rates, nonce replays, verification latency, policy denials, budget overruns, key-rotation failures, and approval time.
High-quality sample answer
I would split the system into identity, delegation, request binding, and policy layers. OAuth or another issuer proves the principal relationship. The delegation proof carries principal, requester, profile, expiry, and budget; the verifier binds it to the HTTP method, trusted origin, target URI, request digest, and nonce that will be executed.
Return 401 with WWW-Authenticate: Delegation and no-store when a proof is missing; return 403 when it is valid but insufficient. Verify format, signature and issuer trust, nonce freshness, time window, request binding, tenant policy, and budget in that order. Any signature failure, unavailable dependency, or lost nonce state fails closed. The proof does not define payment, replace HTTP Message Signatures, or implement OAuth issuance or consent.
Debit the budget in the action’s transaction or a compensating reservation, and atomically consume a tenant-isolated nonce. Support key rotation and emergency revocation, while logs retain only proof ID, principal, target, and outcome. Test replay, cross-tenant copying, proxy rewriting, concurrent overspend, and key rotation. The goal is to prove “who acts for whom, and what it may do to this exact request” before the consequential action occurs.
Common mistakes
- Treating a delegation proof as general identity, OAuth issuance, or a payment protocol.
- Issuing a long-lived token without method, URI, digest, nonce, or expiry binding.
- Allowing requests when signature dependencies are unavailable.
- Trusting proxy-rewritten or untrusted
X-Forwarded-*values for the target. - Logging full credentials or debiting after the action, leaving replay and overspend windows.
Follow-up questions and responses
Why use both 401 and 403?
401 means the proof is missing, invalid, or incomplete, so a client may obtain a new proof from the challenge. 403 means the proof was understood but the authority, budget, or local policy is insufficient; retrying it does not help.
What if the nonce service is temporarily unavailable?
Fail closed for high-risk requests and return a diagnostic no-store error. Only explicitly assessed low-risk read-only actions may have a constrained fallback; a cached old nonce is not a one-time state.
How does this work with OAuth?
OAuth Token Exchange or GNAP can obtain delegation material. The verifier still checks the request-bound proof independently. Verify the identity token and delegation proof separately so delegated scope is not mistaken for all identity-token permissions.
Is this a payment protocol?
No. A budget profile can express amount or service-unit limits, while settlement, payment rails, and HTTP 402 semantics are external. The verifier only decides whether the protected action satisfies delegation policy.