Error Codes
On failure, header.status === 'failure' and body.error = { code, message }. The exception is argument checks done in the connector before any request is sent. selectAddress() called with a non-array, syncAccount() called with a non-array or an invalid item, and setLabel() with a label string that does not match its pattern throw a param_error exception synchronously; setTimeOutMs() with an invalid value throws an INVALID_PARAMS ProviderError — immediately once any request has been made (until popupWindowClose()), otherwise from the next call (see setTimeOutMs); getAddress() / getPublicKey() with a missing chainId / keyPath reject the promise with the same param_error. And sign()'s own input check (for example a non-string or empty method / chainId, a chainId with characters outside its charset, a non-object payload, a missing or empty keyPath, a serialized payload over 65,536 characters): the promise rejects with a ProviderError whose code is the number -32602, and no response object is returned.
Important: the value in body.error.code is the v1 string code (e.g. 'param_error'), not the numeric code. The numeric column below is the internal semantic (JSON-RPC / EIP-1193 / DCENT). Branch on the string.
Catalog
| body.error.code (string) | numeric | standard | meaning / when |
|---|---|---|---|
parse_error | -32700 | JSON-RPC | Payload JSON parse failure — reserved (mapped but no active producer) |
invalid_request | -32600 | JSON-RPC | Malformed request — reserved (mapped but no active producer) |
method_not_found | -32601 | JSON-RPC | The method is not available for this request. Three cases: the network does not support the method at all; the network is supported but the specific operation or payload shape is not (e.g. VeChain multi-clause, HAVAH non-transfer SCORE calls, Stacks unsupported txType, unmodelled Cosmos message types); or, on Cardano, the keyPath purpose rules it out (signData and stake / DRep getPublicKey on legacy m/44') or a witness-analysis check rejects it on m/1852' (all such rejections except an over-long CIP-100 anchor URL, which is param_error -32602) — see Cardano. Read body.error.message for the specific cause. |
param_error | -32602 | JSON-RPC | Bad params — e.g. signMessage called with a non-string message; invalid keyPath (resolves to no currency for the given chainId → routed to a dedicated screen in the bridge popup (the device is not asked)); shape mismatch. (A missing keyPath or bad chainId charset on sign() is caught before sending and rejects instead — see the top of this page.) Most common in practice: an incomplete transaction — the bridge does not fetch consensus values over RPC (Polkadot additionally reads runtime metadata), so a missing nonce / sequence / blockhash fails closed here. |
internal_error | -32603 | JSON-RPC | Bridge internal error — and any bridge code the connector does not map, notably 5008 (a request sent while the USB connection is still waiting for approval on the device screen; retry after approval) and a Tezos device signing failure (-32000). Read body.error.message |
user_cancel | 4001 | EIP-1193 | User rejected at the popup / UI level (account-selection or connection prompt) — distinct from on-device cancel (5004) |
unauthorized | 4100 | EIP-1193 | Popup blocked by the browser (window.open returned null) |
unsupported_method | 4200 | EIP-1193 | Unsupported / unresolvable chain, or device policy rejection (a genuinely unknown method is method_not_found -32601) |
pop-up_closed | 4900 | EIP-1193 | Popup closed (connector) or the device disconnected and auto-reconnect failed (bridge) |
chain_disconnected | 4901 | EIP-1193 | Chain disconnected — reserved. An unknown / unresolvable chainId returns unsupported_method (4200), not 4901 |
device_not_connected | 5001 | DCENT | Device not connected |
device_locked | 5002 | DCENT | Device locked (PIN required) — reserved (no active producer) |
device_timeout | 5003 | DCENT | Hardware response timeout |
user_cancel | 5004 | DCENT | Signature cancelled on the device (connector maps to user_cancel; distinct from popup/UI cancel 4001) |
device_fw_incompatible | 5005 | DCENT | Firmware incompatible |
time_out | 5006 | DCENT | Transport (popup/postMessage) timeout |
protocol_version_mismatch | 5007 | DCENT | connector ↔ bridge protocol major mismatch |
coin_type_error | — | DCENT (v1) | Legacy getAddress(coinType, …) overload only: unsupported coinType (connector isAvaliableCoinType guard). Not emitted on the v2 chainId path |
The request support gate is 2-axis. Before signing, the bridge resolves the request on two axes — chainId and keyPath. An unsupported / unresolvable chainId returns unsupported_method (4200); a chainId whose keyPath matches no currency variant returns param_error (-32602, "Invalid keyPath") and routes to a dedicated screen in the bridge popup (the device is not asked). This chainId→unsupported_method (4200) mapping is on the sign() / signTransaction path; the same two-axis gate applies to getPublicKey as well — an unresolved chainId surfaces as unsupported_method (4200). A family that defines no slot for the requested method still returns -32601 — see the -32601 row above.
Recommended handling
| code | UX |
|---|---|
user_cancel | Offer retry |
method_not_found / unsupported_method | Hide the feature for that network |
param_error | Fix the request shape |
device_not_connected / pop-up_closed | Prompt to connect / unlock |