Orders
How it works
Orders on Velocity go through a multi-stage matching process. When you place an order, it enters a JIT auction (Just-In-Time) where market makers can compete to fill it at better prices. If no one fills during the auction, the order either executes against the DLOB (Decentralized Limit Order Book) or the AMM as a fallback. This design ensures you get the best price from multiple liquidity sources.
Orders are stored in your user account and have both an onchain order ID and an optional user-assigned ID for tracking. When an order fills, your position updates automatically, and you can query fill events to see execution details.
Perp markets only. Velocity’s spot markets are collateral/borrow-lend only — the spot DLOB (order-book trading on spot markets) was removed. placeSpotOrder, placeAndTakeSpotOrder, placeAndMakeSpotOrder, fillSpotOrder, and their getXIx builders all throw at runtime (SpotDlobTradingDisabled). Everything on this page applies to perp orders.
Order Types
| Type | Description |
|---|---|
MARKET | Executes immediately. Goes through a JIT auction first (controlled by auctionStartPrice, auctionEndPrice, auctionDuration), then fills against the DLOB or AMM. |
LIMIT | Rests on the DLOB at a fixed price until filled or canceled. Set postOnly: PostOnlyParams.MUST_POST_ONLY to guarantee maker status and avoid crossing the spread. |
ORACLE | Like a market order, but auction prices and the resting limit price are expressed as offsets from the oracle price (not absolute prices). Useful for market makers who want tight spreads without hardcoding prices. |
TRIGGER_MARKET | A stop/take-profit market order. Executes as a market order when the oracle price crosses triggerPrice in the specified triggerCondition direction. |
TRIGGER_LIMIT | A stop/take-profit limit order. Same trigger mechanism as TRIGGER_MARKET, but executes as a limit order at price once triggered. |
Post-Only Params
When placing limit orders, you can control maker/taker behavior with postOnly:
| Value | Behavior |
|---|---|
PostOnlyParams.NONE | Order can be maker or taker (default) |
PostOnlyParams.MUST_POST_ONLY | Transaction fails if the order would cross the spread |
PostOnlyParams.TRY_POST_ONLY | Order is silently skipped (not placed) if it would cross; tx succeeds |
PostOnlyParams.SLIDE | Order price is adjusted one tick inside the spread to guarantee maker status |
oraclePriceOffset is a BN
OrderParams.oraclePriceOffset (and Order.oraclePriceOffset on filled orders) is a signed BN in PRICE_PRECISION (1e6) units — it was widened from number to BN (i64 on-chain). Always wrap raw numbers with new BN(...); passing a plain JS number will fail type-checking (and, if bypassed, will not round-trip correctly through Borsh encoding).
import { BN, PRICE_PRECISION } from "@velocity-exchange/sdk";
// +$0.30 above oracle
const oraclePriceOffset = new BN(0.3 * PRICE_PRECISION.toNumber());
// or, using client precision helpers:
const oraclePriceOffset2 = velocityClient.convertToPricePrecision(0.3); // already a BNSDK Usage
This page focuses on placing and canceling perp orders via VelocityClient. For concise examples we use helper builders like getMarketOrderParams(...).
Build Market Order Params
import { BN, BASE_PRECISION, MarketType, PositionDirection, getMarketOrderParams } from "@velocity-exchange/sdk";
const orderParams = getMarketOrderParams({
marketIndex: 0,
marketType: MarketType.PERP,
direction: PositionDirection.LONG,
baseAssetAmount: new BN(1).mul(BASE_PRECISION), // 1 SOL (in 1e9 precision)
});Function getMarketOrderParamsReference ↗
Function getMarketOrderParamsReference ↗Builds `OptionalOrderParams` for a market order (`OrderType.MARKET`), filled immediately via a Dutch auction between `auctionStartPrice` and `auctionEndPrice` (defaults derived on-chain from the oracle price if omitted) over `auctionDuration` slots.
| Parameter | Type | Required |
|---|---|---|
params | Omit<OptionalOrderParams, "orderType">Order fields (see `OrderParams`); `baseAssetAmount` is in BASE_PRECISION (1e9),
any price fields are in PRICE_PRECISION (1e6). `orderType` is set automatically and must not be
passed in. | Yes |
Params merged onto `DefaultOrderParams`, ready to pass to `placeOrder`/`placePerpOrder`.
| Returns |
|---|
OptionalOrderParams |
Build Order Params (Generic Helper)
If you want a single helper that works for limit/market/oracle/trigger, use getOrderParams(...).
import { getOrderParams, OrderType, PositionDirection } from "@velocity-exchange/sdk";
const orderParams = getOrderParams({
orderType: OrderType.LIMIT,
marketIndex: 0,
direction: PositionDirection.LONG,
baseAssetAmount: velocityClient.convertToPerpPrecision(1), // 1 base unit → BN(1e9)
price: velocityClient.convertToPricePrecision(21.23), // $21.23 → BN(21_230_000)
});Function getOrderParamsReference ↗
Function getOrderParamsReference ↗Merges `optionalOrderParams` onto `DefaultOrderParams` (filling in any field the caller omitted, e.g. `marketType: MarketType.PERP`, `reduceOnly: false`, no trigger/oracle-offset), then applies `overridingParams` on top of that. Used internally by the `get*OrderParams` factories; call it directly only if you need to force a field that a factory doesn't expose.
example: ``` const orderParams = getOrderParams(optionalOrderParams, { marketType: MarketType.PERP }); ```
| Parameter | Type | Required |
|---|---|---|
optionalOrderParams | OptionalOrderParamsRequired order fields plus any optional `OrderParams` overrides. | Yes |
overridingParams | Record<string, any>Fields applied last, taking precedence over both the defaults and
`optionalOrderParams`. | No |
A fully-populated `OrderParams` object.
| Returns |
|---|
OrderParams |
Place a Perp Order
// Assumes `velocityClient` is subscribed.
const txSig = await velocityClient.placePerpOrder(
getMarketOrderParams({
marketIndex: 0,
direction: PositionDirection.LONG,
baseAssetAmount: new BN(1).mul(BASE_PRECISION),
})
);
console.log(txSig);Method VelocityClient.placePerpOrderReference ↗
Method VelocityClient.placePerpOrderReference ↗| Parameter | Type | Required |
|---|---|---|
orderParams | OptionalOrderParamsOrder to place; `baseAssetAmount` is BASE_PRECISION (1e9), `price` /
`triggerPrice` / `oraclePriceOffset` (signed) / `auctionStartPrice` / `auctionEndPrice` are
PRICE_PRECISION (1e6). | Yes |
txParams | TxParamsOptional compute-unit/priority-fee overrides. | No |
subAccountId | numberSub-account to place the order for; defaults to the active sub-account. | No |
isolatedPositionDepositAmount | anyIf set and the order increases the position, a transfer
into an isolated-margin position (token-mint precision) is prepended in the same transaction. | No |
| Returns |
|---|
Promise<string> |
Place Multiple Orders
await velocityClient.placeOrders([
{
orderType: OrderType.LIMIT,
marketType: MarketType.PERP,
marketIndex: 0,
direction: PositionDirection.LONG,
baseAssetAmount: velocityClient.convertToPerpPrecision(1),
price: velocityClient.convertToPricePrecision(21.23),
},
{
orderType: OrderType.LIMIT,
marketType: MarketType.PERP,
marketIndex: 0,
direction: PositionDirection.SHORT,
baseAssetAmount: velocityClient.convertToPerpPrecision(1),
oraclePriceOffset: velocityClient.convertToPricePrecision(0.05), // BN, not .toNumber()
},
]);Method VelocityClient.placeOrdersReference ↗
Method VelocityClient.placeOrdersReference ↗| Parameter | Type | Required |
|---|---|---|
params | OrderParams[]Orders to place; `baseAssetAmount` is BASE_PRECISION (1e9) for perp
(token-mint precision for spot), `price`/`triggerPrice`/`oraclePriceOffset` are
PRICE_PRECISION (1e6). | Yes |
txParams | TxParamsOptional compute-unit/priority-fee overrides. | No |
subAccountId | numberSub-account to place the orders for; defaults to the active sub-account. | No |
optionalIxs | TransactionInstruction[]Extra instructions to prepend to the transaction. | No |
isolatedPositionDepositAmount | anyIf set and `params` has exactly one perp order that
increases the position, a transfer into an isolated-margin position (token-mint precision)
is prepended before placing. Ignored for batches of more than one order. | No |
| Returns |
|---|
Promise<string> |
Bulk margin enforcement:
placeOrders/placeScaleOrdersrun the initial-margin check once per risk scope touched by the batch (cross-margin, plus each isolated market with a risk-increasing order) rather than a single end-of-batch check. A batch that would have slipped past a weaker/absent margin gate under the old check may now be rejected withInsufficientCollateral.
Oracle / Auction-Style Orders
Oracle orders have prices that track the oracle feed with an offset. They go through a JIT auction before execution, with auction prices that gradually converge from the start offset to the end offset relative to oracle.
Important: For OrderType.ORACLE, auctionStartPrice, auctionEndPrice, and oraclePriceOffset are all offsets from the oracle price (in PRICE_PRECISION, 1e6), not absolute prices, and all three are BN.
import { BN, OrderType, PositionDirection, PRICE_PRECISION } from "@velocity-exchange/sdk";
const marketIndex = 18;
// Offsets are relative to oracle price (in PRICE_PRECISION)
// For a long: auction starts at a better (lower) price and ends at a worse (higher) price
const auctionStartPrice = PRICE_PRECISION.muln(-5).divn(10); // -$0.50 below oracle
const auctionEndPrice = PRICE_PRECISION.muln(5).divn(10); // +$0.50 above oracle
const orderParams = {
orderType: OrderType.ORACLE,
baseAssetAmount: velocityClient.convertToPerpPrecision(10),
direction: PositionDirection.LONG,
marketIndex,
auctionStartPrice,
auctionEndPrice,
oraclePriceOffset: velocityClient.convertToPricePrecision(0.30), // +$0.30 from oracle, BN
auctionDuration: 30, // slots
};
await velocityClient.placePerpOrder(orderParams);Example Oracle orderReference ↗
Example Oracle orderReference ↗Oracle order.Builder Codes
OrderParams accepts an optional builderIdx + builderFeeTenthBps pair to attribute an order to an approved builder and charge an extra builder fee (in tenths of a bps, e.g. 100 = 0.01%). builderIdx indexes into the placing user’s RevenueShareEscrow.approvedBuilders list — approve a builder first with changeApprovedBuilder(...). Both fields are optional; omit them for ordinary orders.
import { OrderType, PositionDirection } from "@velocity-exchange/sdk";
const orderParams = {
orderType: OrderType.LIMIT,
marketIndex: 0,
direction: PositionDirection.LONG,
baseAssetAmount: velocityClient.convertToPerpPrecision(1),
price: velocityClient.convertToPricePrecision(21.23),
builderIdx: 0, // index into this user's approved-builders list
builderFeeTenthBps: 100, // 0.01% builder fee
};
await velocityClient.placePerpOrder(orderParams);Example Builder-fee orderReference ↗
Example Builder-fee orderReference ↗Builder-fee order.If the taker is referred (their UserStats.referrerStatus has the BuilderReferral bit) or the order itself carries a builder code, fillers must attach the taker’s RevenueShareEscrow when filling — see getFillPerpOrderIx below — or the fill is rejected with UnableToLoadRevenueShareAccount.
Cancel Orders
Cancel a specific order by its onchain order ID.
await velocityClient.cancelOrder(1);Method VelocityClient.cancelOrderReference ↗
Method VelocityClient.cancelOrderReference ↗| Parameter | Type | Required |
|---|---|---|
orderId | numberProgram-assigned order ID to cancel; omit to cancel the most recently
placed order (resolved on-chain via `get_last_order_id`). | No |
txParams | TxParamsOptional compute-unit/priority-fee overrides. | No |
subAccountId | numberSub-account the order belongs to; defaults to the active sub-account. | No |
overrides | { withdrawIsolatedDepositAmount?: any; } | No |
| Returns |
|---|
Promise<string> |
Cancel multiple specific orders by their onchain order IDs in a single transaction.
await velocityClient.cancelOrdersByIds([1, 2, 3]);Method VelocityClient.cancelOrdersByIdsReference ↗
Method VelocityClient.cancelOrdersByIdsReference ↗| Parameter | Type | Required |
|---|---|---|
orderIds | number[]Program-assigned order IDs to cancel; an order ID that no longer exists is
silently skipped. `undefined` sends an empty list on-chain, i.e. cancels nothing. | No |
txParams | TxParamsThe transaction parameters. | No |
subAccountId | numberThe sub account id to cancel the orders for. | No |
user | UserThe user to cancel the orders for. If provided, it will be prioritized over the subAccountId. | No |
overrides | { authority?: PublicKey; } | No |
| Returns |
|---|
Promise<string> |
Cancel all orders matching the given market and direction filters. Pass null for any filter to match all. Omit all parameters to cancel every open order.
import { MarketType, PositionDirection } from "@velocity-exchange/sdk";
// Cancel all long perp orders on market 0
await velocityClient.cancelOrders(MarketType.PERP, 0, PositionDirection.LONG);
// Cancel all orders across all markets
await velocityClient.cancelOrders(null, null, null);Method VelocityClient.cancelOrdersReference ↗
Method VelocityClient.cancelOrdersReference ↗| Parameter | Type | Required |
|---|---|---|
marketType | MarketTypeOnly cancel orders of this market type (`PERP`/`SPOT`); combined with
`marketIndex` to scope to one perp or spot market. | No |
marketIndex | numberOnly cancel orders in this market index. | No |
direction | PositionDirectionOnly cancel orders on this side (`LONG`/`SHORT`). | No |
txParams | TxParamsOptional compute-unit/priority-fee overrides. | No |
subAccountId | numberSub-account to cancel orders for; defaults to the active sub-account. | No |
| Returns |
|---|
Promise<string> |
Cancel and Place (Atomic)
Atomically cancels existing orders and places new ones in a single transaction. This is the preferred approach for market makers who need to replace quotes without risk of being filled on stale orders in the gap between a separate cancel and re-quote.
await velocityClient.cancelAndPlaceOrders(
{ marketType: MarketType.PERP, marketIndex: 0 },
[
{
orderType: OrderType.LIMIT,
marketIndex: 0,
direction: PositionDirection.LONG,
baseAssetAmount: velocityClient.convertToPerpPrecision(1),
price: velocityClient.convertToPricePrecision(21.23),
},
]
);Method VelocityClient.cancelAndPlaceOrdersReference ↗
Method VelocityClient.cancelAndPlaceOrdersReference ↗| Parameter | Type | Required |
|---|---|---|
cancelOrderParams | { marketType?: MarketType; marketIndex?: number; direction?: PositionDirection; }Filters for which open orders to cancel; see `cancelOrders` for
semantics (`undefined` fields are not filtered on). | Yes |
placeOrderParams | OrderParams[]Orders to place after the cancel; `baseAssetAmount` is BASE_PRECISION
(1e9), `price`/`triggerPrice`/`oraclePriceOffset` are PRICE_PRECISION (1e6). | Yes |
txParams | TxParamsOptional compute-unit/priority-fee overrides. | No |
subAccountId | numberSub-account to operate on; defaults to the active sub-account. | No |
| Returns |
|---|
Promise<string> |
Modify Orders
await velocityClient.modifyOrder({
orderId: 1,
newBaseAmount: velocityClient.convertToPerpPrecision(2),
});Method VelocityClient.modifyOrderReference ↗
Method VelocityClient.modifyOrderReference ↗| Parameter | Type | Required |
|---|---|---|
orderParams | { orderId: number; newDirection?: PositionDirection; newBaseAmount?: any; newLimitPrice?: any; newOraclePriceOffset?: any; newTriggerPrice?: any; newTriggerCondition?: OrderTriggerCondition; ... 7 more ...; policy?: number; } | Yes |
txParams | TxParamsOptional compute-unit/priority-fee overrides. | No |
subAccountId | numberSub-account the order belongs to; defaults to the active sub-account. | No |
| Returns |
|---|
Promise<string> |
await velocityClient.modifyOrderByUserOrderId({
userOrderId: 1,
newBaseAmount: velocityClient.convertToPerpPrecision(2),
});Method VelocityClient.modifyOrderByUserOrderIdReference ↗
Method VelocityClient.modifyOrderByUserOrderIdReference ↗| Parameter | Type | Required |
|---|---|---|
orderParams | { userOrderId: number; newDirection?: PositionDirection; newBaseAmount?: any; newLimitPrice?: any; newOraclePriceOffset?: any; newTriggerPrice?: any; newTriggerCondition?: OrderTriggerCondition; ... 7 more ...; maxTs?: any; } | Yes |
txParams | TxParamsOptional compute-unit/priority-fee overrides. | No |
subAccountId | numberSub-account the order belongs to; defaults to the active sub-account. | No |
| Returns |
|---|
Promise<string> |
Trigger Orders (Stop / Take-Profit)
import { OrderTriggerCondition, OrderType, PositionDirection } from "@velocity-exchange/sdk";
const orderParams = {
orderType: OrderType.TRIGGER_MARKET,
marketIndex: 0,
direction: PositionDirection.SHORT,
baseAssetAmount: velocityClient.convertToPerpPrecision(1),
triggerPrice: velocityClient.convertToPricePrecision(95),
triggerCondition: OrderTriggerCondition.BELOW,
};
await velocityClient.placePerpOrder(orderParams);Example Trigger orderReference ↗
Example Trigger orderReference ↗Trigger order.Instruction Builders (Advanced)
Higher-level methods like placePerpOrder() build, sign, and send a transaction in one call. Instruction (IX) builders give you the raw TransactionInstruction objects so you can:
- Set a custom compute budget with priority fees for faster inclusion
- Batch multiple instructions into a single transaction (e.g., cancel + place atomically)
- Use Address Lookup Tables (ALTs) to fit more accounts into a transaction
- Compose with other programs (e.g., add a memo or call another protocol in the same tx)
Complete Example: Batching IXs with Compute Budget
import { ComputeBudgetProgram } from "@solana/web3.js";
import {
MarketType, PositionDirection, OrderType, getOrderParams,
} from "@velocity-exchange/sdk";
// 1. Build individual instructions
const cancelIx = await velocityClient.getCancelOrdersIx(
MarketType.PERP, // marketType (null to cancel all types)
0, // marketIndex (null to cancel across all markets)
null // direction (null to cancel both sides)
);
const placeIx = await velocityClient.getPlacePerpOrderIx(
getOrderParams({
orderType: OrderType.LIMIT,
marketIndex: 0,
direction: PositionDirection.LONG,
baseAssetAmount: velocityClient.convertToPerpPrecision(1),
price: velocityClient.convertToPricePrecision(21.0),
})
);
// 2. Add compute budget instructions for priority fees
const computeUnitPrice = ComputeBudgetProgram.setComputeUnitPrice({
microLamports: 50_000, // priority fee in micro-lamports per CU
});
const computeUnitLimit = ComputeBudgetProgram.setComputeUnitLimit({
units: 400_000, // max compute units for the transaction
});
// 3. Build a versioned transaction with all instructions
const tx = await velocityClient.txSender.getVersionedTransaction(
[computeUnitLimit, computeUnitPrice, cancelIx, placeIx],
[], // lookup table accounts (AddressLookupTableAccount[])
velocityClient.wallet.publicKey
);
// 4. Send the transaction
const { txSig } = await velocityClient.txSender.sendVersionedTransaction(
tx,
[],
velocityClient.opts
);
console.log("Batch tx:", txSig);Example IX batching exampleReference ↗
Example IX batching exampleReference ↗IX batching example.Individual IX Builders
getPlacePerpOrderIx builds an instruction to place a perp order.
// Params:
// orderParams: OptionalOrderParams - same params as placePerpOrder()
// subAccountId?: number - defaults to active subaccount
const ix = await velocityClient.getPlacePerpOrderIx(
getOrderParams({
orderType: OrderType.LIMIT,
marketIndex: 0,
direction: PositionDirection.LONG,
baseAssetAmount: velocityClient.convertToPerpPrecision(1),
price: velocityClient.convertToPricePrecision(21.0),
})
);Method VelocityClient.getPlacePerpOrderIxReference ↗
Method VelocityClient.getPlacePerpOrderIxReference ↗| Parameter | Type | Required |
|---|---|---|
orderParams | OptionalOrderParamsOrder to place; see `placePerpOrder` for field precisions. | Yes |
subAccountId | numberSub-account to place the order for; defaults to the active sub-account. | No |
depositToTradeArgs | { isMakingNewAccount: boolean; depositMarketIndex: number; }Pass when composing this instruction ahead of the user account
actually existing on-chain yet (e.g. deposit-to-trade in the same transaction as account
creation): `isMakingNewAccount` skips loading the (not-yet-existing) user account for
`remainingAccounts`, and `depositMarketIndex` marks the deposit's spot market as readable. | No |
| Returns |
|---|
Promise<TransactionInstruction> |
getCancelOrdersIx builds an instruction to cancel orders matching the given filters. Pass null for any filter to match all.
import { MarketType, PositionDirection } from "@velocity-exchange/sdk";
// Params:
// marketType: MarketType | null - filter by PERP or SPOT (null = all)
// marketIndex: number | null - filter by market index (null = all)
// direction: PositionDirection | null - filter by LONG or SHORT (null = both)
// subAccountId?: number - defaults to active subaccount
// Cancel all perp orders on market 0
const ix = await velocityClient.getCancelOrdersIx(MarketType.PERP, 0, null);
// Cancel ALL orders across all markets
const ixAll = await velocityClient.getCancelOrdersIx(null, null, null);Method VelocityClient.getCancelOrdersIxReference ↗
Method VelocityClient.getCancelOrdersIxReference ↗| Parameter | Type | Required |
|---|---|---|
marketType | MarketTypeOnly cancel orders of this market type. | Yes |
marketIndex | numberOnly cancel orders in this market index. | Yes |
direction | PositionDirectionOnly cancel orders on this side. | Yes |
subAccountId | numberSub-account to cancel orders for; defaults to the active sub-account. | No |
| Returns |
|---|
Promise<TransactionInstruction> |
getFillPerpOrderIx builds an instruction to fill another user’s perp order (used by filler/keeper bots).
// Params:
// userAccountPublicKey: PublicKey - the taker's user account address
// userAccount: UserAccount - the taker's deserialized user account
// order: { marketIndex, orderId } - the order to fill
// makerInfo?: MakerInfo | MakerInfo[] - optional maker(s) to match against
// fillerSubAccountId?: number - filler's subaccount
// isSignedMsg?: boolean
// fillerAuthority?: PublicKey
// hasBuilderFee?: boolean
// takerEscrow?: RevenueShareEscrowAccount - the taker's decoded RevenueShareEscrow
// (e.g. from a RevenueShareEscrowMap); REQUIRED when the taker's order carries a
// builder code, or the taker's UserStats.referrerStatus has the BuilderReferral
// bit — otherwise the program rejects the fill with UnableToLoadRevenueShareAccount.
const takerPubkey = takerUser.userAccountPublicKey;
const takerAccount = takerUser.getUserAccount();
const order = takerAccount.orders[0]; // the order to fill
const ix = await velocityClient.getFillPerpOrderIx(
takerPubkey,
takerAccount,
{ marketIndex: order.marketIndex, orderId: order.orderId }
);Method VelocityClient.getFillPerpOrderIxReference ↗
Method VelocityClient.getFillPerpOrderIxReference ↗| Parameter | Type | Required |
|---|---|---|
userAccountPublicKey | PublicKeyPublic key of the order owner's user account. | Yes |
userAccount | UserAccountDecoded user account of the order owner. | Yes |
order | Pick<Order, "marketIndex" | "orderId">The order to fill (`marketIndex`/`orderId`); defaults to the owner's most
recently placed order when omitted and `isSignedMsg` is false. | No |
makerInfo | MakerInfo | MakerInfo[]Maker(s) to attempt to cross against. | No |
fillerSubAccountId | numberFiller's sub-account to credit; defaults to the active sub-account. | No |
isSignedMsg | booleanWhether this fills a signed-msg (swift) order that has not yet been
placed on-chain; when true, `order` is not required and the builder-escrow attachment is
done optimistically (the order's builder flag cannot be inspected before it lands). | No |
fillerAuthority | PublicKeyFiller's authority if different from this client's wallet; the
filler user/user-stats PDAs are derived from this authority. | No |
hasBuilderFee | booleanForce-attach the taker escrow regardless of the detected builder flag. | No |
takerEscrow | RevenueShareEscrowAccountThe taker's decoded `RevenueShareEscrow`. Required to attach the escrow
when the order has a builder code or the taker is referred with an initialized escrow — the
on-chain handler rejects the fill if an owed escrow is missing from `remainingAccounts`. | No |
takerIsReferred | boolean | No |
| Returns |
|---|
Promise<TransactionInstruction> |
getTriggerOrderIx builds an instruction to trigger a conditional order (stop-loss or take-profit) that has met its trigger condition.
// Params:
// userAccountPublicKey: PublicKey - the user whose order to trigger
// userAccount: UserAccount - the deserialized user account
// order: Order - the full order object (must have trigger condition met)
// fillerPublicKey?: PublicKey - optional, defaults to your user account
const userPubkey = targetUser.userAccountPublicKey;
const userAccount = targetUser.getUserAccount();
const triggerOrder = userAccount.orders.find(
(o) => o.orderType.triggerMarket !== undefined || o.orderType.triggerLimit !== undefined
);
const ix = await velocityClient.getTriggerOrderIx(
userPubkey,
userAccount,
triggerOrder
);Method VelocityClient.getTriggerOrderIxReference ↗
Method VelocityClient.getTriggerOrderIxReference ↗| Parameter | Type | Required |
|---|---|---|
userAccountPublicKey | PublicKeyPublic key of the order owner's user account. | Yes |
userAccount | UserAccountDecoded user account for the order owner. | Yes |
order | OrderThe trigger order to activate. | Yes |
fillerPublicKey | PublicKeyFiller's user account public key; defaults to this client's own user account. | No |
| Returns |
|---|
Promise<TransactionInstruction> |
getRevertFillIx builds an instruction to revert a fill (used by filler bots when a fill was invalid).
// Params:
// fillerPublicKey?: PublicKey - defaults to your user account
const ix = await velocityClient.getRevertFillIx();Method VelocityClient.getRevertFillIxReference ↗
Method VelocityClient.getRevertFillIxReference ↗| Parameter | Type | Required |
|---|---|---|
fillerPublicKey | PublicKeyFiller's user account public key; defaults to this client's own
user account. | No |
| Returns |
|---|
Promise<TransactionInstruction> |
getSettlePNLsIxs builds instructions to settle PnL for one or more users across multiple markets. Returns an array of instructions (one per user per market).
// Params:
// users: Array of { settleeUserAccountPublicKey, settleeUserAccount }
// marketIndexes: number[] - perp market indexes to settle
const user = velocityClient.getUser();
const ixs = await velocityClient.getSettlePNLsIxs(
[
{
settleeUserAccountPublicKey: user.userAccountPublicKey,
settleeUserAccount: user.getUserAccount(),
},
],
[0, 1] // settle PnL on perp markets 0 and 1
);
// ixs is an array of TransactionInstruction, one per user per marketMethod VelocityClient.getSettlePNLsIxsReference ↗
Method VelocityClient.getSettlePNLsIxsReference ↗| Parameter | Type | Required |
|---|---|---|
users | { settleeUserAccountPublicKey: PublicKey; settleeUserAccount: UserAccount; }[]Users to settle, each with their user account public key and decoded account. | Yes |
marketIndexes | number[]Perp market indexes to settle for every user in `users`. | Yes |
revenueShareEscrowMap | RevenueShareEscrowMapOptional builder/referral escrow lookup; when a user's escrow
has completed builder or referral orders on a market being settled, its `RevenueShareEscrow`
and builder/referrer accounts are attached so the on-chain sweep can pay them out. | No |
| Returns |
|---|
Promise<TransactionInstruction[]> |
getJupiterSwapIxV6 builds a Jupiter swap instruction routed through Velocity.
// Params:
// inMarketIndex: number - spot market index of the input token
// outMarketIndex: number - spot market index of the output token
// amount: BN - amount of input token (in spot precision)
// slippageBps: number - max slippage in basis points
const ix = await velocityClient.getJupiterSwapIxV6({
inMarketIndex: 0, // e.g. quote asset
outMarketIndex: 1, // e.g. SOL
amount: velocityClient.convertToSpotPrecision(0, 10), // 10 units of the quote asset
slippageBps: 50, // 0.5% max slippage
});Method VelocityClient.getJupiterSwapIxV6Reference ↗
Method VelocityClient.getJupiterSwapIxV6Reference ↗| Parameter | Type | Required |
|---|---|---|
__0 | { jupiterClient: JupiterClient; outMarketIndex: number; inMarketIndex: number; outAssociatedTokenAccount?: PublicKey; inAssociatedTokenAccount?: PublicKey; ... 6 more ...; userAccountPublicKey?: PublicKey; }Optional user account override (e.g. when the account is being
created in the same transaction). | Yes |
| Returns |
|---|
Promise<{ ixs: TransactionInstruction[]; lookupTables: AddressLookupTableAccount[]; }> |