Complete endpoint documentation.
| Environment | Base URL |
|---|---|
| Production | https://api.signedbyme.com |
| Beta | https://api.signedbyme.com |
Standard OpenID Connect discovery endpoints for token validation.
Returns the OpenID Connect discovery document.
{
"issuer": "https://api.signedbyme.com",
"authorization_endpoint": "https://api.signedbyme.com/oauth/authorize",
"token_endpoint": "https://api.signedbyme.com/oauth/token",
"jwks_uri": "https://api.signedbyme.com/oidc/jwks.json",
"response_types_supported": ["id_token"],
"subject_types_supported": ["public"],
"id_token_signing_alg_values_supported": ["RS256"],
"claims_supported": ["sub", "iss", "aud", "exp", "iat", "nonce"]
}
Returns the JSON Web Key Set for token signature validation.
{
"keys": [
{
"kty": "RSA",
"kid": "signedby-2026",
"use": "sig",
"alg": "RS256",
"n": "...",
"e": "AQAB"
}
]
}
Enroll an agent into the Merkle tree during the Genesis flow.
Commit an agent enrollment. Requires both the enterprise authorization (kind 28200) and human delegation (kind 28250) events.
| Field | Type | Description |
|---|---|---|
leaf_commitment required |
string | Hex-encoded leaf commitment (32 bytes) |
authorization_event required |
object | Kind 28200 NOSTR event signed by enterprise |
delegation_event required |
object | Kind 28250 NOSTR event signed by human |
{
"leaf_commitment": "0x1a2b3c4d5e6f...",
"authorization_event": {
"kind": 28200,
"pubkey": "<enterprise_npub_hex>",
"created_at": 1704067200,
"tags": [["p", "<agent_npub_hex>"], ["client_id", "acme-corp"]],
"content": "{\"scopes\":[\"read\",\"write\"]}",
"id": "<event_id>",
"sig": "<enterprise_signature>"
},
"delegation_event": {
"kind": 28250,
"pubkey": "<human_npub_hex>",
"created_at": 1704067200,
"tags": [["p", "<agent_npub_hex>"]],
"content": "{\"agent_npub\":\"npub1...\",\"scopes\":{...},\"expires_at\":\"...\",\"delegation_id\":\"...\"}",
"id": "<event_id>",
"sig": "<human_signature>"
}
}
{
"enrollment_id": "enr_abc123",
"status": "committed",
"tree_id": "tree_acme_members",
"root": "0x7890abcdef...",
"leaf_index": 42,
"witness": {
"siblings": ["0x...", "0x...", ...],
"path_bits": [0, 1, 0, 1, ...]
},
"message": "Enrollment committed successfully"
}
siblings and path_bits
to generate proofs later. The SDK handles this automatically.
Verify a Groth16 proof and receive an OIDC token.
Verify an agent's proof and return an OIDC id_token. Server checks that the Merkle root is valid for the given client.
| Field | Type | Description |
|---|---|---|
proof required |
string | Groth16 proof (hex-encoded) |
public_outputs required |
object | Circuit public outputs |
public_outputs.merkle_root required |
string | Merkle root (hex) |
public_outputs.npub required |
string | Agent's npub (bech32) |
client_id required |
string | Enterprise client ID |
nonce optional |
string | Nonce for replay protection |
{
"proof": "0xabcdef123456...",
"public_outputs": {
"merkle_root": "0x7890abcdef...",
"npub": "npub1abc..."
},
"client_id": "acme-corp",
"nonce": "random_nonce_string"
}
{
"ok": true,
"id_token": "eyJhbGciOiJSUzI1NiIs...",
"token_type": "Bearer",
"expires_in": 3600,
"sub": "npub1abc..."
}
{
"iss": "https://api.signedbyme.com",
"aud": "acme-corp",
"sub": "npub1abc...",
"iat": 1704067200,
"exp": 1704070800,
"nonce": "random_nonce_string",
"amr": ["did_sig", "groth16_proof", "ln_payment"],
"membership_verified": true
}
All errors return a JSON object with error and message fields.
| HTTP | Error Code | Description |
|---|---|---|
| 400 | invalid_request |
Missing or malformed request parameters |
| 400 | invalid_proof |
Groth16 proof verification failed |
| 400 | invalid_signature |
NOSTR event signature verification failed |
| 400 | root_expired |
Merkle root not in last 30 valid roots |
| 401 | invalid_client |
Unknown or unauthorized client_id |
| 403 | enrollment_denied |
Enterprise did not authorize this enrollment |
| 404 | tree_not_found |
No Merkle tree exists for this client |
| 409 | already_enrolled |
This leaf commitment is already in the tree |
| 429 | rate_limited |
Too many requests, slow down |
| 500 | internal_error |
Server error, retry later |
{
"error": "root_expired",
"message": "Merkle root 0x7890... is not in the last 30 valid roots for client acme-corp"
}
Rate limits protect the service from abuse.
| Endpoint | Limit | Window |
|---|---|---|
/v1/login/verify |
100 requests | per minute per IP |
/v1/membership/enroll/commit |
10 requests | per minute per IP |
| OIDC discovery | 1000 requests | per minute per IP |
Responses include these headers:
X-RateLimit-Limit — Maximum requests allowedX-RateLimit-Remaining — Requests remaining in windowX-RateLimit-Reset — Unix timestamp when limit resetsX-RateLimit-Reset
before retrying. Implement exponential backoff in your client.