@drift-labs/sdk 2.30.0-beta.0 → 2.30.0

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.
Files changed (55) hide show
  1. package/lib/accounts/pollingTokenAccountSubscriber.d.ts +3 -3
  2. package/lib/accounts/pollingTokenAccountSubscriber.js +5 -2
  3. package/lib/accounts/types.d.ts +3 -3
  4. package/lib/constants/spotMarkets.js +10 -0
  5. package/lib/dlob/DLOB.d.ts +20 -1
  6. package/lib/dlob/DLOB.js +39 -0
  7. package/lib/driftClient.d.ts +51 -2
  8. package/lib/driftClient.js +162 -13
  9. package/lib/events/types.d.ts +3 -2
  10. package/lib/events/types.js +1 -0
  11. package/lib/examples/makeTradeExample.js +1 -1
  12. package/lib/idl/drift.json +279 -2
  13. package/lib/index.d.ts +1 -0
  14. package/lib/index.js +1 -0
  15. package/lib/jupiter/jupiterClient.d.ts +86 -0
  16. package/lib/jupiter/jupiterClient.js +109 -0
  17. package/lib/math/spotBalance.d.ts +41 -0
  18. package/lib/math/spotBalance.js +41 -0
  19. package/lib/token/index.d.ts +3 -2
  20. package/lib/token/index.js +9 -32
  21. package/lib/tokenFaucet.d.ts +3 -3
  22. package/lib/tokenFaucet.js +4 -9
  23. package/lib/tx/retryTxSender.js +3 -0
  24. package/lib/types.d.ts +29 -1
  25. package/lib/types.js +6 -1
  26. package/lib/wallet.d.ts +5 -3
  27. package/lib/wallet.js +19 -7
  28. package/package.json +2 -2
  29. package/src/accounts/pollingTokenAccountSubscriber.ts +8 -5
  30. package/src/accounts/types.ts +3 -3
  31. package/src/assert/assert.js +9 -0
  32. package/src/constants/spotMarkets.ts +11 -0
  33. package/src/dlob/DLOB.ts +75 -0
  34. package/src/driftClient.ts +288 -37
  35. package/src/events/types.ts +5 -1
  36. package/src/examples/makeTradeExample.ts +2 -4
  37. package/src/idl/drift.json +279 -2
  38. package/src/index.ts +1 -0
  39. package/src/jupiter/jupiterClient.ts +214 -0
  40. package/src/math/spotBalance.ts +41 -0
  41. package/src/token/index.js +38 -0
  42. package/src/token/index.ts +12 -36
  43. package/src/tokenFaucet.ts +15 -34
  44. package/src/tx/retryTxSender.ts +4 -0
  45. package/src/types.ts +32 -1
  46. package/src/util/computeUnits.js +27 -0
  47. package/src/util/promiseTimeout.js +14 -0
  48. package/src/util/tps.js +27 -0
  49. package/src/wallet.ts +34 -12
  50. package/tests/dlob/helpers.ts +9 -0
  51. package/tests/dlob/test.ts +218 -40
  52. package/dlob_read.ts +0 -155
  53. package/lib/util/getTokenAddress.d.ts +0 -2
  54. package/lib/util/getTokenAddress.js +0 -9
  55. package/src/util/getTokenAddress.ts +0 -18
@@ -1,10 +1,11 @@
1
1
  import * as anchor from '@coral-xyz/anchor';
2
2
  import { AnchorProvider, Idl, Program } from '@coral-xyz/anchor';
3
3
  import {
4
- AccountInfo,
5
- ASSOCIATED_TOKEN_PROGRAM_ID,
6
- Token,
7
4
  TOKEN_PROGRAM_ID,
5
+ getAccount,
6
+ Account,
7
+ createAssociatedTokenAccountInstruction,
8
+ getAssociatedTokenAddress,
8
9
  } from '@solana/spl-token';
