FAQ & Troubleshooting
10. Troubleshooting & User FAQ
Section titled “10. Troubleshooting & User FAQ”RFC 9457 Problem Code Directory
Section titled “RFC 9457 Problem Code Directory”All error responses from DID.is conform to RFC 9457 Problem Details (application/problem+json).
| Problem Code | HTTP Status | Root Cause | Plain-Language Remedy |
|---|---|---|---|
INVALID_DID |
400 |
DID syntax fails W3C ABNF parsing. | Check identifier format (did:<method>:<method-id>). Ensure method names contain only lowercase letters and digits. |
INVALID_DID_URL |
400 |
Malformed fragment, query, or path. | In DID URLs, ensure # is percent-encoded as %23 when passed in HTTP paths. Path dereferencing (did:.../path) is unsupported. |
NOT_FOUND |
404 |
Upstream endpoint returned HTTP 404. | For did:web, verify that /.well-known/did.json is published and publicly accessible over HTTPS. |
EGRESS_BLOCKED |
403 |
Host resolved to private/blocked IP. | DID.is blocks loopback, private subnets, and cloud metadata (169.254.169.254). Target domain must resolve to public IP addresses. |
UPSTREAM_UNAVAILABLE |
502 |
Upstream host timed out or reset. | Upstream server failed to respond within the 4-second egress timeout or dropped the TLS handshake. Check upstream server status. |
PAYLOAD_TOO_LARGE |
413 |
Request or upstream body exceeded cap. | Ingress bodies are capped at 512 KiB; documents at 1 MiB; MCP at 2 MiB. Reduce file size or compress status lists. |
RATE_LIMITED |
429 |
Client IP exceeded token-bucket rate. | Standard rate limit is 120 requests/min. Inspect the Retry-After header and throttle requests accordingly. |
KEY_CAPACITY_EXHAUSTED |
429 |
Project reached key limits. | Projects permit 10 active and 100 retained keys. Revoke unused keys or contact enterprise support to increase retained capacity. |
FEATURE_NOT_SUPPORTED |
501 |
Requested operation is not implemented. | Path dereferencing and custom resolution options are not implemented by policy. |
METHOD_NOT_SUPPORTED |
501 |
DID method is not supported. | Native drivers exist for did:key, did:jwk, did:web, and did:webvh. Other methods (did:ion, did:indy, did:cheqd) are not implemented. |
INVALID_DID_DOCUMENT |
422 |
Document id does not match DID. |
The id property inside the published DID document must exactly match the requested DID string. |
Common Warnings & Resolutions
Section titled “Common Warnings & Resolutions”1. Why does my dossier show RESOLVED_WITH_WARNINGS?
Section titled “1. Why does my dossier show RESOLVED_WITH_WARNINGS?”The DID document resolved, but contains non-fatal specification anomalies. Expand Structural Warnings in Level 4 to view specifics:
- The document references an
@contextURI not present in the offline catalog. - The document declares verification methods that are not bound to any verification relationship (
authentication,assertionMethod, etc.). - Deprecated legacy properties (e.g.,
publicKeyinstead ofverificationMethod) were encountered.
2. Why does my Verifiable Credential status evaluate to INDETERMINATE?
Section titled “2. Why does my Verifiable Credential status evaluate to INDETERMINATE?”DID.is fails closed. A credential evaluates to INDETERMINATE when:
- The revocation Bitstring Status List was unreachable, timed out, or returned an HTTP error.
- The status list’s own signature was invalid or signed by a different issuer.
- The signing key was not explicitly listed in the issuer DID’s
assertionMethodrelationship. - The credential was signed using an unsupported cryptosuite (e.g., RDF-based
eddsa-rdfc-2022).
3. Why does my MCP Server inspection show PROFILE_CHANGED under drift?
Section titled “3. Why does my MCP Server inspection show PROFILE_CHANGED under drift?”PROFILE_CHANGED indicates that DID.is updated its internal canonicalization hash version from an unversioned profile to rfc8785-binary64-v1. This is an internal engine upgrade and does not signify that the remote tool provider altered their code.
4. Why does my did:web show control: NOT_ESTABLISHED?
Section titled “4. Why does my did:web show control: NOT_ESTABLISHED?”By W3C definition, did:web updates are controlled by web hosting and DNS, not by cryptographic update keys. Whoever controls the web server can overwrite did.json at any time without holding a private key. If you require cryptographically enforceable update authority, migrate to did:webvh (verifiable history).
Frequently Asked Questions (FAQ)
Section titled “Frequently Asked Questions (FAQ)”Q: Can I pay to have my identity marked as “Verified” or “Trusted”?
A: No. Verification on DID.is is strictly mathematical and cryptographic. Paid plans unlock higher API volumes, monitoring watches, and webhooks; they never alter verification outcomes.
Q: Does DID.is store copies of my private keys?
A: Never. DID.is is a resolution and verification engine. It only processes public keys. Submitting private keys via did:jwk is explicitly rejected with an error.
Q: How do I prove control of my DID on the public directory?
A: Navigate to /account and create a DID Claim. You can prove control via:
- Key Signature: Sign an ephemeral challenge using a key authorized under
authentication. - HTTPS File: Host the challenge token at
/.well-known/did-is-claim.txt. - DNS TXT Record: Publish the challenge as a
_didis-claimDNS TXT record.
Verified claims remain active for 90 days.
Q: Why doesn’t DID.is support RSA or BLS12-381 keys?
A: DID.is enforces modern, constant-time cryptographic suites with audited implementations. RSA is deprecated for decentralized identity due to key size and attack surface; BLS12-381 pairings require finalized W3C standardization before normative inclusion. Supported suites are Ed25519, NIST P-256, secp256k1, and X25519.
Q: Can I self-host DID.is in an air-gapped environment?
A: Yes. The core daemon (resolver-core) and CLI (didis) can be compiled from source (cargo build -p resolver-core) and executed locally without external internet access. In air-gapped environments, did:key and did:jwk resolve with 100% functionality; network methods (did:web) will report UPSTREAM_UNAVAILABLE.
11. Production Integration Checklist
Section titled “11. Production Integration Checklist”Before deploying applications consuming DID.is in production environments, ensure your architecture satisfies these operational standards:
Rate Limiting & Token Buckets
Section titled “Rate Limiting & Token Buckets”- Handle HTTP 429 responses gracefully by reading the
Retry-Afterheader. - If self-hosting behind reverse proxies (Nginx, Cloudflare), set
DIDIS_TRUST_PROXY=trueto parse client IPs from sanitizedX-Forwarded-Forheaders.
Bounded Work Admission & Concurrency
Section titled “Bounded Work Admission & Concurrency”The core daemon enforces bounded internal concurrency to protect memory:
- 32 concurrent standard operations
- 4 concurrent expensive operations (credential verification, policy evaluation, MCP inspection)
- 8 concurrent live SSE streams
- If limits are reached, the server fails fast with HTTP 503 and
Retry-After: 1. Ensure your client includes automatic jittered retry logic.
Egress Security (SafeHttpClient)
Section titled “Egress Security (SafeHttpClient)”All outbound requests are subject to hardened network constraints:
- Only HTTPS on port 443 is permitted.
- Outbound requests to
127.0.0.1, RFC 1918 private subnets, and cloud metadata (169.254.169.254) are blocked at the DNS resolution stage. - Connections are strictly pinned to public IPs to eliminate DNS rebinding.
Deterministic Offline Context Catalog
Section titled “Deterministic Offline Context Catalog”- JSON-LD
@contextdefinitions are recognized offline viacontext_catalog.rs. - Do not design systems that rely on the resolver fetching custom remote JSON-LD schemas over HTTP. Unrecognized schemas resolve safely with
known: false.