PearPear

Adjust a Position

Grow or trim an open basket, whole or one leg at a time.

Growing a basket and trimming it are the same call: POST /trade/{positionId}/adjust (SDK: sdk.core.trade.adjust).

An adjust states the legs to change, not a percentage of the basket. Each leg carries reduceOnly, and that flag is what decides whether the leg grows or shrinks.

Add to a position

Give the leg's current side and reduceOnly: false. This adds 250 USD to each side of a long BTC / short ETH basket:

{
  "type": "MARKET",
  "legs": [
    { "symbol": "0", "side": "BUY",  "mode": "USD", "amount": "250", "reduceOnly": false },
    { "symbol": "1", "side": "SELL", "mode": "USD", "amount": "250", "reduceOnly": false }
  ],
  "clientId": "your-client-id"
}

With the SDK:

await sdk.core.trade.adjust(positionId, {
  type: 'MARKET',
  legs: [
    { symbol: '0', side: 'BUY', mode: 'USD', amount: '250', reduceOnly: false },
    { symbol: '1', side: 'SELL', mode: 'USD', amount: '250', reduceOnly: false },
  ],
});

clientId is optional. type accepts only "MARKET".

Trim a position

Give the opposite side and reduceOnly: true, so a long BTC leg is reduced by selling. This takes 200 USD off each side and leaves the rest open:

{
  "type": "MARKET",
  "legs": [
    { "symbol": "0", "side": "SELL", "mode": "USD", "amount": "200", "reduceOnly": true },
    { "symbol": "1", "side": "BUY",  "mode": "USD", "amount": "200", "reduceOnly": true }
  ]
}

reduceOnly passes through to the exchange's reduce-only flag, which stops the order growing the leg or flipping it past flat.

The leg fields

FieldTypeMeaning
symbolstringThe instrument ID, not the ticker.
sideBUY or SELLThe direction to trade in, not the direction the leg currently holds.
modeQUANTITY or USDHow to read amount.
amountdecimal stringAlways unsigned, so "250", never "-250". The direction lives in side and reduceOnly.
reduceOnlybooleanRequired on every leg.

One leg at a time

Nothing requires you to touch every leg. Adjusting one leg alone is valid, and changes the basket's weights:

{
  "type": "MARKET",
  "legs": [
    { "symbol": "0", "side": "SELL", "mode": "USD", "amount": "200", "reduceOnly": true }
  ]
}

To restore the target shares afterwards, rebalance the position.

An adjust can add a leg the basket does not hold

An adjust does not check that symbol is already in the position. Naming an instrument the basket does not hold grows the basket by that leg: a two-leg pair becomes a three-leg basket, and stays that way.

That is a supported way to build out a basket, and an easy typo to make. If you meant to change an existing leg, check the symbol against the position's exposure before you send it.

An adjust pauses auto-rebalance

An adjust that fills at all pauses the position's auto-rebalance config, with pausedReason: "POSITION_CHANGED". The config stops evaluating and does not rebalance until you resume it with PATCH /rebalance/auto/{id}:

{ "status": "ACTIVE" }

Resume keeps the existing baseline. A rebalance the config performs itself never pauses it — only changes you make do.

Rules

Two checks apply only to legs that add size, never to a reduceOnly leg:

CheckRejected with
The leg is too small for the instrument's minimum order sizeInsufficient size for asset
The leg sells a spot instrumentShort selling is not supported for spot markets

A reducing leg skips both, which is what lets you close out a leg that has shrunk below the minimum.

Adjust on a condition

To scale into a position when the market moves rather than now, arm an open trigger against the position: POST /triggers/open with intent: "ADJUST", a positionId, a condition, and the legs to add. It rests off-book and increases the position when the condition is met. See Trigger Order.

The response

The endpoint answers 202 with an execution, and the change lands over the WebSocket as position.updated. When a reduce takes the basket to zero, the position closes and you get position.closed with closedReason: "USER".

On this page