9
10
  import {
10
11
  ConfirmOptions,
@@ -174,15 +175,12 @@ export class TokenFaucet {
174
175
  { userPubKey: userPublicKey }
175
176
  );
176
177
 
177
- const createAssociatedAccountIx =
178
- Token.createAssociatedTokenAccountInstruction(
179
- ASSOCIATED_TOKEN_PROGRAM_ID,
180
- TOKEN_PROGRAM_ID,
181
- state.mint,
182
- associateTokenPublicKey,
183
- userPublicKey,
184
- this.wallet.publicKey
185
- );
178
+ const createAssociatedAccountIx = createAssociatedTokenAccountInstruction(
179
+ this.wallet.publicKey,
180
+ associateTokenPublicKey,
181
+ userPublicKey,
182
+ state.mint
183
+ );
186
184
 
187
185
  const mintToIx = await this.mintToUserIx(associateTokenPublicKey, amount);
188
186
 
@@ -194,36 +192,19 @@ export class TokenFaucet {
194
192
  }): Promise<anchor.web3.PublicKey> {
195
193
  const state: any = await this.fetchState();
196
194
 
197
- return Token.getAssociatedTokenAddress(
198
- ASSOCIATED_TOKEN_PROGRAM_ID,
199
- TOKEN_PROGRAM_ID,
200
- state.mint,
201
- props.userPubKey
202
- );
195
+ return getAssociatedTokenAddress(state.mint, props.userPubKey);
203
196
  }
204
197
 
205
198
  public async getTokenAccountInfo(props: {
206
199
  userPubKey: PublicKey;
207
- }): Promise<AccountInfo> {
208
- const assosciatedKey = await this.getAssosciatedMockUSDMintAddress(props);
209
-
210
- const state: any = await this.fetchState();
211
-
212
- const token = new Token(
213
- this.connection,
214
- state.mint,
215
- TOKEN_PROGRAM_ID,
216
- // eslint-disable-next-line @typescript-eslint/ban-ts-comment
217
- // @ts-ignore
218
- this.provider.payer
219
- );
220
-
221
- return await token.getAccountInfo(assosciatedKey);
200
+ }): Promise<Account> {
201
+ const associatedKey = await this.getAssosciatedMockUSDMintAddress(props);
202
+ return await getAccount(this.connection, associatedKey);
222
203
  }
223
204
 
