@d8x/perpetuals-sdk 0.0.44 → 0.0.45

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/version.d.ts CHANGED
@@ -1 +1 @@
1
- export declare const D8X_SDK_VERSION = "0.0.43";
1
+ export declare const D8X_SDK_VERSION = "0.0.45";
package/dist/version.js CHANGED
@@ -1,4 +1,4 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.D8X_SDK_VERSION = void 0;
4
- exports.D8X_SDK_VERSION = "0.0.43";
4
+ exports.D8X_SDK_VERSION = "0.0.45";
package/package.json CHANGED
@@ -10,7 +10,8 @@
10
10
  "build:doc": "jsdoc2md --files ./src/accountTrade.ts --configure ./jsdoc2md.json > ./doc/accountTrade.md && jsdoc2md --files ./src/marketData.ts --configure ./jsdoc2md.json > ./doc/marketData.md && jsdoc2md --files ./src/liquidatorTool.ts --configure ./jsdoc2md.json > ./doc/liquidatorTool.md && jsdoc2md --files ./src/liquidityProviderTool.ts --configure ./jsdoc2md.json > ./doc/liquidityProviderTool.md && jsdoc2md --files ./src/brokerTool.ts --configure ./jsdoc2md.json > ./doc/brokerTool.md && jsdoc2md --files ./src/orderReferrerTool.ts --configure ./jsdoc2md.json > ./doc/orderReferrerTool.md && jsdoc2md --files ./src/*.ts --configure ./jsdoc2md.json > ./doc/d8x-perpetuals-sdk.md",
11
11
  "test": "jest",
12
12
  "coverage": "nyc -r lcov -e .ts -x \"*.test.ts\" npm run test",
13
- "prepubish": "test test/readonly.test && build:doc"
13
+ "prebuild": "node -p \"'export const D8X_SDK_VERSION = ' + JSON.stringify(require('./package.json').version) + ';'\" > src/version.ts",
14
+ "prepublish": "yarn build"
14
15
  },
15
16
  "devDependencies": {
16
17
  "@babel/core": "^7.20.2",
@@ -32,7 +33,7 @@
32
33
  },
33
34
  "name": "@d8x/perpetuals-sdk",
34
35
  "description": "Node TypeScript SDK for D8X Perpetual Futures",
35
- "version": "0.0.44",
36
+ "version": "0.0.45",
36
37
  "main": "./dist/index.js",
37
38
  "types": "./dist/index.d.ts",
38
39
  "directories": {
package/src/d8XMath.ts CHANGED
@@ -275,26 +275,33 @@ export function getNewPositionLeverage(
275
275
  );
276
276
  }
277
277
 
