Grouped reference for SDK clients, indexers, and front-end integrators. Each category names its variants, explains when the contract raises them, and prescribes an SDK-side recovery action the caller can take.
Categories are also available as a stable #[repr(u32)] enum —
ContractErrorCategory — with
ContractError::category() to map
any error to its category at runtime.
Source of truth: contracts/credit/src/types.rs.
Cross-reference: docs/ERROR_CODES.md (categorized reference
with recovery actions).
| Code | Variant | When raised |
|---|---|---|
| 1 | Unauthorized |
Caller is not the expected Address for the operation. |
| 2 | NotAdmin |
Caller invoked an admin-only entrypoint without admin privileges. |
| 32 | AdminNotInitialized |
Admin address has not been set in contract storage. |
Recovery action: Prompt the caller to re-connect a wallet with the correct
role. For AdminNotInitialized, advise the deployer to call init() with a
valid admin address before any admin-gated operation.
| Code | Variant | When raised |
|---|---|---|
| 4 | CreditLineClosed |
Action attempted on a permanently closed credit line. |
| 14 | AlreadyInitialized |
init() called more than once. |
| 20 | CreditLineSuspended |
Draw or admin action on a suspended credit line. |
| 21 | CreditLineDefaulted |
Draw or admin action on a defaulted credit line. |
| 51 | AlreadySettled |
The liquidation for this (borrower, settlement_id) pair has already been processed. |
Recovery action:
CreditLineClosed: No recovery — the line is terminal. Create a new credit line.AlreadyInitialized: No action needed (contract is already live).AlreadySettled: No action needed — the settlement has already been processed.CreditLineSuspended: Wait for admin reinstatement or self-reinstatement (seelifecycle.rs); repayments are still allowed.CreditLineDefaulted: The line is in default; the borrower must either cure via repayment or the position must be liquidated through the auction contract.
| Code | Variant | When raised |
|---|---|---|
| 5 | InvalidAmount |
Amount is zero, negative, or malformed where a positive value was required. |
| 7 | NegativeLimit |
Attempt to set a credit limit below zero. |
| 12 | Overflow |
Arithmetic overflow during checked math (e.g., interest proration, limit |
| calculation). | ||
| 33 | TimestampRegression |
Provided or ledger timestamp is not strictly greater than the stored value. |
| 34 | LimitOutOfBounds |
Credit limit falls outside the configured [min_limit, max_limit] range. |
| 52 | InvalidRiskWeight |
Collateral risk weight exceeds 10 000 bps (100 %). |
Recovery action:
InvalidAmount: Re-validate inputs client-side — ensure draw/repay amounts are positive integers within bounds.NegativeLimit: Clamp or reject the limit value before sending.Overflow: This indicates an arithmetic failure at the protocol level. Retry with a smaller amount or under different rate/accrual conditions; if persistent, file a bug report.TimestampRegression: Likely a client clock issue. Re-sync the caller's ledger view and retry.LimitOutOfBounds: Adjust the proposed limit to[min_limit, max_limit]usingget_protocol_config().InvalidRiskWeight: Ensure risk weight is in0..=10_000bps.
| Code | Variant | When raised |
|---|---|---|
| 6 | OverLimit |
Draw would exceed the borrower's credit limit minus utilized amount. |
| 10 | UtilizationNotZero |
Operation (e.g., limit decrease, closure) requires zero outstanding debt. |
| 13 | LimitDecreaseRequiresRepayment |
Credit limit decrease below the currently utilized amount. |
| 17 | DrawExceedsMaxAmount |
Draw amount exceeds the per-transaction max_draw_amount. |
| 28 | RepayExceedsMaxAmount |
Repay amount exceeds the per-transaction max_repay_amount. |
| 45 | CloseFactorAboveMax |
Supplied close_factor_bps exceeds the protocol-configured maximum. |
| 47 | DrawReversalWindowExpired |
Draw reversal attempted after the allowed reversal window elapsed. |
Recovery action:
OverLimit: Reduce the draw amount to ≤credit_limit - utilized. Queryget_credit_line(borrower)to compute the available headroom.UtilizationNotZero: Repay the outstanding balance first, then retry the operation.LimitDecreaseRequiresRepayment: Repay the excess above the new limit before decreasing.DrawExceedsMaxAmount/RepayExceedsMaxAmount: Split the transaction into smaller chunks or querymax_draw_amount/max_repay_amountfrom protocol config and adjust the input.CloseFactorAboveMax: Reduceclose_factor_bpsto ≤ the protocol max.DrawReversalWindowExpired: Reversal no longer possible; the window has passed.
| Code | Variant | When raised |
|---|---|---|
| 22 | MissingLiquidityToken |
Liquidity token address is not configured. |
| 23 | MissingLiquiditySource |
Liquidity source contract is not configured. |
| 24 | InsufficientLiquidityReserve |
The reserve pool cannot cover the requested draw. |
| 25 | LiquidityTokenCallFailed |
An external call to the liquidity token reverted or returned an error |
| where the contract can observe it. | ||
| 26 | InsufficientRepaymentAllowance |
Borrower's token allowance is below the effective repayment amount. |
| 27 | InsufficientRepaymentBalance |
Borrower's token balance is below the effective repayment amount. |
| 30 | TreasuryNotSet |
Treasury address is not configured when attempting a treasury withdrawal. |
| 31 | ExposureCapExceeded |
Draw would push global TotalUtilized above MaxTotalExposure. |
| 41 | BountyNotSet |
Bounty pool address is not configured. |
Recovery action:
MissingLiquidityToken/MissingLiquiditySource: Inform the admin to complete liquidity configuration; the protocol is not yet operational.InsufficientLiquidityReserve: Wait for the reserve to be replenished, or request admin to add liquidity.LiquidityTokenCallFailed: Retry the transaction. If the token contract is genuinely faulty, the admin must replace it.InsufficientRepaymentAllowance: Guide the borrower to increase the allowance for the contract address.InsufficientRepaymentBalance: Guide the borrower to deposit more tokens into their wallet.TreasuryNotSet: Admin must callset_treasurybefore withdrawing.ExposureCapExceeded: Reduce the draw amount or wait for other borrowers to repay so the global cap frees headroom.BountyNotSet: Admin must callset_bountybefore withdrawing.
| Code | Variant | When raised |
|---|---|---|
| 8 | RateTooHigh |
Interest rate change exceeds max_rate_change_bps or the absolute ceiling. |
| 9 | ScoreTooHigh |
Risk score exceeds the maximum allowed (100). |
| 18 | Paused |
Protocol is paused by the emergency circuit breaker. |
| 29 | DrawCooldownActive |
Borrower attempted to draw before draw_min_interval_seconds elapsed. |
Recovery action:
RateTooHigh: Clamp the rate change withinRateChangeConfigbounds. Queryget_rate_change_config()formax_rate_change_bps.ScoreTooHigh: Normalize the risk score to[0, 100]before submitting.Paused: Inform the user that the protocol is paused. Repayments are still accepted. Retry when the admin unpauses.DrawCooldownActive: Waitdraw_min_interval_secondsfrom the last draw timestamp (available viaget_credit_line(borrower).last_accrual_ts) before retrying.
| Code | Variant | When raised |
|---|---|---|
| 36 | OraclePriceInvalid |
Oracle price is zero, negative, or malformed. |
| 37 | OraclePriceStale |
Oracle price exceeds max_age_seconds since last update. |
| 38 | OraclePriceDeviation |
Oracle price deviation exceeds max_deviation_bps relative to prior. |
| 50 | OracleQuorumNotMet |
Fewer than min_quorum_k prices agree within the deviation bound. |
Recovery action:
OraclePriceInvalid: Ensure the oracle is returning a valid positive price.OraclePriceStale: Wait for an oracle price update, or trigger one via the oracle's push mechanism.OraclePriceDeviation: Circuit-breaker tripped; await a new price within the deviation bound. Do not retry with the same price.OracleQuorumNotMet: Submit prices from more independent oracle feeds.
| Code | Variant | When raised |
|---|---|---|
| 35 | CollateralRatioBelowMinimum |
Collateral withdraw would leave the ratio below MinCollateralRatioBps. |
| 39 | InsufficientCollateralBalance |
Withdrawal amount exceeds the borrower's deposited collateral balance. |
| 50 | CollateralInsufficient |
Collateral is insufficient for the requested operation (general semantic). |
Recovery action: For code 35, reduce the withdrawal amount so that
(post_collateral * MinCollateralRatioBps) / 10_000 >= utilized. Query the
minimum collateral ratio via get_protocol_config() and compute the maximum
safe withdrawal client-side. For code 39, query get_collateral_balance and
ensure the requested amount does not exceed it. For code 50, deposit additional
collateral or reduce the requested operation size until collateral coverage is
adequate.
| Code | Variant | When raised |
|---|---|---|
| 16 | BorrowerBlocked |
Borrower is on the admin-managed block list. |
| 19 | DrawsFrozen |
Global draw freeze is active (admin action for liquidity reserve ops). |
| 40 | BorrowerFrozen |
Borrower's draws are temporarily frozen until the specified expiry timestamp. |
| 46 | CreditLineFrozen |
Credit line draws are frozen by admin (compliance or investigation hold). |
Recovery action:
BorrowerBlocked: The borrower is permanently blocked. No recovery from the SDK side; the borrower must contact the protocol admin.DrawsFrozen: Inform the user that draws are temporarily frozen. Repayments remain open. Retry when the admin unfreezes.BorrowerFrozen: Wait for the freeze to expire (or contact the admin to unfreeze early). The freeze is time-bounded and auto-expires.CreditLineFrozen: Admin-compliance hold; wait forunfreeze_credit_line.
| Code | Variant | When raised |
|---|---|---|
| 11 | Reentrancy |
Reentrant call detected during a cross-contract transfer. |
Recovery action: Do not retry the same transaction — the reentrancy guard prevents the contract from being called again during an ongoing operation. Wait for the current transaction to resolve and inspect the on-chain state before submitting a new call.
| Code | Variant | When raised |
|---|---|---|
| 3 | CreditLineNotFound |
The specified borrower has no credit line. |
| 15 | AdminAcceptTooEarly |
Admin acceptance attempted before the propose_admin delay elapsed. |
| 42 | NoPendingTreasuryWithdrawal |
No pending treasury withdrawal proposal exists. |
| 43 | TreasuryTimelockActive |
The 24-hour treasury timelock has not elapsed. |
| 44 | TreasuryProposalExists |
A treasury withdrawal proposal already exists. |
| 48 | OriginalDrawNotFound |
Original draw audit record not found for reversal. |
| 49 | AttestationBatchNotFound |
No attestation batch has been committed for this borrower. |
| 53 | InvalidAttestation |
Attestation proof is invalid or no batch committed. |
Recovery action:
CreditLineNotFound: Create a credit line first viaopen_credit_line.AdminAcceptTooEarly: Wait for the full delay window to elapse.NoPendingTreasuryWithdrawal: Create a proposal viapropose_treasury_withdrawal.TreasuryTimelockActive: Wait for the 24-hour timelock.TreasuryProposalExists: Execute or cancel the existing proposal first.OriginalDrawNotFound: No reversal possible — no matching draw record.AttestationBatchNotFound: Admin must commit a batch first.
| Category | Codes | Count | Dominant SDK recovery |
|---|---|---|---|
| Auth | 1, 2, 32 | 3 | Reconnect wallet / re-deploy with admin init |
| Lifecycle | 4, 14, 20, 21, 51 | 5 | Await admin action or create new line |
| Numeric | 5, 7, 12, 33, 34, 52 | 6 | Validate inputs / re-sync ledger view |
| Limit | 6, 10, 13, 17, 28, 45, 47 | 7 | Reduce amount or repay first |
| Liquidity | 22, 23, 24, 25, 26, 27, 30, 31, 41 | 9 | Replenish allowance / wait for reserve |
| Risk | 8, 9, 18, 29 | 4 | Clamp inputs / wait for cooldown or unpause |
| Oracle | 36, 37, 38, 50 | 4 | Await valid price feed |
| Collateral | 35, 39 | 2 | Reduce withdrawal amount |
| Block | 16, 19, 40, 46 | 4 | Contact admin or wait for unfreeze / expiry |
| Reentrancy | 11 | 1 | Do not retry; inspect on-chain state |
| Misc | 3, 15, 42, 43, 44, 48, 49 | 7 | Create line first / wait for delay |
| Total | 1–52 | 52 | — |