224
205
  public async subscribeToTokenAccount(props: {
225
206
  userPubKey: PublicKey;
226
- callback: (accountInfo: AccountInfo) => void;
207
+ callback: (accountInfo: Account) => void;
227
208
  }): Promise<boolean> {
228
209
  try {
229
210
  const tokenAccountKey = await this.getAssosciatedMockUSDMintAddress(
@@ -122,6 +122,10 @@ export class RetryTxSender implements TxSender {
122
122
  // @ts-ignore
123
123
  tx.sign((additionalSigners ?? []).concat(this.provider.wallet.payer));
124
124
 
125
+ if (opts === undefined) {
126
+ opts = this.provider.opts;
127
+ }
128
+
125
129
  return this.sendRawTransaction(tx.serialize(), opts);
126
130
  }
127
131
 
package/src/types.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { PublicKey, Transaction } from '@solana/web3.js';
1
+ import { PublicKey, Transaction, VersionedTransaction } from '@solana/web3.js';
2
2
  import { BN, ZERO } from '.';
3
3
 
4
4
  // # Utility Types / Enums / Constants
@@ -505,6 +505,18 @@ export type OrderActionRecord = {
505
505
  oraclePrice: BN;
506
506
  };
507
507
 
508
+ export type SwapRecord = {
509
+ ts: BN;
510
+ user: PublicKey;
511
+ amountOut: BN;
512
+ amountIn: BN;
513
+ outMarketIndex: number;
514
+ inMarketIndex: number;
515
+ outOraclePrice: BN;
516
+ inOraclePrice: BN;
517
+ fee: BN;
518
+ };
519
+
508
520
  export type StateAccount = {
509
521
  admin: PublicKey;
510
522
  exchangeStatus: number;
@@ -645,6 +657,10 @@ export type SpotMarketAccount = {
645
657
  nextFillRecordId: BN;
646
658
  spotFeePool: PoolBalance;
647
659
  totalSpotFee: BN;
660
+ totalSwapFee: BN;
661
+
662
+ flashLoanAmount: BN;
663
+ flashLoanInitialTokenAmount: BN;
648
664
 
649
665
  ordersEnabled: boolean;
650
666
  };
@@ -801,6 +817,7 @@ export type UserAccount = {
801
817
  totalWithdraws: BN;
802
818
  totalSocialLoss: BN;
803
819
  cumulativePerpFunding: BN;
820
+ cumulativeSpotFees: BN;
804
821
  liquidationMarginFreed: BN;
805
822
  lastActiveSlot: BN;
806
823
  isMarginTradingEnabled: boolean;
@@ -934,12 +951,26 @@ export type TxParams = {
934
951
  computeUnitsPrice?: number;
935
952
  };
936
953
 
954
+ export class SwapReduceOnly {
955
+ static readonly In = { in: {} };
956
+ static readonly Out = { out: {} };
957
+ }
958
+
937
959
  // # Misc Types
938
960
  export interface IWallet {
939
961
  signTransaction(tx: Transaction): Promise<Transaction>;
940
962
  signAllTransactions(txs: Transaction[]): Promise<Transaction[]>;
941
963
  publicKey: PublicKey;
942
964
  }
965
+ export interface IVersionedWallet {
966
+ signVersionedTransaction(
967
+ tx: VersionedTransaction
968
+ ): Promise<VersionedTransaction>;
969
+ signAllVersionedTransactions(
970
+ txs: VersionedTransaction[]
971
+ ): Promise<VersionedTransaction[]>;
972
+ publicKey: PublicKey;
973
+ }
943
974
 
944
975
  export type FeeStructure = {
945
976
  feeTiers: FeeTier[];
@@ -0,0 +1,27 @@
1
+ "use strict";
2
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
+ return new (P || (P = Promise))(function (resolve, reject) {
5
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
9
+ });
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ exports.findComputeUnitConsumption = void 0;
13
+ function findComputeUnitConsumption(programId, connection, txSignature, commitment = 'confirmed') {
14
+ return __awaiter(this, void 0, void 0, function* () {
15
+ const tx = yield connection.getTransaction(txSignature, { commitment });
16
+ const computeUnits = [];
17
+ const regex = new RegExp(`Program ${programId.toString()} consumed ([0-9]{0,6}) of ([0-9]{0,7}) compute units`);
18
+ tx.meta.logMessages.forEach((logMessage) => {
19
+ const match = logMessage.match(regex);
20
+ if (match && match[1]) {
21
+ computeUnits.push(match[1]);
22
+ }
23
+ });
24
+ return computeUnits;
25
+ });
26
+ }
27
+ exports.findComputeUnitConsumption = findComputeUnitConsumption;
@@ -0,0 +1,14 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.promiseTimeout = void 0;
4
+ function promiseTimeout(promise, timeoutMs) {
5
+ let timeoutId;
6
+ const timeoutPromise = new Promise((resolve) => {
7
+ timeoutId = setTimeout(() => resolve(null), timeoutMs);
8
+ });
9
+ return Promise.race([promise, timeoutPromise]).then((result) => {
10
+ clearTimeout(timeoutId);
11
+ return result;
12
+ });
13
+ }
14
+ exports.promiseTimeout = promiseTimeout;
@@ -0,0 +1,27 @@
1
+ "use strict";
2
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
+ return new (P || (P = Promise))(function (resolve, reject) {
5
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
9
+ });
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ exports.estimateTps = void 0;
13
+ function estimateTps(programId, connection, failed) {
14
+ return __awaiter(this, void 0, void 0, function* () {
15
+ let signatures = yield connection.getSignaturesForAddress(programId, undefined, 'finalized');
16
+ if (failed) {
17
+ signatures = signatures.filter((signature) => signature.err);
18
+ }
19
+ const numberOfSignatures = signatures.length;
20
+ if (numberOfSignatures === 0) {
21
+ return 0;
22
+ }
23
+ return (numberOfSignatures /
24
+ (signatures[0].blockTime - signatures[numberOfSignatures - 1].blockTime));
25
+ });
26
+ }
27
+ exports.estimateTps = estimateTps;
package/src/wallet.ts CHANGED
@@ -1,9 +1,14 @@
1
- import { Keypair, PublicKey, Transaction } from '@solana/web3.js';
2
- import { IWallet } from './types';
1
+ import {
2
+ Keypair,
3
+ PublicKey,
4
+ Transaction,
5
+ VersionedTransaction,
6
+ } from '@solana/web3.js';
7
+ import { IWallet, IVersionedWallet } from './types';
3
8
  import fs from 'fs';
4
9
  import bs58 from 'bs58';
5
10
 
6
- export class Wallet implements IWallet {
11
+ export class Wallet implements IWallet, IVersionedWallet {
7
12
  constructor(readonly payer: Keypair) {}
8
13
 
9
14
  async signTransaction(tx: Transaction): Promise<Transaction> {
@@ -11,6 +16,13 @@ export class Wallet implements IWallet {
11
16
  return tx;
12
17
  }
13
18
 
19
+ async signVersionedTransaction(
20
+ tx: VersionedTransaction
21
+ ): Promise<VersionedTransaction> {
22
+ tx.sign([this.payer]);
23
+ return tx;
24
+ }
25
+
14
26
  async signAllTransactions(txs: Transaction[]): Promise<Transaction[]> {
15
27
  return txs.map((t) => {
16
28
  t.partialSign(this.payer);
@@ -18,6 +30,15 @@ export class Wallet implements IWallet {
18
30
  });
19
31
  }
20
32
 
33
+ async signAllVersionedTransactions(
34
+ txs: VersionedTransaction[]
35
+ ): Promise<VersionedTransaction[]> {
36
+ return txs.map((t) => {
37
+ t.sign([this.payer]);
38
+ return t;
39
+ });
40
+ }
41
+
21
42
  get publicKey(): PublicKey {
22
43
  return this.payer.publicKey;
23
44
  }
@@ -27,17 +48,18 @@ export function loadKeypair(privateKey: string): Keypair {
27
48
  // try to load privateKey as a filepath
28
49
  let loadedKey: Uint8Array;
29
50
  if (fs.existsSync(privateKey)) {
30
- loadedKey = new Uint8Array(
31
- JSON.parse(fs.readFileSync(privateKey).toString())
51
+ privateKey = fs.readFileSync(privateKey).toString();
52
+ }
53
+
54
+ if (privateKey.includes('[') && privateKey.includes(']')) {
55
+ loadedKey = Uint8Array.from(JSON.parse(privateKey));
56
+ } else if (privateKey.includes(',')) {
57
+ loadedKey = Uint8Array.from(
58
+ privateKey.split(',').map((val) => Number(val))
32
59
  );
33
60
  } else {
34
- if (privateKey.includes(',')) {
35
- loadedKey = Uint8Array.from(
36
- privateKey.split(',').map((val) => Number(val))
37
- );
38
- } else {
39
- loadedKey = new Uint8Array(bs58.decode(privateKey));
40
- }
61
+ privateKey = privateKey.replace(/\s/g, '');
62
+ loadedKey = new Uint8Array(bs58.decode(privateKey));
41
63
  }
42
64
 
43
65
  return Keypair.fromSecretKey(Uint8Array.from(loadedKey));
@@ -309,6 +309,9 @@ export const mockSpotMarkets: Array<SpotMarketAccount> = [
309
309
  marketIndex: 0,
310
310
  },
311
311
  totalSpotFee: new BN(0),
312
+ totalSwapFee: new BN(0),
313
+ flashLoanAmount: new BN(0),
314
+ flashLoanInitialTokenAmount: new BN(0),
312
315
  oracleSource: OracleSource.PYTH,
313
316
  historicalOracleData: {
314
317
  lastOraclePrice: new BN(0),
@@ -384,6 +387,9 @@ export const mockSpotMarkets: Array<SpotMarketAccount> = [
384
387
  marketIndex: 0,
385
388
  },
386
389
  totalSpotFee: new BN(0),
390
+ totalSwapFee: new BN(0),
391
+ flashLoanAmount: new BN(0),
392
+ flashLoanInitialTokenAmount: new BN(0),
387
393
  oracleSource: OracleSource.PYTH,
388
394
  historicalOracleData: {
389
395
  lastOraclePrice: new BN(0),
@@ -459,6 +465,9 @@ export const mockSpotMarkets: Array<SpotMarketAccount> = [
459
465
  marketIndex: 0,
460
466
  },
461
467
  totalSpotFee: new BN(0),
468
+ totalSwapFee: new BN(0),
469
+ flashLoanAmount: new BN(0),
470
+ flashLoanInitialTokenAmount: new BN(0),
462
471
  oracleSource: OracleSource.PYTH,
463
472
  historicalOracleData: {
464
473
  lastOraclePrice: new BN(0),