278
- export function getMaxCollateralToRemove(
279
- currentPosition: number,
280
- currentLockedInValue: number,
281
- currentAvailableCash: number,
282
- markPrice: number,
283
- indexPriceS2: number,
284
- indexPriceS3: number,
285
- initialMarginRate: number
286
- ): number {
287
- return (
288
- getMarginRequiredForLeveragedTrade(
289
- 1 / initialMarginRate,
290
- currentPosition,
291
- currentLockedInValue,
292
- 0,
293
- markPrice,
294
- indexPriceS2,
295
- indexPriceS3,
296
- indexPriceS2,
297
- 0
298
- ) - currentAvailableCash
299
- );
278
+ /**
279
+ * Determine amount to be deposited into margin account so that the given leverage
280
+ * is obtained when trading a position pos (trade amount = position)
281
+ * Does NOT include fees
282
+ * Smart contract equivalent: calcMarginForTargetLeverage(..., _ignorePosBalance = false & balance = b0)
283
+ * @param {number} pos0 - current position
284
+ * @param {number} b0 - current balance
285
+ * @param {number} tradeAmnt - amount to trade
286
+ * @param {number} targetLvg - target leverage
287
+ * @param {number} price - price to trade amount 'tradeAmnt'
288
+ * @param {number} S3 - collateral to quote conversion (=S2 if base-collateral, =1 if quote collateral, = index S3 if quanto)
289
+ * @param {number} S2Mark - mark price
290
+ * @returns {number} Amount to be deposited to have the given leverage when trading into position pos before fees
291
+ */
292
+ export function getDepositAmountForLvgTrade(
293
+ pos0: number,
294
+ b0: number,
295
+ tradeAmnt: number,
296
+ targetLvg: number,
297
+ price: number,
298
+ S3: number,
299
+ S2Mark: number
300
+ ) {
301
+ let pnl = (tradeAmnt * (S2Mark - price)) / S3;
302
+ if (targetLvg == 0) {
303
+ targetLvg = (Math.abs(pos0) * S2Mark) / S3 / b0;
304
+ }
305
+ let b = (Math.abs(pos0 + tradeAmnt) * S2Mark) / S3 / targetLvg;
306
+ return -(b0 + pnl - b);
300
307
  }
package/src/index.ts CHANGED
@@ -25,3 +25,5 @@ export {
25
25
  TraderInterface,
26
26
  PerpetualEventHandler,
27
27
  };
28
+
29
+ export * from "./version";
package/src/marketData.ts CHANGED
@@ -5,6 +5,7 @@ import {
5
5
  calculateLiquidationPriceCollateralQuanto,
6
6
  calculateLiquidationPriceCollateralQuote,
7
7
  floatToABK64x64,
8
+ getDepositAmountForLvgTrade,
8
9
  getMarginRequiredForLeveragedTrade,
9
10
  getMaxSignedPositionSize,
10
11
  getNewPositionLeverage,
@@ -297,13 +298,17 @@ export default class MarketData extends PerpetualDataHandler {
297
298
  currentPositionRisk: MarginAccount,
298
299
  symbolToPerpStaticInfo: Map<string, PerpetualStaticInfo>
299
300
  ): MarginAccount {
300
- let currentPosition = currentPositionRisk.positionNotionalBaseCCY;
301
- let newPosition = currentPositionRisk.positionNotionalBaseCCY + tradeAmount;
302
- let side = newPosition > 0 ? BUY_SIDE : newPosition < 0 ? SELL_SIDE : CLOSED_SIDE;
301
+ let currentSide = currentPositionRisk.side;
302
+ let currentPosition = (currentSide == BUY_SIDE ? 1 : -1) * currentPositionRisk.positionNotionalBaseCCY;
303
+ let newPosition = currentPosition + tradeAmount;
304
+ let newSide = newPosition > 0 ? BUY_SIDE : newPosition < 0 ? SELL_SIDE : CLOSED_SIDE;
303
305
  let lockedInValue = currentPositionRisk.entryPrice * currentPosition;
304
306
  if (tradeAmount == 0) {
305
307
  keepPositionLvg = false;
306
308
  }
309
+ let isOpen = newPosition != 0 && (tradeAmount == 0 || currentPosition == 0 || tradeAmount * currentPosition > 0);
310
+ let isFlip = Math.abs(tradeAmount) > Math.abs(currentPosition) && !isOpen;
311
+ let keepPositionLvgOnClose = keepPositionLvg && !isOpen;
307
312
  // need these for leverage/margin calculations
308
313
  let [markPrice, indexPriceS2, indexPriceS3] = [
309
314
  perpetualState.markPrice,
@@ -339,19 +344,26 @@ export default class MarketData extends PerpetualDataHandler {
339
344
  feeRate
340
345
  );
341
346
  } else if (tradeAmount != 0) {
342
- // the order has its own leverage and margin requirements
343
- let tradeCollateral = getMarginRequiredForLeveragedTrade(
344
- tradeLeverage,
345
- 0,
346
- 0,
347
- tradeAmount,
348
- markPrice,
349
- indexPriceS2,
350
- indexPriceS3,
351
- tradePrice,
352
- feeRate
353
- );
354
- newCollateral = currentPositionRisk.collateralCC + tradeCollateral;
347
+ let depositAtTradeTime: number;
348
+ if (!isOpen && !isFlip && !keepPositionLvgOnClose) {
349
+ // no deposit from trader's wallet, but there is realized pnl
350
+ depositAtTradeTime = tradeAmount * (tradePrice - currentPositionRisk.entryPrice);
351
+ } else {
352
+ // target lvg will default current lvg if not specified
353
+ let targetLvg = isFlip || isOpen ? tradeLeverage ?? 0 : 0;
354
+ let b0, pos0;
355
+ [b0, pos0] = isOpen ? [0, 0] : [currentPositionRisk.collateralCC, currentPosition];
356
+ depositAtTradeTime = getDepositAmountForLvgTrade(
357
+ b0,
358
+ pos0,
359
+ tradeAmount,
360
+ targetLvg,
361
+ tradePrice,
362
+ indexPriceS2,
363
+ markPrice
364
+ );
365
+ }
366
+ newCollateral = currentPositionRisk.collateralCC + depositAtTradeTime;
355
367
  // the new leverage corresponds to increasing the position and collateral according to the order
356
368
  newLeverage = getNewPositionLeverage(
357
369
  tradeAmount,
@@ -380,7 +392,7 @@ export default class MarketData extends PerpetualDataHandler {
380
392
  );
381
393
  }
382
394
  let newLockedInValue = lockedInValue + tradeAmount * tradePrice;
383
-
395
+ let entryPrice = newPosition == 0 ? 0 : Math.abs(newLockedInValue / newPosition);
384
396
  // liquidation vars
385
397
  let S2Liq: number, S3Liq: number | undefined;
386
398
  let tau = symbolToPerpStaticInfo.get(symbol)!.maintenanceMarginRate;
@@ -401,14 +413,15 @@ export default class MarketData extends PerpetualDataHandler {
401
413
  } else {
402
414
  S2Liq = calculateLiquidationPriceCollateralQuote(newLockedInValue, newPosition, newCollateral, tau);
403
415
  }
416
+
404
417
  let newPositionRisk: MarginAccount = {
405
418
  symbol: currentPositionRisk.symbol,
406
419
  positionNotionalBaseCCY: Math.abs(newPosition),
407
- side: side,
408
- entryPrice: newPosition == 0 ? 0 : Math.abs(newLockedInValue / newPosition),
420
+ side: newSide,
421
+ entryPrice: entryPrice,
409
422
  leverage: newLeverage,
410
423
  markPrice: markPrice,
411
- unrealizedPnlQuoteCCY: currentPositionRisk.unrealizedPnlQuoteCCY + tradeAmount * (markPrice - tradePrice),
424
+ unrealizedPnlQuoteCCY: newPosition * markPrice - newLockedInValue,
412
425
  unrealizedFundingCollateralCCY: currentPositionRisk.unrealizedFundingCollateralCCY,
413
426
  collateralCC: newCollateral,
414
427
  collToQuoteConversion: indexPriceS3,
package/src/version.ts CHANGED
@@ -1 +1 @@
1
- export const D8X_SDK_VERSION = "0.0.43";
1
+ export const D8X_SDK_VERSION = "0.0.45";