@drift-labs/sdk 2.43.0-beta.0 → 2.43.0-beta.10
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/README.md +1 -0
- package/VERSION +1 -1
- package/bun.lockb +0 -0
- package/get_events.ts +47 -0
- package/lib/constants/perpMarkets.js +20 -0
- package/lib/constants/spotMarkets.js +1 -1
- package/lib/dlob/DLOB.js +3 -1
- package/lib/dlob/orderBookLevels.d.ts +2 -0
- package/lib/dlob/orderBookLevels.js +9 -1
- package/lib/user.js +4 -1
- package/package.json +2 -1
- package/src/constants/perpMarkets.ts +20 -0
- package/src/constants/spotMarkets.ts +1 -1
- package/src/dlob/DLOB.ts +3 -1
- package/src/dlob/orderBookLevels.ts +13 -1
- package/src/user.ts +5 -1
- package/tests/amm/test.ts +78 -0
- package/tests/user/test.ts +10 -13
package/README.md
CHANGED
|
@@ -244,3 +244,4 @@ Drift Protocol v2 is licensed under [Apache 2.0](./LICENSE).
|
|
|
244
244
|
Unless you explicitly state otherwise, any contribution intentionally submitted
|
|
245
245
|
for inclusion in Drift SDK by you, as defined in the Apache-2.0 license, shall be
|
|
246
246
|
licensed as above, without any additional terms or conditions.
|
|
247
|
+
|
package/VERSION
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
2.43.0-beta.
|
|
1
|
+
2.43.0-beta.10
|
package/bun.lockb
CHANGED
|
Binary file
|
package/get_events.ts
ADDED
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
import { Connection, Keypair, PublicKey } from '@solana/web3.js';
|
|
2
|
+
import {
|
|
3
|
+
configs,
|
|
4
|
+
DriftClient,
|
|
5
|
+
Wallet,
|
|
6
|
+
} from "@drift-labs/sdk";
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
async function main() {
|
|
10
|
+
|
|
11
|
+
const driftConfig = configs['mainnet-beta'];
|
|
12
|
+
const connection = new Connection('https://api.mainnet-beta.solana.com');
|
|
13
|
+
|
|
14
|
+
const driftClient = new DriftClient({
|
|
15
|
+
connection: connection,
|
|
16
|
+
wallet: new Wallet(new Keypair()),
|
|
17
|
+
programID: new PublicKey(driftConfig.DRIFT_PROGRAM_ID),
|
|
18
|
+
userStats: true,
|
|
19
|
+
env: 'mainnet-beta',
|
|
20
|
+
});
|
|
21
|
+
console.log(`driftClientSubscribed: ${await driftClient.subscribe()}`);
|
|
22
|
+
|
|
23
|
+
const txHash = "3gvGQufckXGHrFDv4dNWEXuXKRMy3NZkKHMyFrAhLoYScaXXTGCp9vq58kWkfyJ8oDYZrz4bTyGayjUy9PKigeLS";
|
|
24
|
+
|
|
25
|
+
const tx = await driftClient.connection.getParsedTransaction(txHash, {
|
|
26
|
+
commitment: "confirmed",
|
|
27
|
+
maxSupportedTransactionVersion: 0,
|
|
28
|
+
});
|
|
29
|
+
|
|
30
|
+
let logIdx = 0;
|
|
31
|
+
// @ts-ignore
|
|
32
|
+
for (const event of driftClient.program._events._eventParser.parseLogs(tx!.meta!.logMessages)) {
|
|
33
|
+
console.log("----------------------------------------");
|
|
34
|
+
console.log(`Log ${logIdx++}`);
|
|
35
|
+
console.log("----------------------------------------");
|
|
36
|
+
console.log(`${JSON.stringify(event, null, 2)}`);
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
console.log("========================================");
|
|
40
|
+
console.log("Raw transaction logs");
|
|
41
|
+
console.log("========================================");
|
|
42
|
+
console.log(JSON.stringify(tx!.meta!.logMessages, null, 2));
|
|
43
|
+
|
|
44
|
+
process.exit(0);
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
main().catch(console.error);
|
|
@@ -174,6 +174,16 @@ exports.DevnetPerpMarkets = [
|
|
|
174
174
|
launchTs: 1698074659000,
|
|
175
175
|
oracleSource: __1.OracleSource.PYTH,
|
|
176
176
|
},
|
|
177
|
+
{
|
|
178
|
+
fullName: 'Rollbit',
|
|
179
|
+
category: ['Exchange'],
|
|
180
|
+
symbol: 'RLB-PERP',
|
|
181
|
+
baseAssetSymbol: 'RLB',
|
|
182
|
+
marketIndex: 17,
|
|
183
|
+
oracle: new web3_js_1.PublicKey('6BmJozusMugAySsfNfMFsU1YRWcGwyP3oycNX9Pv9oCz'),
|
|
184
|
+
launchTs: 11699265968000,
|
|
185
|
+
oracleSource: __1.OracleSource.PYTH,
|
|
186
|
+
},
|
|
177
187
|
];
|
|
178
188
|
exports.MainnetPerpMarkets = [
|
|
179
189
|
{
|
|
@@ -346,6 +356,16 @@ exports.MainnetPerpMarkets = [
|
|
|
346
356
|
launchTs: 1698074659000,
|
|
347
357
|
oracleSource: __1.OracleSource.PYTH,
|
|
348
358
|
},
|
|
359
|
+
{
|
|
360
|
+
fullName: 'Rollbit',
|
|
361
|
+
category: ['Exchange'],
|
|
362
|
+
symbol: 'RLB-PERP',
|
|
363
|
+
baseAssetSymbol: 'RLB',
|
|
364
|
+
marketIndex: 17,
|
|
365
|
+
oracle: new web3_js_1.PublicKey('4BA3RcS4zE32WWgp49vvvre2t6nXY1W1kMyKZxeeuUey'),
|
|
366
|
+
launchTs: 11699265968000,
|
|
367
|
+
oracleSource: __1.OracleSource.PYTH,
|
|
368
|
+
},
|
|
349
369
|
];
|
|
350
370
|
exports.PerpMarkets = {
|
|
351
371
|
devnet: exports.DevnetPerpMarkets,
|
|
@@ -107,7 +107,7 @@ exports.MainnetSpotMarkets = [
|
|
|
107
107
|
mint: new web3_js_1.PublicKey('J1toso1uCk3RLmjorhTtrVwY9HJ7X8V9yYac6Y7kGCPn'),
|
|
108
108
|
precision: new __1.BN(10).pow(numericConstants_1.NINE),
|
|
109
109
|
precisionExp: numericConstants_1.NINE,
|
|
110
|
-
serumMarket: new web3_js_1.PublicKey('
|
|
110
|
+
serumMarket: new web3_js_1.PublicKey('DkbVbMhFxswS32xnn1K2UY4aoBugXooBTxdzkWWDWRkH'),
|
|
111
111
|
},
|
|
112
112
|
];
|
|
113
113
|
exports.SpotMarkets = {
|
package/lib/dlob/DLOB.js
CHANGED
|
@@ -600,7 +600,7 @@ class DLOB {
|
|
|
600
600
|
bestGenerator.next = bestGenerator.generator.next();
|
|
601
601
|
continue;
|
|
602
602
|
}
|
|
603
|
-
if (filterFcn && filterFcn(bestGenerator.next.value)) {
|
|
603
|
+
if (filterFcn && !filterFcn(bestGenerator.next.value)) {
|
|
604
604
|
bestGenerator.next = bestGenerator.generator.next();
|
|
605
605
|
continue;
|
|
606
606
|
}
|
|
@@ -956,6 +956,7 @@ class DLOB {
|
|
|
956
956
|
return {
|
|
957
957
|
bids,
|
|
958
958
|
asks,
|
|
959
|
+
slot,
|
|
959
960
|
};
|
|
960
961
|
}
|
|
961
962
|
/**
|
|
@@ -990,6 +991,7 @@ class DLOB {
|
|
|
990
991
|
return {
|
|
991
992
|
bids,
|
|
992
993
|
asks,
|
|
994
|
+
slot,
|
|
993
995
|
};
|
|
994
996
|
}
|
|
995
997
|
estimateFillExactBaseAmountInForSide(baseAmountIn, oraclePriceData, slot, dlobSide) {
|
|
@@ -12,6 +12,7 @@ export type L2Level = {
|
|
|
12
12
|
export type L2OrderBook = {
|
|
13
13
|
asks: L2Level[];
|
|
14
14
|
bids: L2Level[];
|
|
15
|
+
slot?: number;
|
|
15
16
|
};
|
|
16
17
|
export interface L2OrderBookGenerator {
|
|
17
18
|
getL2Asks(): Generator<L2Level>;
|
|
@@ -26,6 +27,7 @@ export type L3Level = {
|
|
|
26
27
|
export type L3OrderBook = {
|
|
27
28
|
asks: L3Level[];
|
|
28
29
|
bids: L3Level[];
|
|
30
|
+
slot?: number;
|
|
29
31
|
};
|
|
30
32
|
export declare const DEFAULT_TOP_OF_BOOK_QUOTE_AMOUNTS: BN[];
|
|
31
33
|
/**
|
|
@@ -92,7 +92,14 @@ function getVammL2Generator({ marketAccount, oraclePriceData, numOrders, now, to
|
|
|
92
92
|
(0, assert_1.assert)(topOfBookQuoteAmounts.length < numOrders);
|
|
93
93
|
}
|
|
94
94
|
const updatedAmm = (0, __1.calculateUpdatedAMM)(marketAccount.amm, oraclePriceData);
|
|
95
|
-
|
|
95
|
+
let [openBids, openAsks] = (0, __1.calculateMarketOpenBidAsk)(updatedAmm.baseAssetReserve, updatedAmm.minBaseAssetReserve, updatedAmm.maxBaseAssetReserve, updatedAmm.orderStepSize);
|
|
96
|
+
const minOrderSize = marketAccount.amm.orderStepSize;
|
|
97
|
+
if (openBids.lt(minOrderSize.muln(2))) {
|
|
98
|
+
openBids = __1.ZERO;
|
|
99
|
+
}
|
|
100
|
+
if (openAsks.abs().lt(minOrderSize.muln(2))) {
|
|
101
|
+
openAsks = __1.ZERO;
|
|
102
|
+
}
|
|
96
103
|
now = now !== null && now !== void 0 ? now : new __1.BN(Date.now() / 1000);
|
|
97
104
|
const [bidReserves, askReserves] = (0, __1.calculateSpreadReserves)(updatedAmm, oraclePriceData, now);
|
|
98
105
|
let numBids = 0;
|
|
@@ -202,6 +209,7 @@ function groupL2(l2, grouping, depth) {
|
|
|
202
209
|
return {
|
|
203
210
|
bids: groupL2Levels(l2.bids, grouping, __1.PositionDirection.LONG, depth),
|
|
204
211
|
asks: groupL2Levels(l2.asks, grouping, __1.PositionDirection.SHORT, depth),
|
|
212
|
+
slot: l2.slot,
|
|
205
213
|
};
|
|
206
214
|
}
|
|
207
215
|
exports.groupL2 = groupL2;
|
package/lib/user.js
CHANGED
|
@@ -1564,7 +1564,10 @@ class User {
|
|
|
1564
1564
|
this.getEmptyPosition(targetMarketIndex);
|
|
1565
1565
|
const oracleData = this.getOracleDataForPerpMarket(targetMarketIndex);
|
|
1566
1566
|
let currentPositionQuoteAmount = this.getPerpPositionValue(targetMarketIndex, oracleData, includeOpenOrders);
|
|
1567
|
-
const
|
|
1567
|
+
const worstCaseBase = (0, margin_1.calculateWorstCaseBaseAssetAmount)(currentPosition);
|
|
1568
|
+
// current side is short if position base asset amount is negative OR there is no position open but open orders are short
|
|
1569
|
+
const currentSide = currentPosition.baseAssetAmount.isNeg() ||
|
|
1570
|
+
(currentPosition.baseAssetAmount.eq(numericConstants_1.ZERO) && worstCaseBase.isNeg())
|
|
1568
1571
|
? _1.PositionDirection.SHORT
|
|
1569
1572
|
: _1.PositionDirection.LONG;
|
|
1570
1573
|
if (currentSide === _1.PositionDirection.SHORT)
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@drift-labs/sdk",
|
|
3
|
-
"version": "2.43.0-beta.
|
|
3
|
+
"version": "2.43.0-beta.10",
|
|
4
4
|
"main": "lib/index.js",
|
|
5
5
|
"types": "lib/index.d.ts",
|
|
6
6
|
"author": "crispheaney",
|
|
@@ -52,6 +52,7 @@
|
|
|
52
52
|
"@typescript-eslint/eslint-plugin": "^4.28.0",
|
|
53
53
|
"@typescript-eslint/parser": "^4.28.0",
|
|
54
54
|
"chai": "^4.3.6",
|
|
55
|
+
"encoding": "^0.1.13",
|
|
55
56
|
"eslint": "^7.29.0",
|
|
56
57
|
"eslint-config-prettier": "^8.3.0",
|
|
57
58
|
"eslint-plugin-prettier": "^3.4.0",
|
|
@@ -184,6 +184,16 @@ export const DevnetPerpMarkets: PerpMarketConfig[] = [
|
|
|
184
184
|
launchTs: 1698074659000,
|
|
185
185
|
oracleSource: OracleSource.PYTH,
|
|
186
186
|
},
|
|
187
|
+
{
|
|
188
|
+
fullName: 'Rollbit',
|
|
189
|
+
category: ['Exchange'],
|
|
190
|
+
symbol: 'RLB-PERP',
|
|
191
|
+
baseAssetSymbol: 'RLB',
|
|
192
|
+
marketIndex: 17,
|
|
193
|
+
oracle: new PublicKey('6BmJozusMugAySsfNfMFsU1YRWcGwyP3oycNX9Pv9oCz'),
|
|
194
|
+
launchTs: 11699265968000,
|
|
195
|
+
oracleSource: OracleSource.PYTH,
|
|
196
|
+
},
|
|
187
197
|
];
|
|
188
198
|
|
|
189
199
|
export const MainnetPerpMarkets: PerpMarketConfig[] = [
|
|
@@ -357,6 +367,16 @@ export const MainnetPerpMarkets: PerpMarketConfig[] = [
|
|
|
357
367
|
launchTs: 1698074659000,
|
|
358
368
|
oracleSource: OracleSource.PYTH,
|
|
359
369
|
},
|
|
370
|
+
{
|
|
371
|
+
fullName: 'Rollbit',
|
|
372
|
+
category: ['Exchange'],
|
|
373
|
+
symbol: 'RLB-PERP',
|
|
374
|
+
baseAssetSymbol: 'RLB',
|
|
375
|
+
marketIndex: 17,
|
|
376
|
+
oracle: new PublicKey('4BA3RcS4zE32WWgp49vvvre2t6nXY1W1kMyKZxeeuUey'),
|
|
377
|
+
launchTs: 11699265968000,
|
|
378
|
+
oracleSource: OracleSource.PYTH,
|
|
379
|
+
},
|
|
360
380
|
];
|
|
361
381
|
|
|
362
382
|
export const PerpMarkets: { [key in DriftEnv]: PerpMarketConfig[] } = {
|
|
@@ -135,7 +135,7 @@ export const MainnetSpotMarkets: SpotMarketConfig[] = [
|
|
|
135
135
|
mint: new PublicKey('J1toso1uCk3RLmjorhTtrVwY9HJ7X8V9yYac6Y7kGCPn'),
|
|
136
136
|
precision: new BN(10).pow(NINE),
|
|
137
137
|
precisionExp: NINE,
|
|
138
|
-
serumMarket: new PublicKey('
|
|
138
|
+
serumMarket: new PublicKey('DkbVbMhFxswS32xnn1K2UY4aoBugXooBTxdzkWWDWRkH'),
|
|
139
139
|
},
|
|
140
140
|
];
|
|
141
141
|
|
package/src/dlob/DLOB.ts
CHANGED
|
@@ -1111,7 +1111,7 @@ export class DLOB {
|
|
|
1111
1111
|
continue;
|
|
1112
1112
|
}
|
|
1113
1113
|
|
|
1114
|
-
if (filterFcn && filterFcn(bestGenerator.next.value)) {
|
|
1114
|
+
if (filterFcn && !filterFcn(bestGenerator.next.value)) {
|
|
1115
1115
|
bestGenerator.next = bestGenerator.generator.next();
|
|
1116
1116
|
continue;
|
|
1117
1117
|
}
|
|
@@ -1725,6 +1725,7 @@ export class DLOB {
|
|
|
1725
1725
|
return {
|
|
1726
1726
|
bids,
|
|
1727
1727
|
asks,
|
|
1728
|
+
slot,
|
|
1728
1729
|
};
|
|
1729
1730
|
}
|
|
1730
1731
|
|
|
@@ -1785,6 +1786,7 @@ export class DLOB {
|
|
|
1785
1786
|
return {
|
|
1786
1787
|
bids,
|
|
1787
1788
|
asks,
|
|
1789
|
+
slot,
|
|
1788
1790
|
};
|
|
1789
1791
|
}
|
|
1790
1792
|
|
|
@@ -29,6 +29,7 @@ export type L2Level = {
|
|
|
29
29
|
export type L2OrderBook = {
|
|
30
30
|
asks: L2Level[];
|
|
31
31
|
bids: L2Level[];
|
|
32
|
+
slot?: number;
|
|
32
33
|
};
|
|
33
34
|
|
|
34
35
|
export interface L2OrderBookGenerator {
|
|
@@ -46,6 +47,7 @@ export type L3Level = {
|
|
|
46
47
|
export type L3OrderBook = {
|
|
47
48
|
asks: L3Level[];
|
|
48
49
|
bids: L3Level[];
|
|
50
|
+
slot?: number;
|
|
49
51
|
};
|
|
50
52
|
|
|
51
53
|
export const DEFAULT_TOP_OF_BOOK_QUOTE_AMOUNTS = [
|
|
@@ -164,13 +166,22 @@ export function getVammL2Generator({
|
|
|
164
166
|
|
|
165
167
|
const updatedAmm = calculateUpdatedAMM(marketAccount.amm, oraclePriceData);
|
|
166
168
|
|
|
167
|
-
|
|
169
|
+
let [openBids, openAsks] = calculateMarketOpenBidAsk(
|
|
168
170
|
updatedAmm.baseAssetReserve,
|
|
169
171
|
updatedAmm.minBaseAssetReserve,
|
|
170
172
|
updatedAmm.maxBaseAssetReserve,
|
|
171
173
|
updatedAmm.orderStepSize
|
|
172
174
|
);
|
|
173
175
|
|
|
176
|
+
const minOrderSize = marketAccount.amm.orderStepSize;
|
|
177
|
+
if (openBids.lt(minOrderSize.muln(2))) {
|
|
178
|
+
openBids = ZERO;
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
if (openAsks.abs().lt(minOrderSize.muln(2))) {
|
|
182
|
+
openAsks = ZERO;
|
|
183
|
+
}
|
|
184
|
+
|
|
174
185
|
now = now ?? new BN(Date.now() / 1000);
|
|
175
186
|
const [bidReserves, askReserves] = calculateSpreadReserves(
|
|
176
187
|
updatedAmm,
|
|
@@ -354,6 +365,7 @@ export function groupL2(
|
|
|
354
365
|
return {
|
|
355
366
|
bids: groupL2Levels(l2.bids, grouping, PositionDirection.LONG, depth),
|
|
356
367
|
asks: groupL2Levels(l2.asks, grouping, PositionDirection.SHORT, depth),
|
|
368
|
+
slot: l2.slot,
|
|
357
369
|
};
|
|
358
370
|
}
|
|
359
371
|
|
package/src/user.ts
CHANGED
|
@@ -2884,8 +2884,12 @@ export class User {
|
|
|
2884
2884
|
includeOpenOrders
|
|
2885
2885
|
);
|
|
2886
2886
|
|
|
2887
|
+
const worstCaseBase = calculateWorstCaseBaseAssetAmount(currentPosition);
|
|
2888
|
+
|
|
2889
|
+
// current side is short if position base asset amount is negative OR there is no position open but open orders are short
|
|
2887
2890
|
const currentSide =
|
|
2888
|
-
currentPosition
|
|
2891
|
+
currentPosition.baseAssetAmount.isNeg() ||
|
|
2892
|
+
(currentPosition.baseAssetAmount.eq(ZERO) && worstCaseBase.isNeg())
|
|
2889
2893
|
? PositionDirection.SHORT
|
|
2890
2894
|
: PositionDirection.LONG;
|
|
2891
2895
|
|
package/tests/amm/test.ts
CHANGED
|
@@ -956,4 +956,82 @@ describe('AMM Tests', () => {
|
|
|
956
956
|
);
|
|
957
957
|
assert(totalAskSize.sub(openAsks.abs()).lte(new BN(5))); // only tiny rounding errors
|
|
958
958
|
});
|
|
959
|
+
|
|
960
|
+
it('orderbook L2 gen (no topOfBookQuoteAmounts, 10 numOrders, no liquidity)', async () => {
|
|
961
|
+
const myMockPerpMarkets = _.cloneDeep(mockPerpMarkets);
|
|
962
|
+
|
|
963
|
+
const mockMarket1: PerpMarketAccount = myMockPerpMarkets[0];
|
|
964
|
+
const cc = 38104569;
|
|
965
|
+
mockMarket1.amm.baseAssetReserve = new BN(cc).mul(BASE_PRECISION);
|
|
966
|
+
mockMarket1.amm.minOrderSize = new BN(5);
|
|
967
|
+
mockMarket1.amm.maxBaseAssetReserve = mockMarket1.amm.baseAssetReserve.add(
|
|
968
|
+
new BN(9)
|
|
969
|
+
);
|
|
970
|
+
mockMarket1.amm.minBaseAssetReserve =
|
|
971
|
+
mockMarket1.amm.baseAssetReserve.sub(new BN(9));
|
|
972
|
+
mockMarket1.amm.quoteAssetReserve = new BN(cc).mul(BASE_PRECISION);
|
|
973
|
+
mockMarket1.amm.pegMultiplier = new BN(18.32 * PEG_PRECISION.toNumber());
|
|
974
|
+
mockMarket1.amm.sqrtK = new BN(cc).mul(BASE_PRECISION);
|
|
975
|
+
|
|
976
|
+
const now = new BN(1688881915);
|
|
977
|
+
|
|
978
|
+
const oraclePriceData: OraclePriceData = {
|
|
979
|
+
price: new BN(18.624 * PRICE_PRECISION.toNumber()),
|
|
980
|
+
slot: new BN(0),
|
|
981
|
+
confidence: new BN(1),
|
|
982
|
+
hasSufficientNumberOfDataPoints: true,
|
|
983
|
+
};
|
|
984
|
+
mockMarket1.amm.historicalOracleData.lastOraclePrice = new BN(
|
|
985
|
+
18.5535 * PRICE_PRECISION.toNumber()
|
|
986
|
+
);
|
|
987
|
+
|
|
988
|
+
const updatedAmm = calculateUpdatedAMM(mockMarket1.amm, oraclePriceData);
|
|
989
|
+
|
|
990
|
+
const [openBids, openAsks] = calculateMarketOpenBidAsk(
|
|
991
|
+
updatedAmm.baseAssetReserve,
|
|
992
|
+
updatedAmm.minBaseAssetReserve,
|
|
993
|
+
updatedAmm.maxBaseAssetReserve,
|
|
994
|
+
updatedAmm.orderStepSize
|
|
995
|
+
);
|
|
996
|
+
|
|
997
|
+
const generator = getVammL2Generator({
|
|
998
|
+
marketAccount: mockMarket1,
|
|
999
|
+
oraclePriceData,
|
|
1000
|
+
numOrders: 10,
|
|
1001
|
+
now,
|
|
1002
|
+
topOfBookQuoteAmounts: [],
|
|
1003
|
+
});
|
|
1004
|
+
|
|
1005
|
+
const bids = Array.from(generator.getL2Bids());
|
|
1006
|
+
// console.log(bids);
|
|
1007
|
+
|
|
1008
|
+
const totalBidSize = bids.reduce((total: BN, order: L2Level) => {
|
|
1009
|
+
return total.add(order.size);
|
|
1010
|
+
}, ZERO);
|
|
1011
|
+
|
|
1012
|
+
console.log(
|
|
1013
|
+
'totalBidSize:',
|
|
1014
|
+
totalBidSize.toString(),
|
|
1015
|
+
'openBids:',
|
|
1016
|
+
openBids.toString()
|
|
1017
|
+
);
|
|
1018
|
+
assert(openBids.eq(new BN(9)));
|
|
1019
|
+
assert(totalBidSize.eq(ZERO));
|
|
1020
|
+
|
|
1021
|
+
const asks = Array.from(generator.getL2Asks());
|
|
1022
|
+
// console.log(asks);
|
|
1023
|
+
|
|
1024
|
+
const totalAskSize = asks.reduce((total: BN, order: L2Level) => {
|
|
1025
|
+
return total.add(order.size);
|
|
1026
|
+
}, ZERO);
|
|
1027
|
+
console.log(
|
|
1028
|
+
'totalAskSize:',
|
|
1029
|
+
totalAskSize.toString(),
|
|
1030
|
+
'openAsks:',
|
|
1031
|
+
openAsks.toString()
|
|
1032
|
+
);
|
|
1033
|
+
|
|
1034
|
+
assert(openAsks.eq(new BN(-9)));
|
|
1035
|
+
assert(totalAskSize.eq(ZERO));
|
|
1036
|
+
});
|
|
959
1037
|
});
|
package/tests/user/test.ts
CHANGED
|
@@ -289,8 +289,9 @@ describe('User Tests', () => {
|
|
|
289
289
|
mockUser.getMaxLeverageForPerp(0).toString()
|
|
290
290
|
);
|
|
291
291
|
assert(mockUser.getMaxLeverageForPerp(0).eq(new BN('50000'))); // 5x
|
|
292
|
-
assert(
|
|
293
|
-
|
|
292
|
+
assert(
|
|
293
|
+
mockUser.getMaxLeverageForPerp(0, 'Maintenance').eq(new BN('100000'))
|
|
294
|
+
); // 10x
|
|
294
295
|
});
|
|
295
296
|
|
|
296
297
|
it('worst case token amount', async () => {
|
|
@@ -399,8 +400,7 @@ describe('User Tests', () => {
|
|
|
399
400
|
); // -$2k
|
|
400
401
|
});
|
|
401
402
|
|
|
402
|
-
|
|
403
|
-
it('custom margin ratio (sol spot)', async() => {
|
|
403
|
+
it('custom margin ratio (sol spot)', async () => {
|
|
404
404
|
const myMockUserAccount = _.cloneDeep(mockUserAccount);
|
|
405
405
|
|
|
406
406
|
const solMarket = Object.assign({}, _.cloneDeep(mockSpotMarkets[1]), {
|
|
@@ -427,12 +427,10 @@ describe('User Tests', () => {
|
|
|
427
427
|
);
|
|
428
428
|
|
|
429
429
|
console.log(worstCase);
|
|
430
|
-
assert(worstCase.weight.eq(new BN(8000)));
|
|
431
|
-
|
|
430
|
+
assert(worstCase.weight.eq(new BN(8000)));
|
|
432
431
|
|
|
433
432
|
myMockUserAccount.maxMarginRatio = MARGIN_PRECISION.toNumber(); // max 1x pls
|
|
434
433
|
|
|
435
|
-
|
|
436
434
|
const worstCaseAfter = getWorstCaseTokenAmounts(
|
|
437
435
|
spotPosition,
|
|
438
436
|
solMarket,
|
|
@@ -443,10 +441,9 @@ describe('User Tests', () => {
|
|
|
443
441
|
|
|
444
442
|
console.log(worstCaseAfter);
|
|
445
443
|
assert(worstCaseAfter.weight.eq(new BN(0))); // not allowed to increase exposure
|
|
446
|
-
|
|
447
444
|
});
|
|
448
445
|
|
|
449
|
-
it('custom margin ratio (sol perp)', async() => {
|
|
446
|
+
it('custom margin ratio (sol perp)', async () => {
|
|
450
447
|
const myMockPerpMarkets = _.cloneDeep(mockPerpMarkets);
|
|
451
448
|
const myMockSpotMarkets = _.cloneDeep(mockSpotMarkets);
|
|
452
449
|
const myMockUserAccount = _.cloneDeep(mockUserAccount);
|
|
@@ -469,7 +466,6 @@ describe('User Tests', () => {
|
|
|
469
466
|
[1, 1, 1, 1, 1, 1, 1, 1]
|
|
470
467
|
);
|
|
471
468
|
|
|
472
|
-
|
|
473
469
|
assert(mockUser.getTokenAmount(0).eq(new BN('10000000000')));
|
|
474
470
|
assert(mockUser.getNetSpotMarketValue().eq(new BN('10000000000')));
|
|
475
471
|
assert(
|
|
@@ -486,7 +482,9 @@ describe('User Tests', () => {
|
|
|
486
482
|
assert(iLev == 5000);
|
|
487
483
|
assert(mLev == 10000);
|
|
488
484
|
|
|
489
|
-
myMockUserAccount.maxMarginRatio = MARGIN_PRECISION.div(
|
|
485
|
+
myMockUserAccount.maxMarginRatio = MARGIN_PRECISION.div(
|
|
486
|
+
new BN(2)
|
|
487
|
+
).toNumber(); // 2x max pls
|
|
490
488
|
|
|
491
489
|
const mockUser2: User = await makeMockUser(
|
|
492
490
|
myMockPerpMarkets,
|
|
@@ -498,9 +496,8 @@ describe('User Tests', () => {
|
|
|
498
496
|
iLev = mockUser2.getMaxLeverageForPerp(0, 'Initial').toNumber();
|
|
499
497
|
mLev = mockUser2.getMaxLeverageForPerp(0, 'Maintenance').toNumber();
|
|
500
498
|
console.log(iLev, mLev);
|
|
501
|
-
|
|
499
|
+
|
|
502
500
|
assert(iLev == 2000);
|
|
503
501
|
assert(mLev == 10000);
|
|
504
|
-
|
|
505
502
|
});
|
|
506
503
|
});
|