# Leverage (loop)

Endpoint reference for the 1delta API. Index: https://docs.1delta.io/llms.txt · every endpoint: https://docs.1delta.io/llms-full.txt

---

### GET /v1/actions/loop/leverage

- operationId: `loop-leverage`
- docs: https://docs.1delta.io/1delta-api/loop-leverage/
- markdown: https://docs.1delta.io/1delta-api/loop-leverage.md
- tags: Loop (Actions)

Leverage (loop)

Open a leveraged position via borrow → swap → deposit. Identify the debt market with `marketUidIn` and collateral market with `marketUidOut`. Omit `account` for quote-only (returns `data.quotes` with price deltas). Include `account` to build full transaction calldata (populates `actions` with `alternatives`, `transactions`, and `permissions`).

**Response `actions` fields (when `account` is provided):**
- `alternatives`: DEX aggregator swap transactions sorted best-output-first. Pick one to execute.
- `transactions`: Pre-trade setup — mode/e-mode switch (Aave V3) or collateral enable (Venus). Empty if not needed.
- `permissions`: ERC20 approvals (targeting the composer contract) and lender borrow delegations (targeting the lending protocol contract). Only missing approvals are returned. Execute these first.

**Paying the margin:** which `payAsset` a pair accepts is lender-specific — [`GET /v1/actions/loop/leverage/pay-assets`](https://docs.1delta.io/1delta-api/loop-leverage-pay-assets/) lists them for the same two market uids, and an asset outside that list is refused here as `PAY_ASSET_UNSUPPORTED` (with the accepted set in `details.payAssets`) before anything is quoted.

**Lista DAO fixed-term (brokered) markets:** when `marketUidIn` is brokered, pass `termId` to open the loop's debt leg as a fixed-term broker loan. The collateral deposit leg is handled automatically (routed through the market's `collateralProvider` when set, e.g. slisBNB). Closing such a loop requires the loan's `loanId` on `/v1/actions/loop/close`.

