UNPKG

@d8x/perpetuals-sdk

Version:

Node TypeScript SDK for D8X Perpetual Futures

587 lines (549 loc) 19.2 kB
import { BigNumberish, BytesLike, ContractTransaction, ContractTransactionResponse, Interface } from "ethers"; import { CollaterlCCY } from "./constants"; export interface NodeSDKConfig { name: string | undefined; chainId: number; version: number; nodeURL: string; configSource: string; proxyAddr: string; proxyABILocation: string; shareTokenABILocation: string; limitOrderBookABILocation: string; limitOrderBookFactoryABILocation: string; symbolListLocation: string; priceFeedConfigNetwork: string; gasLimit?: number | undefined; proxyABI?: Interface | undefined; lobFactoryABI?: Interface | undefined; lobABI?: Interface | undefined; shareTokenABI?: Interface | undefined; priceFeedEndpoints?: PriceFeedEndpointsOptionalWrite; multicall?: string; } export type SettlementConfig = SettlementCcyItem[]; export interface SettlementCcyItem { perpFlags: bigint; description: string; settleTokenDecimals: number; settleCCY: string; settleCCYAddr: string; collateralCCY: string; collateralCCYAddr: string; triangulation: string[]; } export interface MarginAccount { symbol: string; positionNotionalBaseCCY: number; side: string; entryPrice: number; leverage: number; markPrice: number; unrealizedPnlQuoteCCY: number; unrealizedFundingCollateralCCY: number; collateralCC: number; liquidationPrice: [number, number | undefined]; liquidationLvg: number; collToQuoteConversion: number; } export interface PoolStaticInfo { poolId: number; poolMarginSymbol: string; poolMarginTokenAddr: string; poolMarginTokenDecimals: number; poolSettleSymbol: string; poolSettleTokenAddr: string; poolSettleTokenDecimals: number; MgnToSettleTriangulation: string[]; shareTokenAddr: string; oracleFactoryAddr: string; isRunning: boolean; } export interface PerpetualStaticInfo { id: number; poolId: number; state: string; //INVALID,INITIALIZING,NORMAL,EMERGENCY,SETTLE,CLEARED limitOrderBookAddr: string; initialMarginRate: number; maintenanceMarginRate: number; collateralCurrencyType: CollaterlCCY; S2Symbol: string; S3Symbol: string; lotSizeBC: number; referralRebate: number; priceIds: string[]; isPyth: boolean[]; perpFlags: bigint; fAMMTargetDD: bigint; } /* PerpetualStaticInfo { uint24 id; address limitOrderBookAddr; int128 fInitialMarginRate; int128 fMaintenanceMarginRate; uint8 perpetualState; AMMPerpLogic.CollateralCurrency collCurrencyType; bytes4 S2BaseCCY; //base currency of S2 bytes4 S2QuoteCCY; //quote currency of S2 bytes4 S3BaseCCY; //base currency of S3 bytes4 S3QuoteCCY; //quote currency of S3 int128 fLotSizeBC; int128 fReferralRebateCC; bytes32[] priceIds; bool[] isPyth; } */ /** * @global * @typedef {Object} ExchangeInfo * @property {PoolState[]} pools Array of state objects for all pools in the exchange. * @property {string} oracleFactoryAddr Address of the oracle factory used by the pools in the exchange. */ export interface ExchangeInfo { pools: PoolState[]; oracleFactoryAddr: string; proxyAddr: string; } /** * @global * @typedef {Object} PoolState * @property {boolean} isRunning True if the pool is running. * @property {string} marginTokenAddr Address of the token used by the pool. * This is the token used for margin deposits, liquidity provision, and trading fees. * @property {string} poolShareTokenAddr Address of the pool share token. * This is the token issued to external liquidity providers. * @property {number} defaultFundCashCC Amount of cash in the default fund of this pool, denominated in margin tokens. * @property {number} pnlParticipantCashCC Amount of cash in the PnL participation pool, i.e. cash deposited by external liquidity providers. * @property {number} totalTargetAMMFundSizeCC Target AMM funds aggregated across all perpetuals in this pool. * @property {number} brokerCollateralLotSize Price of one lot for brokers who wish to participate in this pool. Denominated in margin tokens. * @property {PerpetualState[]} perpetuals Array of all perpetuals in this pool. */ export interface PoolState { isRunning: boolean; poolSymbol: string; settleSymbol: string; marginTokenAddr: string; settleTokenAddr: string; poolShareTokenAddr: string; defaultFundCashCC: number; pnlParticipantCashCC: number; totalTargetAMMFundSizeCC: number; brokerCollateralLotSize: number; perpetuals: PerpetualState[]; } export interface PerpetualState { id: number; state: string; baseCurrency: string; quoteCurrency: string; indexPrice: number; collToQuoteIndexPrice: number; markPremium: number; markPrice: number; midPrice: number; currentFundingRateBps: number; openInterestBC: number; longBC: number; shortBC: number; isMarketClosed: boolean; } export interface OrderResponse { tx: ContractTransactionResponse; orderId: string; } export interface OrderStruct { orders: Order[]; orderIds: string[]; } export interface Order { symbol: string; //symbol of the form ETH-USD-MATIC side: string; type: string; quantity: number; reduceOnly?: boolean | undefined; limitPrice?: number | undefined; keepPositionLvg?: boolean | undefined; brokerFeeTbps?: number | undefined; brokerAddr?: string | undefined; brokerSignature?: BytesLike | undefined; stopPrice?: number | undefined; leverage?: number | undefined; deadline?: number | undefined; executionTimestamp: number; submittedTimestamp?: number; parentChildOrderIds?: [string, string]; } export interface TradeEvent { perpetualId: number; positionId: string; orderId: string; newPositionSizeBC: number; executionPrice: number; } /** * @global * @typedef {Object} SmartContractOrder * @property {bigint} flags * @property {number} iPerpetualId * @property {number} brokerFeeTbps * @property {string} traderAddr * @property {string} brokerAddr * @property {string} executorAddr * @property {BytesLike} brokerSignature * @property {bigint} fAmount * @property {bigint} fLimitPrice * @property {bigint} fTriggerPrice * @property {number} leverageTDR * @property {number} iDeadline * @property {number} executionTimestamp * @property {number} submittedTimestamp */ export interface SmartContractOrder { flags: BigNumberish; iPerpetualId: BigNumberish; brokerFeeTbps: BigNumberish; traderAddr: string; brokerAddr: string; executorAddr: string; brokerSignature: BytesLike; fAmount: bigint; fLimitPrice: bigint; fTriggerPrice: bigint; leverageTDR: BigNumberish; iDeadline: BigNumberish; executionTimestamp: BigNumberish; submittedTimestamp: BigNumberish; } // { // leverageTDR: bigint; // brokerFeeTbps: bigint; // iPerpetualId: bigint; // traderAddr: string; // executionTimestamp: bigint; // brokerAddr: string; // submittedTimestamp: bigint; // flags: bigint; // iDeadline: bigint; // executorAddr: string; // fAmount: bigint; // fLimitPrice: bigint; // fTriggerPrice: bigint; // brokerSignature: string; // }; /** * @global * @typedef {Object} ClientOrder * @property {bigint} flags * @property {bigint} iPerpetualId * @property {bigint} brokerFeeTbps * @property {string} traderAddr * @property {string} brokerAddr * @property {string} executorAddr * @property {BytesLike} brokerSignature * @property {bigint} fAmount * @property {bigint} fLimitPrice * @property {bigint} fTriggerPrice * @property {bigint} leverageTDR * @property {bigint} iDeadline * @property {bigint} executionTimestamp * @property {string} parentChildDigest1 * @property {string} parentChildDigest2 * @property {string} callbackTarget */ export interface ClientOrder { flags: BigNumberish; iPerpetualId: BigNumberish; brokerFeeTbps: BigNumberish; traderAddr: string; brokerAddr: string; executorAddr: string; brokerSignature: BytesLike; fAmount: bigint; fLimitPrice: bigint; fTriggerPrice: bigint; leverageTDR: BigNumberish; iDeadline: BigNumberish; executionTimestamp: BigNumberish; parentChildDigest1: string; parentChildDigest2: string; callbackTarget: string; } export interface TypeSafeOrder { flags: bigint; iPerpetualId: number; brokerFeeTbps: number; traderAddr: string; brokerAddr: string; brokerSignature: string; fAmount: bigint; fLimitPrice: bigint; fTriggerPrice: bigint; leverageTDR: number; iDeadline: number; executionTimestamp: number; parentChildDigest1: string; parentChildDigest2: string; callbackTarget: string; } export interface PriceFeedConfig { network: string; ids: Array<{ symbol: string; id: string; type: string; origin: string }>; endpoints: PriceFeedEndpoints; } export interface PriceFeedEndpointsItem { // low-liq is the legacy version of v3 type: string | "odin" | "pyth" | "onchain" | "v2" | "v3" | "low-liq" | "polymarket"; // Read only endpoints. Used by default. endpoints: string[]; // Price feed endpoints which are used for fetching prices which will be // submitted for updates on chain. writeEndpoints?: string[]; } // For price feeds config export type PriceFeedEndpoints = Array<Required<PriceFeedEndpointsItem>>; // For SDK configuration writeEndpoints are set as optional for backwards // compatibility. See NodeSDKConfig interface. export type PriceFeedEndpointsOptionalWrite = Array<PriceFeedEndpointsItem>; export interface PriceFeedSubmission { symbols: Map<string, string[]>; //id -> symbols ids: string[]; priceFeedVaas: string[]; prices: number[]; isMarketClosed: boolean[]; timestamps: number[]; } export interface PriceFeedFormat { conf: bigint; expo: number; price: bigint; publish_time: number; } // json version of PriceFeedFormat export interface PriceFeedJson { conf: string; expo: number; price: string; publish_time: number; } export interface PythV2MetaData { slot: number; proof_available_time: number; prev_publish_time: number; } export interface PythV2LatestPriceFeed { binary: { encoding: string; data: string[]; }; parsed: [ { ema_price: PriceFeedFormat; id: string; price: PriceFeedFormat; metadata: PythV2MetaData; } ]; } // Payload to be sent to backend when creating // a new referral code. Intended for trader- // backends that have an active referral system export interface APIReferralCodePayload { code: string; referrerAddr: string; createdOn: number; passOnPercTDF: number; signature: string; } // Payload to be sent to backend when an agency/broker // assigns a "partner". export interface APIReferPayload { parentAddr: string; referToAddr: string; passOnPercTDF: number; createdOn: number; signature: string; } // Payload to be sent to backend when the trader // selects a new referral code. Intended for trader- // backends that have an active referral system export interface APIReferralCodeSelectionPayload { code: string; traderAddr: string; createdOn: number; signature: string; } export interface GasPriceV2 { maxPriorityFee: number; maxfee: number; } export interface GasInfo { safeLow: number | GasPriceV2; standard: number | GasPriceV2; fast: number | GasPriceV2; fastest?: number; estimatedBaseFee?: number; blockTime: number; blockNumber: number; } export interface TokenOverride { tokenAddress: string; newSymbol: string; } /** * Perpetualdata corresponding to the data in the smart contract */ export interface PerpetualData { poolId: number; id: number; fInitialMarginRate: number; //parameter: initial margin fSigma2: number; // parameter: volatility of base-quote pair iLastFundingTime: number; //timestamp since last funding rate payment fDFCoverNRate: number; // parameter: cover-n rule for default fund. E.g., fDFCoverNRate=0.05 -> we try to cover 5% of active accounts with default fund fMaintenanceMarginRate: number; // parameter: maintenance margin perpetualState: string; // Perpetual AMM state eCollateralCurrency: number; //parameter: in what currency is the collateral held? // ------ 1 S2BaseCCY: string; //base currency of S2 S2QuoteCCY: string; //quote currency of S2 incentiveSpreadBps: number; //parameter: maximum spread added to the PD minimalSpreadBps: number; //parameter: minimal spread between long and short perpetual price S3BaseCCY: string; //base currency of S3 S3QuoteCCY: string; //quote currency of S3 fSigma3: number; // parameter: volatility of quanto-quote pair fRho23: number; // parameter: correlation of quanto/base returns liquidationPenaltyRateBps: number; //parameter: penalty if AMM closes the position and not the trader //------- 2 currentMarkPremiumRatePrice: number; //relative diff to index price EMA, used for markprice. currentMarkPremiumRateTime: number; //relative diff to index price EMA, used for markprice. //------- 3 premiumRatesEMA: number; // EMA of premium rate fUnitAccumulatedFunding: number; //accumulated funding in collateral currency //------- 4 fOpenInterest: number; //open interest is the larger of the amount of long and short positions in base currency fTargetAMMFundSize: number; //target liquidity pool funds to allocate to the AMM //------- 5 fCurrentTraderExposureEMA: number; // trade amounts (storing absolute value) fCurrentFundingRate: number; // current instantaneous funding rate //------- 6 fLotSizeBC: number; //parameter: minimal trade unit (in base currency) to avoid dust positions fReferralRebateCC: number; //parameter: referall rebate in collateral currency //------- 7 fTargetDFSize: number; // target default fund size fkStar: number; // signed trade size that minimizes the AMM risk //------- 8 fAMMTargetDD: number; // parameter: target distance to default (=inverse of default probability) perpFlags: bigint; // parameter: flags for perpetual //------- 9 fMinimalTraderExposureEMA: number; // parameter: minimal value for fCurrentTraderExposureEMA that we don't want to undershoot fMinimalAMMExposureEMA: number; // parameter: minimal abs value for fCurrentAMMExposureEMA that we don't want to undershoot //------- 10 fSettlementS3PriceData: number; //quanto index fSettlementS2PriceData: number; //base-quote pair. Used as last price in normal state. //------- 11 fTotalMarginBalance: number; //calculated for settlement, in collateral currency fMarkPriceEMALambda: number; // parameter: Lambda parameter for EMA used in mark-price for funding rates fFundingRateClamp: number; // parameter: funding rate clamp between which we charge 1bps fMaximalTradeSizeBumpUp: number; // parameter: >1, users can create a maximal position of size fMaximalTradeSizeBumpUp*fCurrentAMMExposureEMA iLastTargetPoolSizeTime: number; //timestamp (seconds) since last update of fTargetDFSize and fTargetAMMFundSize //------- 12 fStressReturnS3: [number, number]; // parameter: negative and positive stress returns for quanto-quote asset fDFLambda: [number, number]; // parameter: EMA lambda for AMM and trader exposure K,k: EMA*lambda + (1-lambda)*K. 0 regular lambda, 1 if current value exceeds past fCurrentAMMExposureEMA: [number, number]; // 0: negative aggregated exposure (storing negative value), 1: positive fStressReturnS2: [number, number]; // parameter: negative and positive stress returns for base-quote asset } /** * LiquidityPoolData corresponding to the data in the smart contract */ export interface LiquidityPoolData { isRunning: boolean; // state iPerpetualCount: number; // state id: number; // parameter: index, starts from 1 fCeilPnLShare: number; // parameter: cap on the share of PnL allocated to liquidity providers marginTokenDecimals: number; // parameter: decimals of margin token, inferred from token contract iTargetPoolSizeUpdateTime: number; //parameter: timestamp in seconds. How often we update the pool's target size marginTokenAddress: string; //parameter: address of the margin token // ----- prevAnchor: number; // state: keep track of timestamp since last withdrawal was initiated fRedemptionRate: number; // state: used for settlement in case of AMM default shareTokenAddress: string; // parameter fPnLparticipantsCashCC: number; // state: addLiquidity/withdrawLiquidity + profit/loss - rebalance fTargetAMMFundSize: number; // state: target liquidity for all perpetuals in pool (sum) fDefaultFundCashCC: number; // state: profit/loss fTargetDFSize: number; // state: target default fund size for all perpetuals in pool fBrokerCollateralLotSize: number; // param:how much collateral do brokers deposit when providing "1 lot" (not trading lot) prevTokenAmount: number; // state nextTokenAmount: number; // state totalSupplyShareToken: number; // state fBrokerFundCashCC: number; // state: amount of cash in broker fund } // referral types: export const referralDomain = { name: "Referral System", } as const; export const referralTypes = { // ["string", "address", "uint32", "uint256"], // [rc.code, rc.referrerAddr, passOnPercTwoDigitsFormat, Math.round(rc.createdOn)] NewCode: [ { name: "Code", type: "string" }, { name: "ReferrerAddr", type: "address" }, { name: "PassOnPercTDF", type: "uint32" }, { name: "CreatedOn", type: "uint256" }, ], // ["address", "address", "uint32", "uint256"], // [rc.parentAddr, rc.referToAddr, passOnPercTwoDigitsFormat, Math.round(rc.createdOn)] NewReferral: [ { name: "ParentAddr", type: "address" }, { name: "ReferToAddr", type: "address" }, { name: "PassOnPercTDF", type: "uint32" }, { name: "CreatedOn", type: "uint256" }, ], // ["string", "address", "uint256"], [rc.code, rc.traderAddr, Math.round(rc.createdOn)] CodeSelection: [ { name: "Code", type: "string" }, { name: "TraderAddr", type: "address" }, { name: "CreatedOn", type: "uint256" }, ], // domain: name only (multichain) EIP712Domain: [{ name: "name", type: "string" }], } as const; // Price information that can be used for // prediction markets and regular markets export interface IdxPriceInfo { s2: number; s3?: number; ema: number; s2MktClosed: boolean; s3MktClosed?: boolean; conf: bigint; predMktCLOBParams: bigint; } export interface PredMktPriceInfo { s2: number; ema: number; s2MktClosed: boolean; conf: bigint; predMktCLOBParams: bigint; } export interface PythMetadata { id: string; // id without leading 0x market_hours: { is_open: boolean; // false, next_open?: number; // 1746019800, next_close?: number; //1746043200 }; attributes: { symbol?: string; //"Equity.US.BTCO/USD", asset_type?: string; // "Equity", base?: string; //"BTCO", cms_symbol?: string; //"BTCO", country?: string; //"US", cqs_symbol?: string; //"BTCO", description?: string; //"INVESCO GALAXY BITCOIN ETF / US DOLLAR", display_symbol?: string; // "BTCO/USD", nasdaq_symbol?: string; // "BTCO", publish_interval?: string; //"5", quote_currency?: string; //"USD", schedule?: string; // "America/New_York;0930-1600,0930-1600,0930-1600,0930-1600,0930-1600,C,C;0418/C,0526/C,0619/C,0703/0930-1300,0704/C" }; }