/api/v1/attest/challengeBackground-Check · mint a challenge that carries the ask (C1)
The default server→server flow. Your server calls this with its rh_sk_ secret key to mint a single-use challenge, relays the `challenge` string to its keyless client verbatim, and submits the client's response to /attest/verify. The challenge names the ask (what the device must prove) and the policy it will be judged under. No pre-enrolled RP, no client-side key.
| Name | In | Type | Required | Description |
|---|---|---|---|---|
| Authorization | header | string | yes | Bearer rh_sk_… secret key. |
| ask | body | ("identity" | "posture" | "key")[] | no | What the device is asked to prove. identity = the enrolled TPM answers the nonce (PCR 7 only, no event log). posture = full PCRs + event log + Secure Boot claims. key = posture plus a freshly created, AK-certified ECC P-256 app key whose wrapped blob is returned to the caller. Omitted ⇒ ["identity", "posture"]. |
| policy | body | string | no | Policy the response will be judged under: a tenant-owned policy id or a rootherald:builtin:* name. Verify may not name a weaker policy than this one (422 policy_downgrade). Omitted ⇒ your tenant default (strict-hardware unless changed). |
| keyPurpose | body | "sign" | no | Only with a key ask. The purpose the app key is certified for. Today the only value is "sign". |
| deviceHint | body | string | no | Advisory hint identifying the device; recorded for your own correlation, never trusted. |
200 with a single-use challenge (5-minute TTL). `challenge` is what the client consumes — relay it verbatim; a client refuses anything that is not an `rhc1.` string. `nonce` is the same 32 bytes, for your own logging. 401 on a missing/invalid secret key · 422 unknown_policy · 400 on an unknown ask value.
{
"challengeId": "2f9c4a1c-8b…",
"challenge": "rhc1.<nonce>.<ask>",
"nonce": "base64…",
"expiresAt": "2026-06-18T18:09:11Z"
}