@gainsnetwork/sdk 0.0.0-v10.rc20 → 0.0.0-v10.rc22
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/lib/trade/pnl/index.d.ts +3 -2
- package/lib/trade/pnl/index.js +44 -28
- package/lib/trade/pnl/types.d.ts +6 -2
- package/lib/trade/priceImpact/close/index.js +5 -9
- package/lib/trade/priceImpact/index.d.ts +1 -1
- package/lib/trade/priceImpact/index.js +1 -2
- package/lib/trade/priceImpact/open/index.js +7 -7
- package/lib/trade/priceImpact/open/types.d.ts +0 -1
- package/lib/trade/priceImpact/skew/index.d.ts +3 -10
- package/lib/trade/priceImpact/skew/index.js +8 -38
- package/package.json +1 -1
package/lib/trade/pnl/index.d.ts
CHANGED
|
@@ -39,12 +39,13 @@ export declare const getTradeValue: (collateral: number, pnlPercent: number, tot
|
|
|
39
39
|
/**
|
|
40
40
|
* @dev Comprehensive PnL calculation including all fees
|
|
41
41
|
* @param trade The trade to calculate PnL for
|
|
42
|
-
* @param
|
|
42
|
+
* @param marketPrice Current market price (without price impact)
|
|
43
|
+
* @param executionPrice Price after all impacts (spread, skew, volume)
|
|
43
44
|
* @param tradeInfo Trade info with version and timestamps
|
|
44
45
|
* @param context Context with all fee parameters
|
|
45
46
|
* @returns Detailed PnL breakdown
|
|
46
47
|
*/
|
|
47
|
-
export declare const getComprehensivePnl: (trade: Trade,
|
|
48
|
+
export declare const getComprehensivePnl: (trade: Trade, marketPrice: number, executionPrice: number, tradeInfo: TradeInfo, context: GetComprehensivePnlContext) => ComprehensivePnlResult;
|
|
48
49
|
/**
|
|
49
50
|
* @dev Legacy getPnl function for backward compatibility
|
|
50
51
|
* @deprecated Use getComprehensivePnl for new implementations
|
package/lib/trade/pnl/index.js
CHANGED
|
@@ -74,23 +74,24 @@ exports.getTradeValue = getTradeValue;
|
|
|
74
74
|
/**
|
|
75
75
|
* @dev Comprehensive PnL calculation including all fees
|
|
76
76
|
* @param trade The trade to calculate PnL for
|
|
77
|
-
* @param
|
|
77
|
+
* @param marketPrice Current market price (without price impact)
|
|
78
|
+
* @param executionPrice Price after all impacts (spread, skew, volume)
|
|
78
79
|
* @param tradeInfo Trade info with version and timestamps
|
|
79
80
|
* @param context Context with all fee parameters
|
|
80
81
|
* @returns Detailed PnL breakdown
|
|
81
82
|
*/
|
|
82
|
-
const getComprehensivePnl = (trade,
|
|
83
|
+
const getComprehensivePnl = (trade, marketPrice, executionPrice, tradeInfo, context) => {
|
|
83
84
|
var _a;
|
|
84
|
-
// Calculate
|
|
85
|
-
let
|
|
85
|
+
// Calculate both raw PnL (market price) and impact-adjusted PnL (execution price)
|
|
86
|
+
let rawPnlPercent = (0, exports.getPnlPercent)(trade.openPrice, marketPrice, trade.long, trade.leverage);
|
|
87
|
+
let impactPnlPercent = (0, exports.getPnlPercent)(trade.openPrice, executionPrice, trade.long, trade.leverage);
|
|
86
88
|
if (!context.tradeData) {
|
|
87
89
|
throw new Error("Trade data is undefined");
|
|
88
90
|
}
|
|
89
91
|
// Calculate position size
|
|
90
92
|
const positionSizeCollateral = trade.collateralAmount * trade.leverage;
|
|
91
93
|
// Calculate holding fees - always use getTradePendingHoldingFeesCollateral
|
|
92
|
-
|
|
93
|
-
const pendingHoldingFees = (0, trading_1.getTradePendingHoldingFeesCollateral)(trade, tradeInfo, context.tradeData.tradeFeesData, currentPrice, {
|
|
94
|
+
const pendingHoldingFees = (0, trading_1.getTradePendingHoldingFeesCollateral)(trade, tradeInfo, context.tradeData.tradeFeesData, executionPrice, {
|
|
94
95
|
contractsVersion: context.core.contractsVersion,
|
|
95
96
|
currentTimestamp: context.core.currentTimestamp,
|
|
96
97
|
collateralPriceUsd: context.core.collateralPriceUsd,
|
|
@@ -112,39 +113,56 @@ const getComprehensivePnl = (trade, currentPrice, tradeInfo, context) => {
|
|
|
112
113
|
// Total fees
|
|
113
114
|
const totalHoldingFees = borrowingFeeV1 + borrowingFeeV2 + fundingFee;
|
|
114
115
|
const totalFees = totalHoldingFees + closingFee;
|
|
115
|
-
// Check liquidation
|
|
116
|
+
// Check liquidation (using raw PnL for liquidation check)
|
|
116
117
|
const liquidationThreshold = ((_a = context.tradeData) === null || _a === void 0 ? void 0 : _a.liquidationParams)
|
|
117
118
|
? (0, liquidation_1.getLiqPnlThresholdP)(context.tradeData.liquidationParams, trade.leverage) *
|
|
118
119
|
-100
|
|
119
120
|
: -90; // Default 90% loss
|
|
120
|
-
const isLiquidated =
|
|
121
|
-
// If liquidated, set PnL to -100%
|
|
121
|
+
const isLiquidated = rawPnlPercent <= liquidationThreshold;
|
|
122
|
+
// If liquidated, set both PnL percentages to -100%
|
|
122
123
|
if (isLiquidated) {
|
|
123
|
-
|
|
124
|
+
rawPnlPercent = -100;
|
|
125
|
+
impactPnlPercent = -100;
|
|
124
126
|
}
|
|
125
127
|
// Get realized PnL components from TradeFeesData
|
|
126
128
|
const { totalRealizedPnlCollateral } = (0, exports.getTradeRealizedPnlCollateral)(context.tradeData.tradeFeesData);
|
|
127
|
-
// Calculate
|
|
128
|
-
const
|
|
129
|
-
// Calculate PnL in collateral
|
|
130
|
-
const
|
|
131
|
-
// Calculate
|
|
132
|
-
const
|
|
133
|
-
|
|
134
|
-
|
|
129
|
+
// Calculate raw PnL in collateral (using market price)
|
|
130
|
+
const rawPnlCollateral = trade.collateralAmount * (rawPnlPercent / 100);
|
|
131
|
+
// Calculate impact-adjusted PnL in collateral (using execution price)
|
|
132
|
+
const impactPnlCollateral = trade.collateralAmount * (impactPnlPercent / 100);
|
|
133
|
+
// Calculate price impact
|
|
134
|
+
const priceImpactCollateral = impactPnlCollateral - rawPnlCollateral;
|
|
135
|
+
const priceImpactPercent = impactPnlPercent - rawPnlPercent;
|
|
136
|
+
// Calculate unrealized PnL (before closing fee, after holding fees, using market price)
|
|
137
|
+
// This is what the trader sees for open positions
|
|
138
|
+
const uPnlCollateral = rawPnlCollateral - totalHoldingFees + totalRealizedPnlCollateral;
|
|
135
139
|
const uPnlPercent = (uPnlCollateral / trade.collateralAmount) * 100;
|
|
136
|
-
//
|
|
137
|
-
|
|
140
|
+
// Calculate realized PnL (after all fees including closing, using execution price)
|
|
141
|
+
// This is what the trader would get if closing the position
|
|
142
|
+
const realizedPnlCollateral = impactPnlCollateral - totalFees + totalRealizedPnlCollateral;
|
|
138
143
|
const realizedPnlPercent = (realizedPnlCollateral / trade.collateralAmount) * 100;
|
|
144
|
+
// Calculate trade value using execution price (what trader would receive)
|
|
145
|
+
const tradeValue = (0, exports.getTradeValue)(trade.collateralAmount, impactPnlPercent, totalFees);
|
|
139
146
|
return {
|
|
140
|
-
//
|
|
141
|
-
pnlPercent,
|
|
142
|
-
pnlCollateral,
|
|
147
|
+
// Raw PnL values (using market price, no price impact)
|
|
148
|
+
pnlPercent: rawPnlPercent,
|
|
149
|
+
pnlCollateral: rawPnlCollateral,
|
|
150
|
+
// Impact-adjusted PnL values (using execution price)
|
|
151
|
+
impactPnlPercent,
|
|
152
|
+
impactPnlCollateral,
|
|
153
|
+
// Price impact
|
|
154
|
+
priceImpact: {
|
|
155
|
+
percent: priceImpactPercent,
|
|
156
|
+
collateral: priceImpactCollateral,
|
|
157
|
+
},
|
|
158
|
+
// Trade value (what trader would receive if closing)
|
|
143
159
|
tradeValue,
|
|
144
|
-
// Unrealized PnL (after holding fees, before closing fee)
|
|
160
|
+
// Unrealized PnL (after holding fees, before closing fee, using market price)
|
|
161
|
+
// Use for open position display
|
|
145
162
|
uPnlCollateral,
|
|
146
163
|
uPnlPercent,
|
|
147
|
-
// Realized PnL (after all fees)
|
|
164
|
+
// Realized PnL (after all fees, using execution price)
|
|
165
|
+
// Use for closing preview
|
|
148
166
|
realizedPnlCollateral,
|
|
149
167
|
realizedPnlPercent,
|
|
150
168
|
// Fee breakdown
|
|
@@ -157,9 +175,7 @@ const getComprehensivePnl = (trade, currentPrice, tradeInfo, context) => {
|
|
|
157
175
|
},
|
|
158
176
|
// Status flags
|
|
159
177
|
isLiquidated,
|
|
160
|
-
isProfitable:
|
|
161
|
-
// Additional info
|
|
162
|
-
leveragedPositionSize,
|
|
178
|
+
isProfitable: rawPnlPercent > 0, // Based on raw PnL
|
|
163
179
|
};
|
|
164
180
|
};
|
|
165
181
|
exports.getComprehensivePnl = getComprehensivePnl;
|
package/lib/trade/pnl/types.d.ts
CHANGED
|
@@ -42,16 +42,20 @@ export type PriceImpactBreakdown = {
|
|
|
42
42
|
export type ComprehensivePnlResult = {
|
|
43
43
|
pnlPercent: number;
|
|
44
44
|
pnlCollateral: number;
|
|
45
|
+
impactPnlPercent: number;
|
|
46
|
+
impactPnlCollateral: number;
|
|
47
|
+
priceImpact: {
|
|
48
|
+
percent: number;
|
|
49
|
+
collateral: number;
|
|
50
|
+
};
|
|
45
51
|
tradeValue: number;
|
|
46
52
|
uPnlCollateral: number;
|
|
47
53
|
uPnlPercent: number;
|
|
48
54
|
realizedPnlCollateral: number;
|
|
49
55
|
realizedPnlPercent: number;
|
|
50
56
|
fees: FeeBreakdown;
|
|
51
|
-
priceImpact?: PriceImpactBreakdown;
|
|
52
57
|
isLiquidated: boolean;
|
|
53
58
|
isProfitable: boolean;
|
|
54
|
-
leveragedPositionSize: number;
|
|
55
59
|
};
|
|
56
60
|
/**
|
|
57
61
|
* @dev Context for comprehensive PnL calculations with nested sub-contexts
|
|
@@ -25,7 +25,7 @@ const calculateClosingPositionSizeToken = (positionSizeCollateral, originalPosit
|
|
|
25
25
|
const totalPositionSizeCollateral = originalCollateral * originalLeverage;
|
|
26
26
|
if (totalPositionSizeCollateral === 0)
|
|
27
27
|
return 0;
|
|
28
|
-
//
|
|
28
|
+
// (positionSizeCollateral * originalPositionSizeToken) / totalPositionSizeCollateral
|
|
29
29
|
return ((positionSizeCollateral * originalPositionSizeToken) /
|
|
30
30
|
totalPositionSizeCollateral);
|
|
31
31
|
};
|
|
@@ -83,22 +83,18 @@ const getTradeClosingPriceImpact = (input, context) => {
|
|
|
83
83
|
}
|
|
84
84
|
}
|
|
85
85
|
// Calculate skew price impact (v10+ only)
|
|
86
|
-
const skewPriceImpactP = input.contractsVersion
|
|
87
|
-
? (0, skew_1.
|
|
86
|
+
const skewPriceImpactP = input.contractsVersion >= types_1.ContractsVersion.V10
|
|
87
|
+
? (0, skew_1.getTradeSkewPriceImpact)({
|
|
88
88
|
collateralIndex: input.collateralIndex,
|
|
89
89
|
pairIndex: input.pairIndex,
|
|
90
90
|
long: input.trade.long,
|
|
91
91
|
open: false,
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
contractsVersion: input.contractsVersion,
|
|
95
|
-
isCounterTrade: input.trade.isCounterTrade,
|
|
96
|
-
}, context.skewContext)
|
|
92
|
+
positionSizeToken,
|
|
93
|
+
}, context.skewContext).priceImpactP
|
|
97
94
|
: 0;
|
|
98
95
|
// Total price impact (all components)
|
|
99
96
|
const totalPriceImpactP = fixedSpreadP + cumulVolPriceImpactP + skewPriceImpactP;
|
|
100
97
|
// Calculate final price after all impacts
|
|
101
|
-
// The direction is already handled by getFixedSpreadP (reverses for closing)
|
|
102
98
|
const priceAfterImpact = (0, __1.getPriceAfterImpact)(input.currentPairPrice, totalPriceImpactP);
|
|
103
99
|
return {
|
|
104
100
|
positionSizeToken,
|
|
@@ -15,7 +15,7 @@ export { getTradeClosingPriceImpact, getTradeClosingPriceImpactAtOracle, buildTr
|
|
|
15
15
|
export { getTradeCumulVolPriceImpactP, getCumulVolPriceImpact, // Convenience function
|
|
16
16
|
getSpreadWithCumulVolPriceImpactP, getSpreadWithPriceImpactP, // Legacy alias
|
|
17
17
|
getProtectionCloseFactor, isProtectionCloseFactorActive, getCumulativeFactor, getLegacyFactor, getFixedSpreadP, getSpreadP, convertOiWindowsSettings, convertOiWindow, convertOiWindows, convertOiWindowsSettingsArray, buildCumulVolContext, CumulVolContext, } from "./cumulVol";
|
|
18
|
-
export { getNetSkewToken, getNetSkewCollateral, getTradeSkewDirection, calculateSkewPriceImpactP, getTradeSkewPriceImpact,
|
|
18
|
+
export { getNetSkewToken, getNetSkewCollateral, getTradeSkewDirection, calculateSkewPriceImpactP, getTradeSkewPriceImpact, calculatePartialSizeToken, SkewPriceImpact, } from "./skew";
|
|
19
19
|
export { convertPairOiToken, convertPairOiTokenArray, convertPairOiCollateral, convertPairOiCollateralArray, convertSkewDepth, convertPairSkewDepths, } from "./skew/converter";
|
|
20
20
|
export { buildSkewPriceImpactContext } from "./skew/builder";
|
|
21
21
|
export type { PairOiToken, PairOiCollateral, SkewPriceImpactInput, SkewPriceImpactResult, SkewPriceImpactContext, TradeSkewParams, PositionSizeResult, } from "./skew/types";
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* @dev Exports cumulative volume, skew, and combined opening/closing price impact functionality
|
|
5
5
|
*/
|
|
6
6
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
|
-
exports.buildSkewPriceImpactContext = exports.convertPairSkewDepths = exports.convertSkewDepth = exports.convertPairOiCollateralArray = exports.convertPairOiCollateral = exports.convertPairOiTokenArray = exports.convertPairOiToken = exports.SkewPriceImpact = exports.calculatePartialSizeToken = exports.
|
|
7
|
+
exports.buildSkewPriceImpactContext = exports.convertPairSkewDepths = exports.convertSkewDepth = exports.convertPairOiCollateralArray = exports.convertPairOiCollateral = exports.convertPairOiTokenArray = exports.convertPairOiToken = exports.SkewPriceImpact = exports.calculatePartialSizeToken = exports.getTradeSkewPriceImpact = exports.calculateSkewPriceImpactP = exports.getTradeSkewDirection = exports.getNetSkewCollateral = exports.getNetSkewToken = exports.buildCumulVolContext = exports.convertOiWindowsSettingsArray = exports.convertOiWindows = exports.convertOiWindow = exports.convertOiWindowsSettings = exports.getSpreadP = exports.getFixedSpreadP = exports.getLegacyFactor = exports.getCumulativeFactor = exports.isProtectionCloseFactorActive = exports.getProtectionCloseFactor = exports.getSpreadWithPriceImpactP = exports.getSpreadWithCumulVolPriceImpactP = exports.getCumulVolPriceImpact = exports.getTradeCumulVolPriceImpactP = exports.buildTradeClosingPriceImpactContext = exports.getTradeClosingPriceImpactAtOracle = exports.getTradeClosingPriceImpact = exports.buildTradeOpeningPriceImpactContext = exports.getTradeOpeningPriceImpactAtMarket = exports.getTradeOpeningPriceImpact = exports.getPriceAfterImpact = void 0;
|
|
8
8
|
/**
|
|
9
9
|
* @dev Calculates price after impact using the same formula as the Solidity contract
|
|
10
10
|
* @dev Mirrors contract's getPriceAfterImpact function
|
|
@@ -63,7 +63,6 @@ Object.defineProperty(exports, "getNetSkewCollateral", { enumerable: true, get:
|
|
|
63
63
|
Object.defineProperty(exports, "getTradeSkewDirection", { enumerable: true, get: function () { return skew_1.getTradeSkewDirection; } });
|
|
64
64
|
Object.defineProperty(exports, "calculateSkewPriceImpactP", { enumerable: true, get: function () { return skew_1.calculateSkewPriceImpactP; } });
|
|
65
65
|
Object.defineProperty(exports, "getTradeSkewPriceImpact", { enumerable: true, get: function () { return skew_1.getTradeSkewPriceImpact; } });
|
|
66
|
-
Object.defineProperty(exports, "getTradeSkewPriceImpactWithChecks", { enumerable: true, get: function () { return skew_1.getTradeSkewPriceImpactWithChecks; } });
|
|
67
66
|
Object.defineProperty(exports, "calculatePartialSizeToken", { enumerable: true, get: function () { return skew_1.calculatePartialSizeToken; } });
|
|
68
67
|
// Types namespace
|
|
69
68
|
Object.defineProperty(exports, "SkewPriceImpact", { enumerable: true, get: function () { return skew_1.SkewPriceImpact; } });
|
|
@@ -31,19 +31,20 @@ const getTradeOpeningPriceImpact = (input, context) => {
|
|
|
31
31
|
true, // open
|
|
32
32
|
0, // lastPosIncreaseBlock - not relevant for opening
|
|
33
33
|
context.cumulVolContext);
|
|
34
|
+
// Calculate price after spread and cumulative volume impact (before skew)
|
|
35
|
+
const priceAfterSpreadAndCumulVolPriceImpact = (0, __1.getPriceAfterImpact)(input.openPrice, spreadP + cumulVolPriceImpactP);
|
|
36
|
+
// Calculate position size in tokens using the price after fixed spread and cumul vol impact
|
|
37
|
+
const positionSizeToken = positionSizeCollateral / priceAfterSpreadAndCumulVolPriceImpact;
|
|
34
38
|
// Calculate skew price impact (v10+ only)
|
|
35
|
-
const
|
|
39
|
+
const skewResult = (0, skew_1.getTradeSkewPriceImpact)({
|
|
36
40
|
collateralIndex: input.collateralIndex,
|
|
37
41
|
pairIndex: input.pairIndex,
|
|
38
42
|
long: input.long,
|
|
39
43
|
open: true,
|
|
40
|
-
|
|
41
|
-
currentPrice: input.openPrice,
|
|
42
|
-
contractsVersion: input.contractsVersion,
|
|
43
|
-
isCounterTrade: input.isCounterTrade,
|
|
44
|
+
positionSizeToken,
|
|
44
45
|
}, context.skewContext);
|
|
46
|
+
const skewPriceImpactP = skewResult.priceImpactP;
|
|
45
47
|
// Total price impact (signed - can be positive or negative)
|
|
46
|
-
// Spread is always positive, impacts can be negative
|
|
47
48
|
const totalPriceImpactP = spreadP + cumulVolPriceImpactP + skewPriceImpactP;
|
|
48
49
|
// Calculate final price after impact using the same formula as Solidity
|
|
49
50
|
const priceAfterImpact = (0, __1.getPriceAfterImpact)(input.openPrice, totalPriceImpactP);
|
|
@@ -53,7 +54,6 @@ const getTradeOpeningPriceImpact = (input, context) => {
|
|
|
53
54
|
const percentProfitP = -totalPriceImpactP;
|
|
54
55
|
return {
|
|
55
56
|
priceAfterImpact,
|
|
56
|
-
priceImpactP: Math.abs(totalPriceImpactP),
|
|
57
57
|
percentProfitP,
|
|
58
58
|
cumulVolPriceImpactP,
|
|
59
59
|
skewPriceImpactP,
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
* @dev Skew price impact calculations for v10+ trades
|
|
3
3
|
* @dev Based on formula: (existingSkew + tradeSize/2) / skewDepth
|
|
4
4
|
*/
|
|
5
|
-
import { PairOiToken, SkewPriceImpactInput, SkewPriceImpactResult, SkewPriceImpactContext
|
|
5
|
+
import { PairOiToken, SkewPriceImpactInput, SkewPriceImpactResult, SkewPriceImpactContext } from "./types";
|
|
6
6
|
/**
|
|
7
7
|
* @dev Calculates net skew in tokens (long - short)
|
|
8
8
|
* @param pairOi Pair OI data with long and short token amounts
|
|
@@ -28,10 +28,10 @@ export declare const getTradeSkewDirection: (long: boolean, open: boolean) => bo
|
|
|
28
28
|
* @param existingSkewToken Current net skew in tokens (signed)
|
|
29
29
|
* @param tradeSizeToken Trade size in tokens (always positive)
|
|
30
30
|
* @param skewDepth Skew depth in tokens
|
|
31
|
-
* @param
|
|
31
|
+
* @param tradePositiveSkew Whether trade increases skew in its direction
|
|
32
32
|
* @returns Price impact percentage (can be positive or negative)
|
|
33
33
|
*/
|
|
34
|
-
export declare const calculateSkewPriceImpactP: (existingSkewToken: number, tradeSizeToken: number, skewDepth: number,
|
|
34
|
+
export declare const calculateSkewPriceImpactP: (existingSkewToken: number, tradeSizeToken: number, skewDepth: number, tradePositiveSkew: boolean) => number;
|
|
35
35
|
/**
|
|
36
36
|
* @dev Main function to calculate skew price impact for a trade
|
|
37
37
|
* @param input Trade parameters
|
|
@@ -39,13 +39,6 @@ export declare const calculateSkewPriceImpactP: (existingSkewToken: number, trad
|
|
|
39
39
|
* @returns Skew price impact result
|
|
40
40
|
*/
|
|
41
41
|
export declare const getTradeSkewPriceImpact: (input: SkewPriceImpactInput, context: SkewPriceImpactContext) => SkewPriceImpactResult;
|
|
42
|
-
/**
|
|
43
|
-
* @dev Calculate skew price impact for a trade with all parameters
|
|
44
|
-
* @param params Trade parameters including price and version checks
|
|
45
|
-
* @param context Skew price impact context
|
|
46
|
-
* @returns Price impact percentage or 0 if not applicable
|
|
47
|
-
*/
|
|
48
|
-
export declare const getTradeSkewPriceImpactWithChecks: (params: TradeSkewParams, context: SkewPriceImpactContext) => number;
|
|
49
42
|
/**
|
|
50
43
|
* @dev Calculate position sizes for partial operations
|
|
51
44
|
* @param originalSizeCollateral Original position size in collateral
|
|
@@ -30,9 +30,7 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
|
30
30
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
31
31
|
};
|
|
32
32
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
33
|
-
exports.SkewPriceImpact = exports.calculatePartialSizeToken = exports.
|
|
34
|
-
const utils_1 = require("../../utils");
|
|
35
|
-
const types_1 = require("../../../contracts/types");
|
|
33
|
+
exports.SkewPriceImpact = exports.calculatePartialSizeToken = exports.getTradeSkewPriceImpact = exports.calculateSkewPriceImpactP = exports.getTradeSkewDirection = exports.getNetSkewCollateral = exports.getNetSkewToken = void 0;
|
|
36
34
|
// Constants
|
|
37
35
|
const PRICE_IMPACT_DIVIDER = 2; // Half price impact to match cumulative volume impact scale
|
|
38
36
|
/**
|
|
@@ -71,18 +69,18 @@ exports.getTradeSkewDirection = getTradeSkewDirection;
|
|
|
71
69
|
* @param existingSkewToken Current net skew in tokens (signed)
|
|
72
70
|
* @param tradeSizeToken Trade size in tokens (always positive)
|
|
73
71
|
* @param skewDepth Skew depth in tokens
|
|
74
|
-
* @param
|
|
72
|
+
* @param tradePositiveSkew Whether trade increases skew in its direction
|
|
75
73
|
* @returns Price impact percentage (can be positive or negative)
|
|
76
74
|
*/
|
|
77
|
-
const calculateSkewPriceImpactP = (existingSkewToken, tradeSizeToken, skewDepth,
|
|
75
|
+
const calculateSkewPriceImpactP = (existingSkewToken, tradeSizeToken, skewDepth, tradePositiveSkew) => {
|
|
78
76
|
if (skewDepth === 0) {
|
|
79
77
|
return 0; // No impact if depth is 0
|
|
80
78
|
}
|
|
81
79
|
// Convert signed values based on trade direction
|
|
82
|
-
const tradeSkewMultiplier =
|
|
80
|
+
const tradeSkewMultiplier = tradePositiveSkew ? 1 : -1;
|
|
83
81
|
const signedExistingSkew = existingSkewToken;
|
|
84
82
|
const signedTradeSize = tradeSizeToken * tradeSkewMultiplier;
|
|
85
|
-
//
|
|
83
|
+
// (existingSkew + tradeSize/2) / skewDepth
|
|
86
84
|
const numerator = signedExistingSkew + signedTradeSize / 2;
|
|
87
85
|
const priceImpactP = numerator / skewDepth;
|
|
88
86
|
// Apply divider to match cumulative volume impact scale
|
|
@@ -100,10 +98,10 @@ const getTradeSkewPriceImpact = (input, context) => {
|
|
|
100
98
|
const { skewDepth, pairOiToken: pairOi } = context;
|
|
101
99
|
// Calculate net skew
|
|
102
100
|
const netSkewToken = (0, exports.getNetSkewToken)(pairOi);
|
|
103
|
-
// Determine trade direction
|
|
104
|
-
const
|
|
101
|
+
// Determine trade direction
|
|
102
|
+
const tradePositiveSkew = (0, exports.getTradeSkewDirection)(input.long, input.open);
|
|
105
103
|
// Calculate price impact
|
|
106
|
-
const priceImpactP = (0, exports.calculateSkewPriceImpactP)(netSkewToken, input.positionSizeToken, skewDepth,
|
|
104
|
+
const priceImpactP = (0, exports.calculateSkewPriceImpactP)(netSkewToken, input.positionSizeToken, skewDepth, tradePositiveSkew);
|
|
107
105
|
// Determine trade direction relative to skew
|
|
108
106
|
let tradeDirection;
|
|
109
107
|
if (priceImpactP > 0) {
|
|
@@ -123,34 +121,6 @@ const getTradeSkewPriceImpact = (input, context) => {
|
|
|
123
121
|
};
|
|
124
122
|
};
|
|
125
123
|
exports.getTradeSkewPriceImpact = getTradeSkewPriceImpact;
|
|
126
|
-
/**
|
|
127
|
-
* @dev Calculate skew price impact for a trade with all parameters
|
|
128
|
-
* @param params Trade parameters including price and version checks
|
|
129
|
-
* @param context Skew price impact context
|
|
130
|
-
* @returns Price impact percentage or 0 if not applicable
|
|
131
|
-
*/
|
|
132
|
-
const getTradeSkewPriceImpactWithChecks = (params, context) => {
|
|
133
|
-
// v10+ trades only
|
|
134
|
-
if (params.contractsVersion < types_1.ContractsVersion.V10) {
|
|
135
|
-
return 0;
|
|
136
|
-
}
|
|
137
|
-
// Counter trades don't pay skew impact
|
|
138
|
-
if (params.isCounterTrade) {
|
|
139
|
-
return 0;
|
|
140
|
-
}
|
|
141
|
-
// Calculate position size in tokens
|
|
142
|
-
const positionSizeToken = (0, utils_1.calculatePositionSizeToken)(params.positionSizeCollateral, params.currentPrice);
|
|
143
|
-
// Get skew price impact
|
|
144
|
-
const result = (0, exports.getTradeSkewPriceImpact)({
|
|
145
|
-
collateralIndex: params.collateralIndex,
|
|
146
|
-
pairIndex: params.pairIndex,
|
|
147
|
-
long: params.long,
|
|
148
|
-
open: params.open,
|
|
149
|
-
positionSizeToken,
|
|
150
|
-
}, context);
|
|
151
|
-
return result.priceImpactP;
|
|
152
|
-
};
|
|
153
|
-
exports.getTradeSkewPriceImpactWithChecks = getTradeSkewPriceImpactWithChecks;
|
|
154
124
|
/**
|
|
155
125
|
* @dev Calculate position sizes for partial operations
|
|
156
126
|
* @param originalSizeCollateral Original position size in collateral
|