**Trade economics (`data.quotes[i].economics`, best route mirrored at `data.economics`):** a [`TradeEconomics`](#/components/schemas/TradeEconomics) block per route, so a client never re-derives an entry cost or a break-even from the deltas. It carries `entryCostUsd` (swap slippage vs the oracle, day-0 fees off the debt leg's term sheet + the flash fee, gas over the outstanding permissions + main transaction), `carryPerDayUsd` at the PROJECTED rates the same IRM path behind `rateImpact` produces (with and without incentives — `carryBasis` says `sticker` when the projection was unavailable), `breakEvenDays`, `roundTripDays` (the exit ASSUMED symmetric to the entry until a close is quoted — `closeQuoted: false`; null on a debt with no early exit), the trade's clock (`horizonDays`: PT expiry, debt maturity, rolling term) and `breaksEvenBeforeHorizon`. With an `account`, `existingExposure` makes it MARGINAL to the book the trade lands in: the debt the account already holds in the same market reprices with the new borrow, and that cost is netted out of the carry. Whatever could not be computed is `null` with a line in `notes` — the block itself is never omitted. Gas is a real `eth_estimateGas` when it succeeds (`gas.estimated`), a typical-size table otherwise; on a quote-only request it is not priced.

**Parameters**

| Name | In | Type | Required | Description |
| --- | --- | --- | --- | --- |
| `route` | query | "auto" \| "bundler3" \| "native" \| "composer" \| "proxy" | no | Which assembly to use, for lenders that have more than one. **Morpho Blue only** today. - *(omitted)* — `auto`: prefer the protocol’s own tooling and fall back to the composer for anything it cannot express (a cross-market pair, a margin paid in a foreign asset, an `EXACT_OUTPUT` close, a chain with no bundler3 or no swap adapter). - `bundler3` / `native` — force Morpho’s bundler3. A request it cannot serve becomes an ERROR instead of silently falling back, which is what makes the route testable. - `composer` / `proxy` — force the 1delta composer. The default matters: the bundler3 route asks for `setAuthorization(GeneralAdapter1)`, Morpho’s own audited adapter, where the composer route asks for a standing grant on ours. |
| `marketUidIn` | query | string | yes | Market identifier for input side (`lender:chainId:address`). |
| `marketUidOut` | query | string | yes | Market identifier for output side (`lender:chainId:address`). |
| `slippage` | query | number | yes | Slippage tolerance (basis points) |
| `account` | query | string | no | Account address. Include to build transaction, omit for quote-only. |
| `debtAmount` | query | string | yes | Debt amount in wei |
| `payAsset` | query | string | no | Asset the margin is paid in (optional zap-in asset). Which assets a given pair accepts is LENDER-SPECIFIC — the collateral, the debt, and native when the wrapped native is one of the two on the composer lenders; collateral only on Curvance / Fraxlend / Resupply / Twyne; no native on LlamaLend; the debt asset only on Exactly; the collateral (or native into a WETH collateral) on Flying Tulip, whose open is a signed flow: answers carry one `actions.signs[0]` step each until none is owed. Ask [`GET /v1/actions/loop/leverage/pay-assets`](https://docs.1delta.io/1delta-api/loop-leverage-pay-assets/) with the same `marketUidIn` / `marketUidOut` to list them in advance. An asset outside that list is refused up front with `PAY_ASSET_UNSUPPORTED`, `details.payAssets` carrying the accepted set (Twyne excepted — it answers `ZAP_REQUIRED` with a swap quote instead). Native is the zero address. |
| `payAmount` | query | string | no | Pay amount in wei |
| `hedge` | query | "boros" | no | `boros` — attach `data.hedge`: the Pendle Boros SHORT that locks the perp FUNDING the new collateral earns (sUSDe, wstUSR …) at a fixed rate, sized on the best route’s collateral USD × `hedgeRatio`. A second set of transactions on ARBITRUM (42161), never part of the loop bundle and not atomic with it; `available: false` + `reason` when the collateral earns no funding. Tuning: `hedgeRatio` (default 1), `hedgeTenor` (longest\|nearest), `hedgeExposure` (ethena\|resolv), `hedgeMarketIds`, `hedgeMarginBuffer`, `hedgeSlippage` (bps of APR). See [`/v1/actions/boros/hedge`](https://docs.1delta.io/1delta-api/boros-hedge/). |
| `marginFromAccountId` | query | integer | no | **Dolomite only.** Fund the margin from this existing Dolomite sub-account instead of the wallet, collapsing the open to ONE transaction: the transfer rides inside the leverage call and no deposit or token approval is emitted. Omit to pull `payAmount` from the wallet (two transactions — Dolomite's trader proxy can only move funds between the caller's own sub-accounts). `0` is the default sub-account and a valid source. Passing the trade account's own id is treated as absent, since the margin is already there. The source must hold `payAmount` of the pay asset or the transaction reverts. |
| `leverage` | query | number | no | Target leverage multiplier |
| `usePendleMintRedeem` | query | boolean | no | Use Pendle mint/redeem |
| `borrowMode` | query | 0 \| 1 \| 2 | no | Borrow mode (0=NONE, 1=STABLE, 2=VARIABLE) |
| `termId` | query | integer | no | **Lista DAO fixed-term (brokered) debt markets only.** Selects the fixed term to borrow for the loop's debt leg, from the debt market's `terms[]` rate card (the `MarketTerm.termId`). Required when `marketUidIn` is a brokered market — the borrow leg routes through the broker; ignored otherwise. |
| `posId` | query | string | no | **Twyne only.** Which collateral vault to lever — a Twyne position is a contract the borrower deploys, and one account may own several in a market, each with its own collateral, debt and liquidation LTV. Omit when the account owns exactly one (or none). Passing none while owning several is refused rather than guessed. |
| `liqLtv` | query | integer | no | **Twyne only, and only when the account owns NO vault in this market yet.** The liquidation LTV (1e4 scale) the position this call DEPLOYS will carry. The deploy runs as the first item of the same EVC batch, so a first-time borrower opens a leveraged position in one transaction; the response then carries `createdPosition` and a `collateralVault` address that does not exist until the transaction lands. Defaults to the market’s LIVE ceiling (`maxTwyneLTVs`) — the extra LTV is the reason to borrow here, and the value is not a commitment: `setTwyneLiqLTV` moves it at any time with no cooldown, and lowering it RELEASES reserved credit and lowers what the borrower pays. Must sit inside the live band (`externalLiqLTV × externalLiqBuffer` … `maxTwyneLTVs`); both bounds move, so a value is validated against a fresh read and refused by name rather than reverting `ValueOutOfRange()` on chain. Ignored when a position already exists — moving an existing dial is `/v1/actions/twyne/set-liq-ltv`. |
| `accountId` | query | string | no | Account ID (Init Capital, Euler V2, Dolomite). Dolomite: a uint256 account number, or `iso:<marketId>:<n>` for a position inside an isolation-mode vault (dGM, dsavETH, dGMX …); borrow positions on those need n >= 100, account 0 is the supply-only vault balance. |
| `selectedMode` | query | integer | no | Position mode for new positions (Init Capital) |

**Response `200`** — Quote or full build response

| Field | Type | Description |
| --- | --- | --- |
| `success` | true |  |
| `data` | object | Informational data (quotes, simulation results, etc.) |
| `data.lender` | string | Protocol identifier |
| `data.quotes` | object[] | Candidate routes, best output first. Execute exactly one. |
| `data.quotes[].deltas` | object |  |
| `data.quotes[].deltas.aggregator` | string | Aggregator source |
| `data.quotes[].deltas.tradeInput` | number | Trade input amount |
| `data.quotes[].deltas.tradeOutput` | number | Trade output amount |
| `data.quotes[].deltas.deltas` | object | Balance deltas |
| `data.quotes[].rateImpact` | object[] | Projected interest-rate impact per market for THIS quote (its own trade amounts). Omitted if IRM data is unavailable. |
| `data.quotes[].rateImpact[].marketUid` | string | Market identifier (format: `lender:chainId:address`) |
| `data.quotes[].rateImpact[].utilization` | object | A current/projected pair for a single rate metric. |
| `data.quotes[].rateImpact[].utilization.current` | number | Current value |
| `data.quotes[].rateImpact[].utilization.projected` | number | Projected value after the action |
| `data.quotes[].rateImpact[].borrowRate` | object | A current/projected pair for a single rate metric. |
| `data.quotes[].rateImpact[].borrowRate.current` | number | Current value |
| `data.quotes[].rateImpact[].borrowRate.projected` | number | Projected value after the action |
| `data.quotes[].rateImpact[].depositRate` | object | A current/projected pair for a single rate metric. |
| `data.quotes[].rateImpact[].depositRate.current` | number | Current value |
| `data.quotes[].rateImpact[].depositRate.projected` | number | Projected value after the action |
| `data.quotes[].rateImpact[].intrinsicYield` | number | The asset's own yield in percent (LST staking yield, RWA NAV growth, a Gearbox quota rate as a negative), size-invariant, ADDED to both sides: earned on a deposit, forgone on a borrow. Absent when the lender meta was not readable when the response was built — never defaulted to 0 in that case. |
| `data.quotes[].rateImpact[].depositRewardApr` | number | Sum of reward-stream APRs (%) on the deposit side. Absent with `intrinsicYield`. |
| `data.quotes[].rateImpact[].borrowRewardApr` | number | Sum of reward-stream APRs (%) rebated on the borrow side. Absent with `intrinsicYield`. |
| `data.quotes[].rateImpact[].effectiveDepositRate` | object | A current/projected pair for a single rate metric. |
| `data.quotes[].rateImpact[].effectiveDepositRate.current` | number | Current value |
| `data.quotes[].rateImpact[].effectiveDepositRate.projected` | number | Projected value after the action |
| `data.quotes[].rateImpact[].effectiveBorrowRate` | object | A current/projected pair for a single rate metric. |
| `data.quotes[].rateImpact[].effectiveBorrowRate.current` | number | Current value |
| `data.quotes[].rateImpact[].effectiveBorrowRate.projected` | number | Projected value after the action |
| `data.quotes[].rateImpact[].flat` | boolean | True when the market has no utilization curve to shift (Morpho Blue collateral, a fixed-rate broker): current === projected, taken from the published rates, and `utilization` is NaN. Present so the leg is not silently missing from a position preview. |
| `data.quotes[].netApr` | object | The trade's carry at post-trade rates — the position net APR. `annualUsd` is the change in yearly carry the trade causes (deposit/withdraw legs earn, borrow/repay legs cost); `aprPct` puts it on the net equity the trade moves (the margin on an open) and is null when that equity is not positive (a pure leverage step, a swap). The bare figures exclude rewards; `*Total` include them. |
| `data.quotes[].netApr.annualUsd` | number |  |
| `data.quotes[].netApr.annualUsdTotal` | number |  |
| `data.quotes[].netApr.equityUsd` | number |  |
| `data.quotes[].netApr.aprPct` | number |  |
| `data.quotes[].netApr.aprPctTotal` | number |  |
| `data.quotes[].netApr.legs` | object[] |  |
| `data.quotes[].netApr.legs[].marketUid` | string | Market identifier, formatted `lender:chainId:address`. |
| `data.quotes[].netApr.legs[].side` | "deposit" \| "borrow" \| "withdraw" \| "repay" |  |
| `data.quotes[].netApr.legs[].usd` | number | Absolute USD size of the leg. |
| `data.quotes[].netApr.legs[].ratePct` | number | Effective PROJECTED rate (IRM + intrinsic, %) the leg is priced at; the bare IRM rate where the overlay was unavailable. |
| `data.quotes[].netApr.legs[].ratePctTotal` | number | ratePct with rewards folded in (+ on an earning leg, − on a paying leg). |
| `data.quotes[].economics` | object | THIS route's trade economics — `TradeEconomics` on an open, `CloseEconomics` on a close. See the schema for the discipline. |
| `data.quotes[].economics.notionalUsd` | object | The position this route creates, at the oracle. `equity` is the margin the user brings (0 on a pure leverage step). |
| `data.quotes[].economics.notionalUsd.equity` | number |  |
| `data.quotes[].economics.notionalUsd.collateral` | number |  |
| `data.quotes[].economics.notionalUsd.debt` | number |  |
| `data.quotes[].economics.entryCostUsd` | object | Day-0 cost of getting in. `slippage` = swap input at the oracle − swap output at the oracle (floored at 0; `slippageBp` keeps the sign). `gas` is null when it could not be priced. |
| `data.quotes[].economics.entryCostUsd.slippage` | number |  |
| `data.quotes[].economics.entryCostUsd.fees` | number |  |
| `data.quotes[].economics.entryCostUsd.gas` | number |  |
| `data.quotes[].economics.entryCostUsd.total` | number |  |
| `data.quotes[].economics.slippageBp` | number | Signed swap-vs-oracle, BP of the swap input. Negative = the route costs money. |
| `data.quotes[].economics.entryCostBp` | number | `entryCostUsd.total` over the DEBT notional, BP. |
| `data.quotes[].economics.fees` | object[] |  |
| `data.quotes[].economics.fees[].id` | string | The term sheet's `FeeTerm.id` (`origination`, `early-repay-penalty`, …) or `flash` for the flash-loan fee. |
| `data.quotes[].economics.fees[].label` | string |  |
| `data.quotes[].economics.fees[].when` | "entry" \| "exit" | `entry` items sum to `entryCostUsd.fees`; `exit` items are in the round-trip exit cost. |
| `data.quotes[].economics.fees[].usd` | number | Priced on the notional the fee is charged on. Negative = a rebate. |
| `data.quotes[].economics.fees[].value` | number | The published rate (read with `unit`). |
| `data.quotes[].economics.fees[].unit` | string | `percent` \| `bps` \| … |
| `data.quotes[].economics.fees[].basis` | string | `principal` \| `face-value` \| `collateral` \| … |
| `data.quotes[].economics.fees[].mutable` | boolean | Governance-mutable snapshot — re-verify before quoting it as a term. |
| `data.quotes[].economics.carryPerDayUsd` | object | The trade's carry per day at PROJECTED rates — what it earns after its own borrow has moved the pool. `total` counts incentives, `base` does not. With an account, the repricing of the existing book is netted out. |
| `data.quotes[].economics.carryPerDayUsd.total` | number |  |
| `data.quotes[].economics.carryPerDayUsd.base` | number |  |
| `data.quotes[].economics.carryBasis` | "projected" \| "sticker" \| "none" |  |
| `data.quotes[].economics.breakEvenDays` | object | `entryCostUsd.total / carryPerDayUsd`. Null when the carry is not positive (never pays for itself — see `notes`) or unknown. |
| `data.quotes[].economics.breakEvenDays.total` | number |  |
| `data.quotes[].economics.breakEvenDays.base` | number |  |
| `data.quotes[].economics.roundTripDays` | object | `(entry + exit cost) / carry`. `closeQuoted` says whether the exit was PRICED (a real close quote) or ASSUMED symmetric to the entry (the default today). Null on a debt that cannot be repaid early (Midnight): the round trip is at maturity, not before. |
| `data.quotes[].economics.roundTripDays.total` | number |  |
| `data.quotes[].economics.roundTripDays.base` | number |  |
| `data.quotes[].economics.roundTripDays.closeQuoted` | boolean |  |
| `data.quotes[].economics.roundTripDays.exitCostUsd` | number |  |
| `data.quotes[].economics.horizonDays` | number | Days until the trade's clock runs out. Null = perpetual. |
| `data.quotes[].economics.horizon` | object |  |
| `data.quotes[].economics.horizon.kind` | "perpetual" \| "to-expiry" \| "to-maturity" \| "rolling" |  |
| `data.quotes[].economics.horizon.endsAt` | integer | Unix seconds. |
| `data.quotes[].economics.horizon.source` | string |  |
| `data.quotes[].economics.breaksEvenBeforeHorizon` | boolean |  |
| `data.quotes[].economics.gas` | object |  |
| `data.quotes[].economics.gas.units` | number | Gas units over the whole bundle — outstanding permissions + main transaction. |
| `data.quotes[].economics.gas.txCount` | integer |  |
| `data.quotes[].economics.gas.estimated` | boolean | `true` when every transaction was `eth_estimateGas`-ed from the account; `false` when at least one used the typical-size table (the `notes` say which — the main transaction usually reverts under estimation until its permissions are granted). |
| `data.quotes[].economics.gas.gasPriceGwei` | number |  |
| `data.quotes[].economics.gas.nativePriceUsd` | number |  |
| `data.quotes[].economics.gas.usd` | number |  |
| `data.quotes[].economics.existingExposure` | object | The marginal view — what this trade does to the account it lands in. The new borrow moves the pool rate, and the debt the account ALREADY holds in that market reprices with it: an ongoing cost the one-off slippage never shows. Same on the deposit side with the opposite sign. |
| `data.quotes[].economics.existingExposure.debtUsdSameMarket` | number | Debt already held in the DEBT market, USD. |
| `data.quotes[].economics.existingExposure.depositUsdSameMarket` | number | Deposits already held in the COLLATERAL market, USD. |
| `data.quotes[].economics.existingExposure.rateDeltaBp` | number | Projected − current borrow rate on the debt market, BP. |
| `data.quotes[].economics.existingExposure.depositRateDeltaBp` | number | Projected − current deposit rate on the collateral market, BP. |
| `data.quotes[].economics.existingExposure.repriceCostPerDayUsd` | number | Repricing of the existing book per day (debt repriced up minus deposits repriced up). Positive = a cost. Already netted out of `carryPerDayUsd`. |
| `data.quotes[].economics.existingExposure.accountAprPre` | number | Account net APR before the trade, percent, rewards included. |
| `data.quotes[].economics.existingExposure.accountAprPost` | number | Account net APR after the trade at PROJECTED rates, percent. |
| `data.quotes[].economics.existingExposure.accountNavUsd` | number |  |
| `data.quotes[].economics.existingExposure.accountNavUsdPost` | number |  |
| `data.quotes[].economics.notes` | string[] | Every assumption and every input that was missing, in words. Read them before showing a number. |
| `data.quotes[].economics.notionalUsd.collateralRemoved` | number |  |
| `data.quotes[].economics.notionalUsd.debtRepaid` | number |  |
| `data.quotes[].economics.notionalUsd.equityFreed` | number |  |
| `data.quotes[].economics.exitCostUsd` | object |  |
| `data.quotes[].economics.exitCostUsd.slippage` | number |  |
| `data.quotes[].economics.exitCostUsd.fees` | number |  |
| `data.quotes[].economics.exitCostUsd.gas` | number |  |
| `data.quotes[].economics.exitCostUsd.total` | number |  |
| `data.quotes[].economics.exitCostBp` | number | `exitCostUsd.total` over the debt repaid, BP. |
| `data.quotes[].economics.carryForgonePerDayUsd` | object |  |
| `data.quotes[].economics.carryForgonePerDayUsd.total` | number |  |
| `data.quotes[].economics.carryForgonePerDayUsd.base` | number |  |
| `data.quotes[].economics.daysOfCarry` | object |  |
| `data.quotes[].economics.daysOfCarry.total` | number |  |
| `data.quotes[].economics.daysOfCarry.base` | number |  |
| `data.rateImpact` | object[] | Projected interest-rate impact per market. Single-market actions produce 1 entry; loop actions produce 2. Null if IRM data is unavailable. |
| `data.rateImpact[].marketUid` | string | Market identifier (format: `lender:chainId:address`) |
| `data.rateImpact[].utilization` | object | A current/projected pair for a single rate metric. |
| `data.rateImpact[].utilization.current` | number | Current value |
| `data.rateImpact[].utilization.projected` | number | Projected value after the action |
| `data.rateImpact[].borrowRate` | object | A current/projected pair for a single rate metric. |
| `data.rateImpact[].borrowRate.current` | number | Current value |
| `data.rateImpact[].borrowRate.projected` | number | Projected value after the action |
| `data.rateImpact[].depositRate` | object | A current/projected pair for a single rate metric. |
| `data.rateImpact[].intrinsicYield` | number | The asset's own yield in percent (LST staking yield, RWA NAV growth, a Gearbox quota rate as a negative), size-invariant, ADDED to both sides: earned on a deposit, forgone on a borrow. Absent when the lender meta was not readable when the response was built — never defaulted to 0 in that case. |
| `data.rateImpact[].depositRewardApr` | number | Sum of reward-stream APRs (%) on the deposit side. Absent with `intrinsicYield`. |
| `data.rateImpact[].borrowRewardApr` | number | Sum of reward-stream APRs (%) rebated on the borrow side. Absent with `intrinsicYield`. |
| `data.rateImpact[].effectiveDepositRate` | object | A current/projected pair for a single rate metric. |
| `data.rateImpact[].effectiveBorrowRate` | object | A current/projected pair for a single rate metric. |
| `data.rateImpact[].flat` | boolean | True when the market has no utilization curve to shift (Morpho Blue collateral, a fixed-rate broker): current === projected, taken from the published rates, and `utilization` is NaN. Present so the leg is not silently missing from a position preview. |
| `data.netApr` | object | The trade's carry at post-trade rates — the position net APR. `annualUsd` is the change in yearly carry the trade causes (deposit/withdraw legs earn, borrow/repay legs cost); `aprPct` puts it on the net equity the trade moves (the margin on an open) and is null when that equity is not positive (a pure leverage step, a swap). The bare figures exclude rewards; `*Total` include them. |
| `data.economics` | object | The first (best) quote's `economics`, mirrored. |
| `data.flashFeeBps` | number | Fee of the flash source the bundle uses, BPS — priced in `economics.fees` as `flash`. Absent when no flash is used. |
| `actions` | object | Transaction calldata and approvals. Null for quote-only responses (no account provided). |

**Example response**

```json
{
  "success": true,
  "data": {
    "lender": "AAVE_V3",
    "quotes": [
      {
        "deltas": {
          "aggregator": "string",
          "tradeInput": 1,
          "tradeOutput": 1,
          "deltas": {}
        },
        "rateImpact": [
          {
            "marketUid": "AAVE_V3:8453:0x4200000000000000000000000000000000000006",
            "utilization": {
              "current": 1,
              "projected": 1
            },
            "borrowRate": {
              "current": 1,
              "projected": 1
            },
            "depositRate": {
              "current": 1,
              "projected": 1
            },
            "intrinsicYield": 10.37,
            "depositRewardApr": 1,
            "borrowRewardApr": 1,
            "effectiveDepositRate": {
              "current": 1,
              "projected": 1
            },
            "effectiveBorrowRate": {
              "current": 1,
              "projected": 1
            },
            "flat": true
          }
        ],
        "netApr": {
          "annualUsd": 1,
          "annualUsdTotal": 1,
          "equityUsd": 1,
          "aprPct": 1,
          "aprPctTotal": 1,
          "legs": [
            {
              "marketUid": "AAVE_V3:1:0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2",
              "side": "deposit",
              "usd": 1,
              "ratePct": 1,
              "ratePctTotal": 1
            }
          ]
        },
        "economics": {
          "notionalUsd": {
            "equity": 1,
            "collateral": 1,
            "debt": 1
          },
          "entryCostUsd": {
            "slippage": 1,
            "fees": 1,
            "gas": 1,
            "total": 1
          },
          "slippageBp": 1,
          "entryCostBp": 1,
          "fees": [
            {
              "id": "string",
              "label": "string",
              "when": "entry",
              "usd": 1,
              "value": 1,
              "unit": "string",
              "basis": "string",
              "mutable": true
            }
          ],
          "carryPerDayUsd": {
            "total": 1,
            "base": 1
          },
          "carryBasis": "projected",
          "breakEvenDays": {
            "total": 1,
            "base": 1
          },
          "roundTripDays": {
            "total": 1,
            "base": 1,
            "closeQuoted": true,
            "exitCostUsd": 1
          },
          "horizonDays": 1,
          "horizon": {
            "kind": "perpetual",
            "endsAt": 1,
            "source": "string"
          },
          "breaksEvenBeforeHorizon": true,
          "gas": {
            "units": 1,
            "txCount": 1,
            "estimated": true,
            "gasPriceGwei": 1,
            "nativePriceUsd": 1,
            "usd": 1
          },
          "existingExposure": {
            "debtUsdSameMarket": 1,
            "depositUsdSameMarket": 1,
            "rateDeltaBp": 1,
            "depositRateDeltaBp": 1,
            "repriceCostPerDayUsd": 1,
            "accountAprPre": 1,
            "accountAprPost": 1,
            "accountNavUsd": 1,
            "accountNavUsdPost": 1
          },
          "notes": [
            "string"
          ]
        }
      }
    ],
    "rateImpact": [
      {
        "marketUid": "AAVE_V3:8453:0x4200000000000000000000000000000000000006",
        "utilization": {
          "current": 1,
          "projected": 1
        },
        "borrowRate": {
          "current": 1,
          "projected": 1
        },
        "depositRate": {
          "current": 1,
          "projected": 1
        },
        "intrinsicYield": 10.37,
        "depositRewardApr": 1,
        "borrowRewardApr": 1,
        "effectiveDepositRate": {
          "current": 1,
          "projected": 1
        },
        "effectiveBorrowRate": {
          "current": 1,
          "projected": 1
        },
        "flat": true
      }
    ],
    "netApr": {
      "annualUsd": 1,
      "annualUsdTotal": 1,
      "equityUsd": 1,
      "aprPct": 1,
      "aprPctTotal": 1,
      "legs": [
        {
          "marketUid": "AAVE_V3:1:0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2",
          "side": "deposit",
          "usd": 1,
          "ratePct": 1,
          "ratePctTotal": 1
        }
      ]
    },
    "economics": {
      "notionalUsd": {
        "equity": 1,
        "collateral": 1,
        "debt": 1
      },
      "entryCostUsd": {
        "slippage": 1,
        "fees": 1,
        "gas": 1,
        "total": 1
      },
      "slippageBp": 1,
      "entryCostBp": 1,
      "fees": [
        {
          "id": "string",
          "label": "string",
          "when": "entry",
          "usd": 1,
          "value": 1,
          "unit": "string",
          "basis": "string",
          "mutable": true
        }
      ],
      "carryPerDayUsd": {
        "total": 1,
        "base": 1
      },
      "carryBasis": "projected",
      "breakEvenDays": {
        "total": 1,
        "base": 1
      },
      "roundTripDays": {
        "total": 1,
        "base": 1,
        "closeQuoted": true,
        "exitCostUsd": 1
      },
      "horizonDays": 1,
      "horizon": {
        "kind": "perpetual",
        "endsAt": 1,
        "source": "string"
      },
      "breaksEvenBeforeHorizon": true,
      "gas": {
        "units": 1,
        "txCount": 1,
        "estimated": true,
        "gasPriceGwei": 1,
        "nativePriceUsd": 1,
        "usd": 1
      },
      "existingExposure": {
        "debtUsdSameMarket": 1,
        "depositUsdSameMarket": 1,
        "rateDeltaBp": 1,
        "depositRateDeltaBp": 1,
        "repriceCostPerDayUsd": 1,
        "accountAprPre": 1,
        "accountAprPost": 1,
        "accountNavUsd": 1,
        "accountNavUsdPost": 1
      },
      "notes": [
        "string"
      ]
    },
    "flashFeeBps": 1
  },
  "actions": {
    "transactions": [
      {
        "chainType": "evm",
        "to": "0x87870Bca3F3fD6335C3F4ce8392D69350B4fA4E2",
  
… truncated
```

**Response `400`** — Validation error

**Response `429`** — Rate limited. Unauthenticated callers share a per-IP budget; send an `x-api-key` header to lift it. Retry with exponential backoff.

**Response `500`** — Unexpected server error. Safe to retry with backoff.

**Response `502`** — An upstream data source or protocol origin failed (`error.code` is `ORIGIN_FAILED`). `error.details` carries the per-origin status. This is also what a missing or malformed required parameter currently returns, rather than a 400.
