{"openapi":"3.1.0","info":{"title":"HashSign API","version":"0.1.0","summary":"Cryptographic document signing and Hedera ledger anchoring for AI agents.","description":"REST API consumed by the HashSign web portal and the `hashsign-python` SDK.\nAll paths are relative to `/v1`. Production Hedera consensus submissions and\npersistence attach at the hooks documented on each operation.\n","license":{"name":"Proprietary","identifier":"LicenseRef-HashSign"},"contact":{"name":"HashSign","url":"https://hashsign.io"}},"servers":[{"url":"https://api.hashsign.io/v1","description":"Production"},{"url":"https://api.staging.hashsign.io/v1","description":"Staging"},{"url":"http://localhost:3000/api/v1","description":"Local portal mock"}],"tags":[{"name":"Auth"},{"name":"Teams"},{"name":"Documents"},{"name":"Keys"},{"name":"Logs"},{"name":"Branding"},{"name":"Dashboard"}],"security":[{"BearerAuth":[]}],"paths":{"/auth/login":{"post":{"tags":["Auth"],"operationId":"login","summary":"Email and password login","security":[],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LoginRequest"}}}},"responses":{"200":{"description":"Authenticated session","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/auth/register":{"post":{"tags":["Auth"],"operationId":"register","summary":"Create a user and default team","security":[],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RegisterRequest"}}}},"responses":{"201":{"description":"Registered session","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthResponse"}}}},"409":{"$ref":"#/components/responses/Conflict"},"422":{"$ref":"#/components/responses/ValidationError"}}}},"/auth/oauth/{provider}":{"post":{"tags":["Auth"],"operationId":"oauthLogin","summary":"Complete an OAuth authorization-code exchange","security":[],"parameters":[{"$ref":"#/components/parameters/OAuthProvider"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OAuthLoginRequest"}}}},"responses":{"200":{"description":"Authenticated session","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/auth/token":{"post":{"tags":["Auth"],"operationId":"tokenLogin","summary":"Exchange a long-lived API token for a portal session","security":[],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TokenLoginRequest"}}}},"responses":{"200":{"description":"Authenticated session","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/teams":{"get":{"tags":["Teams"],"operationId":"listTeams","summary":"List teams the current user can access","responses":{"200":{"description":"Team list","content":{"application/json":{"schema":{"type":"object","required":["items"],"properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/Team"}}}}}}}}}},"/teams/switch":{"post":{"tags":["Teams"],"operationId":"switchTeam","summary":"Switch the active team on the current session","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["teamId"],"properties":{"teamId":{"$ref":"#/components/schemas/TeamId"}}}}}},"responses":{"200":{"description":"Updated session","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthResponse"}}}},"404":{"$ref":"#/components/responses/NotFound"}}}},"/dashboard":{"get":{"tags":["Dashboard"],"operationId":"getDashboard","summary":"Metrics overview and recent activity","responses":{"200":{"description":"Dashboard payload","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DashboardResponse"}}}}}}},"/documents":{"get":{"tags":["Documents"],"operationId":"listDocuments","summary":"List uploaded documents for the active team","parameters":[{"name":"page","in":"query","schema":{"type":"integer","minimum":1,"default":1}},{"name":"pageSize","in":"query","schema":{"type":"integer","minimum":1,"maximum":100,"default":25}},{"name":"status","in":"query","schema":{"$ref":"#/components/schemas/SignatureStatus"}}],"responses":{"200":{"description":"Paginated documents","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DocumentListResponse"}}}}}},"post":{"tags":["Documents"],"operationId":"uploadDocument","summary":"Register a document by SHA-384 hash","description":"The Python SDK computes the SHA-384 digest locally before calling this\nendpoint. HOOK: persist the document row, then optionally submit the\nhash to a Hedera Consensus Service topic for pending registration.\n","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DocumentUploadRequest"}},"multipart/form-data":{"schema":{"type":"object","required":["file"],"properties":{"file":{"type":"string","format":"binary"},"metadata":{"type":"string","description":"JSON-encoded DocumentMetadata"}}}}}},"responses":{"201":{"description":"Document registered","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DocumentUploadResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"422":{"$ref":"#/components/responses/ValidationError"}}}},"/documents/{documentId}":{"get":{"tags":["Documents"],"operationId":"getDocument","summary":"Fetch a single document","parameters":[{"$ref":"#/components/parameters/DocumentId"}],"responses":{"200":{"description":"Document","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Document"}}}},"404":{"$ref":"#/components/responses/NotFound"}}}},"/documents/{documentId}/sign":{"post":{"tags":["Documents"],"operationId":"signDocument","summary":"Produce a cryptographic verification payload","description":"Signs the document digest. When `pqcMode` is true, or the signer\nkey has `requirePqcSignatures`, the response envelope is\n`hybrid-ecdsa-ml-dsa`: a classical signature plus an ML-DSA-65\n(FIPS 204) signature over the raw 48-byte SHA-384 digest.\n\n`requirePqcSignatures` is a boolean on the API key, not a key scope.\nScopes remain `read`, `write`, and `sign`. A key with\n`requirePqcSignatures: true` rejects `documents.sign` unless\n`pqcMode` is true.\n\nThe Hedera Consensus Service message does not carry the 3309-byte\nML-DSA signature. It carries `hybridAnchor`, the 48-byte SHA-384\ndescribed on `PqcSignature`. The example topic used by the landing\npage and local mock receipts is `0.0.9001`; live submits use the\nconfigured `HEDERA_TOPIC_ID`.\n\nThird-party verification of an anchored hybrid envelope:\n\n1. Read the HCS message JSON. It contains `docHash` (SHA-384, 96 hex characters),\n   `hashAlgorithm` (`SHA-384`), and `hybridAnchor`.\n2. Let `classical` be `payload.signature` and `ml` be `payload.pqc.signature`,\n   both lowercase hex.\n3. Compute `SHA-384(UTF-8(classical + ml))` and compare to\n   `payload.pqc.hybridAnchor` and to the HCS `hybridAnchor`.\n4. Compare HCS `docHash` to `payload.sha384`.\n5. Optional signature check: ML-DSA-65.Verify(publicKey, digest, signature)\n   where `digest` is the raw 48 bytes of `payload.sha384` (pure ML-DSA,\n   not HashML-DSA), `signature` is 3309 bytes, and `publicKey` is the\n   1952 bytes in `payload.pqc.publicKey`.\n","parameters":[{"$ref":"#/components/parameters/DocumentId"}],"requestBody":{"required":false,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignDocumentRequest"}}}},"responses":{"200":{"description":"Signed payload","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignDocumentResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"429":{"$ref":"#/components/responses/RateLimited"},"503":{"$ref":"#/components/responses/HederaUnavailable"}}}},"/documents/{documentId}/verify":{"get":{"tags":["Documents"],"operationId":"verifyDocument","summary":"Return the Hedera ledger audit proof","description":"Strictly read-only: never changes document status. Anchoring is driven\nby the sign flow. HOOK: query Hedera mirror node / HCS topic for the\nconsensus message matching `sha384` and assemble `LedgerProof`.\n","parameters":[{"$ref":"#/components/parameters/DocumentId"}],"responses":{"200":{"description":"Ledger proof","content":{"application/json":{"schema":{"$ref":"#/components/schemas/VerifyDocumentResponse"}}}},"404":{"$ref":"#/components/responses/NotFound"},"503":{"$ref":"#/components/responses/HederaUnavailable"}}}},"/public/documents/{documentId}/verify":{"get":{"tags":["Documents"],"operationId":"verifyDocumentPublic","summary":"Public audit proof card","description":"Unauthenticated read of the same `VerifyDocumentResponse` used by the\nportal verify modal. Renders `/verify/{id}` in the web app.\n","security":[],"parameters":[{"$ref":"#/components/parameters/DocumentId"}],"responses":{"200":{"description":"Ledger proof","content":{"application/json":{"schema":{"$ref":"#/components/schemas/VerifyDocumentResponse"}}}},"404":{"$ref":"#/components/responses/NotFound"}}}},"/branding":{"get":{"tags":["Branding"],"operationId":"listAgentBrands","summary":"List minted and draft agent identities for the active team","responses":{"200":{"description":"Agent brands","content":{"application/json":{"schema":{"$ref":"#/components/schemas/BrandListResponse"}}}}}},"post":{"tags":["Branding"],"operationId":"registerAgentBrand","summary":"Hash a logo and mint it to the Hedera Agent Identity topic","description":"The portal hashes the logo locally (SHA-384), derives an IPFS CID-style\nURI, and submits the `{ brandHash, ipfsUri, agentId }` tuple as an HCS\nmessage on the team's identity topic.\n","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BrandMintRequest"}}}},"responses":{"201":{"description":"Minted brand","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentBrand"}}}},"422":{"$ref":"#/components/responses/ValidationError"}}}},"/keys":{"get":{"tags":["Keys"],"operationId":"listApiKeys","summary":"List API keys for the active team","responses":{"200":{"description":"API keys (secrets never included)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiKeyListResponse"}}}}}},"post":{"tags":["Keys"],"operationId":"createApiKey","summary":"Generate a new API key","description":"The plaintext `secret` is returned once.","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateApiKeyRequest"}}}},"responses":{"201":{"description":"Created key including secret","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateApiKeyResponse"}}}},"422":{"$ref":"#/components/responses/ValidationError"}}}},"/keys/rotate":{"post":{"tags":["Keys"],"operationId":"rotateCurrentApiKey","summary":"Rotate the API key used for this request","description":"Used by `HashSignClient.keys.rotate()`. Issues a **new** ApiKey record\n(returned with its secret) and marks the calling key `rotated` with\n`rotatedToKeyId` set, preserving audit history.\n","responses":{"200":{"description":"Rotated key including new secret","content":{"application/json":{"schema":{"$ref":"#/components/schemas/RotateApiKeyResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/keys/{keyId}":{"patch":{"tags":["Keys"],"operationId":"updateApiKey","summary":"Update key name or scopes","parameters":[{"$ref":"#/components/parameters/KeyId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateApiKeyRequest"}}}},"responses":{"200":{"description":"Updated key","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiKey"}}}},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Keys"],"operationId":"revokeApiKey","summary":"Revoke an API key","parameters":[{"$ref":"#/components/parameters/KeyId"}],"responses":{"204":{"description":"Revoked"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/keys/{keyId}/rotate":{"post":{"tags":["Keys"],"operationId":"rotateApiKey","summary":"Rotate a specific API key","description":"Issues a new ApiKey record and marks `keyId` as `rotated` with\n`rotatedToKeyId` pointing at the replacement.\n","parameters":[{"$ref":"#/components/parameters/KeyId"}],"responses":{"200":{"description":"Rotated key including new secret","content":{"application/json":{"schema":{"$ref":"#/components/schemas/RotateApiKeyResponse"}}}},"404":{"$ref":"#/components/responses/NotFound"}}}},"/logs":{"get":{"tags":["Logs"],"operationId":"listAuditLogs","summary":"Query the programmatic signing audit log","parameters":[{"name":"since","in":"query","schema":{"type":"string","format":"date-time"}},{"name":"agentId","in":"query","schema":{"$ref":"#/components/schemas/AgentId"}},{"name":"limit","in":"query","schema":{"type":"integer","minimum":1,"maximum":200,"default":50}}],"responses":{"200":{"description":"Audit entries","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuditLogListResponse"}}}}}}},"/logs/stream":{"get":{"tags":["Logs"],"operationId":"streamAuditLogs","summary":"Server-sent events stream of audit log entries","responses":{"200":{"description":"SSE stream (`text/event-stream`) of AuditLogEntry","content":{"text/event-stream":{"schema":{"$ref":"#/components/schemas/AuditLogEntry"}}}}}}}},"components":{"securitySchemes":{"BearerAuth":{"type":"http","scheme":"bearer","description":"Portal sessions send a JWT; SDK agents send an API key\n(`Bearer hs_live_...` / `Bearer hs_test_...`). Both use the same header.\n"}},"parameters":{"DocumentId":{"name":"documentId","in":"path","required":true,"schema":{"$ref":"#/components/schemas/DocumentId"}},"KeyId":{"name":"keyId","in":"path","required":true,"schema":{"$ref":"#/components/schemas/ApiKeyId"}},"OAuthProvider":{"name":"provider","in":"path","required":true,"schema":{"$ref":"#/components/schemas/OAuthProvider"}}},"responses":{"Unauthorized":{"description":"Authentication failed","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiErrorResponse"}}}},"ValidationError":{"description":"Request failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiErrorResponse"}}}},"NotFound":{"description":"Resource not found","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiErrorResponse"}}}},"Conflict":{"description":"Resource already exists","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiErrorResponse"}}}},"RateLimited":{"description":"Rate limit exceeded","headers":{"Retry-After":{"schema":{"type":"integer"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiErrorResponse"}}}},"HederaUnavailable":{"description":"Hedera network error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiErrorResponse"}}}}},"schemas":{"ISODateString":{"type":"string","format":"date-time"},"HexSha256":{"description":"A cryptographic hash stored as 64 hexadecimal characters. Not a document seal.","type":"string","pattern":"^[a-f0-9]{64}$"},"HexSha384":{"description":"SHA-384 document seal or anchored digest, 96 hexadecimal characters.","type":"string","pattern":"^[a-fA-F0-9]{96}$"},"HederaTransactionId":{"type":"string","examples":["0.0.45291@1726780800.123456789"]},"DocumentId":{"type":"string"},"ApiKeyId":{"type":"string"},"AgentId":{"type":"string"},"TeamId":{"type":"string"},"UserId":{"type":"string"},"OAuthProvider":{"type":"string","enum":["github","google","microsoft"]},"SignatureStatus":{"type":"string","enum":["pending","signed","anchored"]},"KeyScope":{"type":"string","enum":["read","write","sign"]},"ApiKeyStatus":{"type":"string","enum":["active","revoked","rotated"]},"AuditEventType":{"type":"string","enum":["document.uploaded","document.signed","document.verified","document.anchored","key.created","key.rotated","key.revoked","auth.login","auth.token","brand.minted","brand.updated","agent.pre_sign"]},"HederaNetworkHealth":{"type":"string","enum":["healthy","degraded","unavailable"]},"ApiErrorCode":{"type":"string","enum":["authentication_error","forbidden","validation_error","rate_limit_error","hedera_network_error","not_found","conflict","internal_error"]},"User":{"type":"object","additionalProperties":false,"required":["id","email","name","avatarUrl","createdAt"],"properties":{"id":{"$ref":"#/components/schemas/UserId"},"email":{"type":"string","format":"email"},"name":{"type":"string"},"avatarUrl":{"type":["string","null"]},"createdAt":{"$ref":"#/components/schemas/ISODateString"}}},"Team":{"type":"object","additionalProperties":false,"required":["id","name","slug","plan","hederaAccountId"],"properties":{"id":{"$ref":"#/components/schemas/TeamId"},"name":{"type":"string"},"slug":{"type":"string"},"plan":{"type":"string","enum":["starter","pro","business","enterprise"]},"hederaAccountId":{"type":["string","null"]}}},"Session":{"type":"object","additionalProperties":false,"required":["user","team","teams","accessToken","expiresAt"],"properties":{"user":{"$ref":"#/components/schemas/User"},"team":{"$ref":"#/components/schemas/Team"},"teams":{"type":"array","items":{"$ref":"#/components/schemas/Team"}},"accessToken":{"type":"string"},"expiresAt":{"$ref":"#/components/schemas/ISODateString"}}},"LoginRequest":{"type":"object","additionalProperties":false,"required":["email","password"],"properties":{"email":{"type":"string","format":"email"},"password":{"type":"string","minLength":8}}},"RegisterRequest":{"type":"object","additionalProperties":false,"required":["name","email","password","teamName"],"properties":{"name":{"type":"string"},"email":{"type":"string","format":"email"},"password":{"type":"string","minLength":8},"teamName":{"type":"string"}}},"TokenLoginRequest":{"type":"object","additionalProperties":false,"required":["apiToken"],"properties":{"apiToken":{"type":"string"}}},"OAuthLoginRequest":{"type":"object","additionalProperties":false,"required":["provider","code","redirectUri"],"properties":{"provider":{"$ref":"#/components/schemas/OAuthProvider"},"code":{"type":"string"},"redirectUri":{"type":"string","format":"uri"}}},"AuthResponse":{"type":"object","additionalProperties":false,"required":["session"],"properties":{"session":{"$ref":"#/components/schemas/Session"}}},"DocumentMetadata":{"type":"object","additionalProperties":false,"properties":{"title":{"type":"string"},"description":{"type":"string"},"tags":{"type":"array","items":{"type":"string"}},"agentId":{"$ref":"#/components/schemas/AgentId"},"agentLogoUri":{"description":"IPFS (or HTTPS) URI of the minted agent / workspace logo.","type":["string","null"],"format":"uri"},"agentBrandHash":{"description":"SHA-384 of the minted logo bytes, as registered on the identity topic.","oneOf":[{"$ref":"#/components/schemas/HexSha384"},{"type":"null"}]},"extra":{"type":"object","additionalProperties":{"type":["string","number","boolean"]}}}},"Document":{"type":"object","additionalProperties":false,"required":["id","fileName","mimeType","sizeBytes","sha384","status","uploadedBy","teamId","createdAt","signedAt","anchoredAt","hederaTransactionId","metadata"],"properties":{"id":{"$ref":"#/components/schemas/DocumentId"},"fileName":{"type":"string"},"mimeType":{"type":"string"},"sizeBytes":{"type":"integer","minimum":0},"sha384":{"$ref":"#/components/schemas/HexSha384"},"status":{"$ref":"#/components/schemas/SignatureStatus"},"uploadedBy":{"$ref":"#/components/schemas/UserId"},"teamId":{"$ref":"#/components/schemas/TeamId"},"createdAt":{"$ref":"#/components/schemas/ISODateString"},"signedAt":{"type":["string","null"],"format":"date-time"},"anchoredAt":{"type":["string","null"],"format":"date-time"},"hederaTransactionId":{"type":["string","null"]},"metadata":{"$ref":"#/components/schemas/DocumentMetadata"},"pqc":{"description":"Dual-signature envelope, present once the document was signed with\n`pqcMode` or by a key that requires post-quantum signatures.\n","oneOf":[{"$ref":"#/components/schemas/PqcSignature"},{"type":"null"}]}}},"DocumentUploadRequest":{"type":"object","additionalProperties":false,"required":["fileName","mimeType","sha384"],"properties":{"fileName":{"type":"string"},"mimeType":{"type":"string"},"sizeBytes":{"type":"integer","minimum":0},"contentBase64":{"type":"string"},"sha384":{"$ref":"#/components/schemas/HexSha384"},"metadata":{"$ref":"#/components/schemas/DocumentMetadata"}}},"DocumentUploadResponse":{"type":"object","additionalProperties":false,"required":["document"],"properties":{"document":{"$ref":"#/components/schemas/Document"}}},"SignDocumentRequest":{"type":"object","additionalProperties":false,"properties":{"metadata":{"$ref":"#/components/schemas/DocumentMetadata"},"pqcMode":{"type":"boolean","description":"When true, `documents.sign` must return a `hybrid-ecdsa-ml-dsa`\nenvelope (classical signature plus ML-DSA-65). Ignored keys that\nset `requirePqcSignatures` still require this flag.\n"}}},"PqcSignature":{"type":"object","additionalProperties":false,"required":["enabled","algorithm","signature","hybridAnchor"],"description":"Hybrid post-quantum half of a `hybrid-ecdsa-ml-dsa` envelope.\n`signature` is hex of a 3309-byte FIPS 204 ML-DSA-65 signature over\nthe raw document digest. `hybridAnchor` is\n`SHA-384(UTF-8(classicalSignatureHex + signatureHex))` and is the\nvalue submitted to Hedera HCS (example topic `0.0.9001`).\n","properties":{"enabled":{"type":"boolean"},"algorithm":{"type":"string","enum":["ml-dsa-65"]},"signature":{"type":"string","description":"Lowercase hex. Production signatures are 6618 hex characters (3309 bytes)."},"publicKey":{"type":"string","description":"Lowercase hex of the 1952-byte ML-DSA-65 public key."},"hybridAnchor":{"$ref":"#/components/schemas/HexSha384"}}},"SignedPayload":{"type":"object","additionalProperties":false,"required":["documentId","sha384","signedAt","signerKeyId","signature","algorithm"],"properties":{"documentId":{"$ref":"#/components/schemas/DocumentId"},"sha384":{"$ref":"#/components/schemas/HexSha384"},"signedAt":{"$ref":"#/components/schemas/ISODateString"},"signerKeyId":{"$ref":"#/components/schemas/ApiKeyId"},"signature":{"type":"string"},"algorithm":{"type":"string","enum":["ed25519","ecdsa-p256","hybrid-ecdsa-ml-dsa"]},"pqc":{"oneOf":[{"$ref":"#/components/schemas/PqcSignature"},{"type":"null"}]},"agentLogoUri":{"type":["string","null"],"format":"uri"},"agentBrandHash":{"oneOf":[{"$ref":"#/components/schemas/HexSha384"},{"type":"null"}]}}},"SignDocumentResponse":{"type":"object","additionalProperties":false,"required":["document","payload"],"properties":{"document":{"$ref":"#/components/schemas/Document"},"payload":{"$ref":"#/components/schemas/SignedPayload"}}},"LedgerProof":{"type":"object","additionalProperties":false,"required":["documentId","sha384","status","hederaTransactionId","hederaConsensusTimestamp","topicId","network","verified"],"properties":{"documentId":{"$ref":"#/components/schemas/DocumentId"},"sha384":{"$ref":"#/components/schemas/HexSha384"},"status":{"$ref":"#/components/schemas/SignatureStatus"},"hederaTransactionId":{"type":["string","null"]},"hederaConsensusTimestamp":{"type":["string","null"],"format":"date-time"},"topicId":{"type":["string","null"]},"network":{"type":"string","enum":["mainnet","testnet","previewnet","mock"]},"verified":{"type":"boolean"}}},"VerifyDocumentResponse":{"type":"object","additionalProperties":false,"required":["document","proof"],"properties":{"document":{"$ref":"#/components/schemas/Document"},"proof":{"$ref":"#/components/schemas/LedgerProof"}}},"DocumentListResponse":{"type":"object","additionalProperties":false,"required":["items","total","page","pageSize"],"properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/Document"}},"total":{"type":"integer"},"page":{"type":"integer"},"pageSize":{"type":"integer"}}},"ApiKey":{"allOf":[{"$ref":"#/components/schemas/ApiKeyBase"}],"unevaluatedProperties":false},"ApiKeyBase":{"type":"object","required":["id","name","prefix","scopes","status","agentId","teamId","createdAt","lastUsedAt","expiresAt","revokedAt","requirePqcSignatures"],"properties":{"id":{"$ref":"#/components/schemas/ApiKeyId"},"name":{"type":"string"},"prefix":{"type":"string"},"scopes":{"type":"array","items":{"$ref":"#/components/schemas/KeyScope"}},"status":{"$ref":"#/components/schemas/ApiKeyStatus"},"agentId":{"$ref":"#/components/schemas/AgentId"},"teamId":{"$ref":"#/components/schemas/TeamId"},"createdAt":{"$ref":"#/components/schemas/ISODateString"},"lastUsedAt":{"type":["string","null"],"format":"date-time"},"expiresAt":{"type":["string","null"],"format":"date-time"},"revokedAt":{"type":["string","null"],"format":"date-time"},"rotatedToKeyId":{"description":"Set on a `rotated` key; points at the credential that replaced it.","type":["string","null"]},"requirePqcSignatures":{"description":"When true, documents.sign must be called with `pqcMode: true` and\nmust emit a hybrid ECDSA + ML-DSA-65 envelope. This is not a scope;\nthe key still needs the `sign` scope.\n","type":"boolean"}}},"ApiKeyCreated":{"description":"An ApiKey plus its plaintext `secret`. Each `allOf` branch is evaluated\nindependently, so the closed-world constraint lives on\n`unevaluatedProperties` at this level rather than on either branch.\n","allOf":[{"$ref":"#/components/schemas/ApiKeyBase"},{"type":"object","required":["secret"],"properties":{"secret":{"type":"string"}}}],"unevaluatedProperties":false},"CreateApiKeyRequest":{"type":"object","additionalProperties":false,"required":["name","scopes"],"properties":{"name":{"type":"string"},"scopes":{"type":"array","minItems":1,"items":{"$ref":"#/components/schemas/KeyScope"}},"expiresAt":{"type":["string","null"],"format":"date-time"},"requirePqcSignatures":{"type":"boolean"}}},"CreateApiKeyResponse":{"type":"object","additionalProperties":false,"required":["key"],"properties":{"key":{"$ref":"#/components/schemas/ApiKeyCreated"}}},"RotateApiKeyResponse":{"type":"object","additionalProperties":false,"required":["key"],"properties":{"key":{"$ref":"#/components/schemas/ApiKeyCreated"}}},"UpdateApiKeyRequest":{"type":"object","additionalProperties":false,"properties":{"name":{"type":"string"},"scopes":{"type":"array","items":{"$ref":"#/components/schemas/KeyScope"}},"requirePqcSignatures":{"type":"boolean"}}},"ApiKeyListResponse":{"type":"object","additionalProperties":false,"required":["items"],"properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/ApiKey"}}}},"AuditLogEntry":{"type":"object","additionalProperties":false,"required":["id","timestamp","event","agentId","documentId","documentHash","hederaTransactionId","apiKeyId","teamId","message","statusCode"],"properties":{"id":{"type":"string"},"timestamp":{"$ref":"#/components/schemas/ISODateString"},"event":{"$ref":"#/components/schemas/AuditEventType"},"agentId":{"type":["string","null"]},"documentId":{"type":["string","null"]},"documentHash":{"type":["string","null"]},"hederaTransactionId":{"type":["string","null"]},"apiKeyId":{"type":["string","null"]},"teamId":{"$ref":"#/components/schemas/TeamId"},"message":{"type":"string"},"statusCode":{"type":"integer"},"eventHash":{"description":"Present on `agent.pre_sign`. a cryptographic hash of the canonical JSON record\n(sorted keys) of the pre-sign checks. Recompute it to detect a\ntampered audit line.\n","oneOf":[{"$ref":"#/components/schemas/HexSha256"},{"type":"null"}]}}},"AgentBrand":{"type":"object","additionalProperties":false,"required":["id","teamId","agentId","name","logoDataUrl","logoMimeType","brandHash","ipfsUri","identityTopicId","hederaTransactionId","mintedAt","status"],"properties":{"id":{"type":"string"},"teamId":{"$ref":"#/components/schemas/TeamId"},"agentId":{"type":["string","null"]},"name":{"type":"string"},"logoDataUrl":{"type":"string"},"logoMimeType":{"type":"string"},"brandHash":{"$ref":"#/components/schemas/HexSha384"},"ipfsUri":{"type":"string"},"identityTopicId":{"type":"string"},"hederaTransactionId":{"type":["string","null"]},"mintedAt":{"type":["string","null"],"format":"date-time"},"status":{"type":"string","enum":["draft","minted"]}}},"BrandMintRequest":{"type":"object","additionalProperties":false,"required":["name","logoBase64","logoMimeType","sha384"],"properties":{"name":{"type":"string"},"agentId":{"type":["string","null"]},"logoBase64":{"type":"string"},"logoMimeType":{"type":"string"},"sha384":{"$ref":"#/components/schemas/HexSha384"}}},"BrandListResponse":{"type":"object","additionalProperties":false,"required":["items"],"properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/AgentBrand"}}}},"AuditLogListResponse":{"type":"object","additionalProperties":false,"required":["items","total"],"properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/AuditLogEntry"}},"total":{"type":"integer"}}},"HederaLedgerStatus":{"type":"object","additionalProperties":false,"required":["network","health","lastConsensusTimestamp","topicId","latencyMs"],"properties":{"network":{"type":"string","enum":["mainnet","testnet","previewnet","mock"]},"health":{"$ref":"#/components/schemas/HederaNetworkHealth"},"lastConsensusTimestamp":{"type":["string","null"],"format":"date-time"},"topicId":{"type":["string","null"]},"latencyMs":{"type":["number","null"]}}},"DashboardMetrics":{"type":"object","additionalProperties":false,"required":["totalDocumentsSigned","documentsPending","documentsAnchored","activeAgentKeys","signingRequests24h","ledger"],"properties":{"totalDocumentsSigned":{"type":"integer"},"documentsPending":{"type":"integer"},"documentsAnchored":{"type":"integer"},"activeAgentKeys":{"type":"integer"},"signingRequests24h":{"type":"integer"},"ledger":{"$ref":"#/components/schemas/HederaLedgerStatus"}}},"ActivityItem":{"type":"object","additionalProperties":false,"required":["id","timestamp","title","detail","event"],"properties":{"id":{"type":"string"},"timestamp":{"$ref":"#/components/schemas/ISODateString"},"title":{"type":"string"},"detail":{"type":"string"},"event":{"$ref":"#/components/schemas/AuditEventType"}}},"DashboardResponse":{"type":"object","additionalProperties":false,"required":["metrics","recentActivity"],"properties":{"metrics":{"$ref":"#/components/schemas/DashboardMetrics"},"recentActivity":{"type":"array","items":{"$ref":"#/components/schemas/ActivityItem"}}}},"ApiError":{"type":"object","additionalProperties":false,"required":["code","message"],"properties":{"code":{"$ref":"#/components/schemas/ApiErrorCode"},"message":{"type":"string"},"details":{"type":"object","additionalProperties":true},"requestId":{"type":"string"},"retryAfterSeconds":{"type":"integer"}}},"ApiErrorResponse":{"type":"object","additionalProperties":false,"required":["error"],"properties":{"error":{"$ref":"#/components/schemas/ApiError"}}}}}}