@drift-labs/sdk 2.82.0-beta.9 → 2.83.0-beta.1

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 (71) hide show
  1. package/VERSION +1 -1
  2. package/lib/accounts/types.d.ts +0 -3
  3. package/lib/accounts/webSocketAccountSubscriber.js +1 -1
  4. package/lib/clock/clockSubscriber.d.ts +29 -0
  5. package/lib/clock/clockSubscriber.js +74 -0
  6. package/lib/constants/perpMarkets.js +10 -0
  7. package/lib/constants/spotMarkets.js +31 -0
  8. package/lib/dlob/DLOB.js +2 -2
  9. package/lib/dlob/orderBookLevels.js +1 -0
  10. package/lib/driftClient.d.ts +11 -14
  11. package/lib/driftClient.js +159 -261
  12. package/lib/driftClientConfig.d.ts +2 -0
  13. package/lib/idl/drift.json +1 -1
  14. package/lib/index.d.ts +2 -0
  15. package/lib/index.js +2 -0
  16. package/lib/jupiter/jupiterClient.d.ts +2 -1
  17. package/lib/jupiter/jupiterClient.js +10 -6
  18. package/lib/math/exchangeStatus.d.ts +2 -2
  19. package/lib/math/orders.d.ts +1 -1
  20. package/lib/math/orders.js +2 -2
  21. package/lib/tx/baseTxSender.d.ts +8 -6
  22. package/lib/tx/baseTxSender.js +6 -49
  23. package/lib/tx/fastSingleTxSender.d.ts +6 -6
  24. package/lib/tx/fastSingleTxSender.js +3 -31
  25. package/lib/tx/forwardOnlyTxSender.d.ts +4 -2
  26. package/lib/tx/forwardOnlyTxSender.js +2 -1
  27. package/lib/tx/retryTxSender.d.ts +4 -2
  28. package/lib/tx/retryTxSender.js +2 -1
  29. package/lib/tx/txHandler.d.ts +138 -0
  30. package/lib/tx/txHandler.js +396 -0
  31. package/lib/tx/txParamProcessor.d.ts +7 -11
  32. package/lib/tx/txParamProcessor.js +20 -22
  33. package/lib/tx/types.d.ts +3 -7
  34. package/lib/tx/whileValidTxSender.d.ts +7 -6
  35. package/lib/tx/whileValidTxSender.js +7 -28
  36. package/lib/types.d.ts +24 -4
  37. package/lib/types.js +10 -1
  38. package/lib/user.d.ts +1 -1
  39. package/lib/user.js +7 -7
  40. package/lib/util/chainClock.d.ts +17 -0
  41. package/lib/util/chainClock.js +29 -0
  42. package/package.json +3 -3
  43. package/src/accounts/types.ts +0 -4
  44. package/src/accounts/webSocketAccountSubscriber.ts +1 -1
  45. package/src/clock/clockSubscriber.ts +113 -0
  46. package/src/constants/perpMarkets.ts +10 -0
  47. package/src/constants/spotMarkets.ts +33 -0
  48. package/src/dlob/DLOB.ts +2 -2
  49. package/src/dlob/orderBookLevels.ts +2 -0
  50. package/src/driftClient.ts +251 -388
  51. package/src/driftClientConfig.ts +2 -0
  52. package/src/idl/drift.json +1 -1
  53. package/src/index.ts +2 -0
  54. package/src/jupiter/jupiterClient.ts +15 -6
  55. package/src/math/exchangeStatus.ts +2 -1
  56. package/src/math/orders.ts +3 -2
  57. package/src/tx/baseTxSender.ts +21 -75
  58. package/src/tx/fastSingleTxSender.ts +10 -55
  59. package/src/tx/forwardOnlyTxSender.ts +5 -1
  60. package/src/tx/retryTxSender.ts +5 -1
  61. package/src/tx/txHandler.ts +625 -0
  62. package/src/tx/txParamProcessor.ts +28 -36
  63. package/src/tx/types.ts +2 -18
  64. package/src/tx/whileValidTxSender.ts +24 -48
  65. package/src/types.ts +26 -2
  66. package/src/user.ts +10 -10
  67. package/src/util/chainClock.ts +41 -0
  68. package/tests/dlob/helpers.ts +3 -0
  69. package/lib/tx/utils.d.ts +0 -6
  70. package/lib/tx/utils.js +0 -43
  71. package/src/tx/utils.ts +0 -68
package/VERSION CHANGED
@@ -1 +1 @@
1
- 2.82.0-beta.9
1
+ 2.83.0-beta.1
@@ -29,9 +29,6 @@ export interface DriftClientAccountEvents {
29
29
  update: void;
30
30
  error: (e: Error) => void;
31
31
  }
32
- export interface DriftClientMetricsEvents {
33
- txSigned: void;
34
- }
35
32
  export interface DriftClientAccountSubscriber {
36
33
  eventEmitter: StrictEventEmitter<EventEmitter, DriftClientAccountEvents>;
37
34
  isSubscribed: boolean;
@@ -126,7 +126,7 @@ class WebSocketAccountSubscriber {
126
126
  }
127
127
  }
128
128
  unsubscribe(onResub = false) {
129
- if (!onResub) {
129
+ if (!onResub && this.resubOpts) {
130
130
  this.resubOpts.resubTimeoutMs = undefined;
131
131
  }
132
132
  this.isUnsubscribing = true;
@@ -0,0 +1,29 @@
1
+ /// <reference types="node" />
2
+ import { Commitment, Connection } from '@solana/web3.js';
3
+ import { EventEmitter } from 'events';
4
+ import StrictEventEmitter from 'strict-event-emitter-types/types/src';
5
+ type ClockSubscriberConfig = {
6
+ commitment: Commitment;
7
+ resubTimeoutMs?: number;
8
+ };
9
+ export interface ClockSubscriberEvent {
10
+ clockUpdate: (ts: number) => void;
11
+ }
12
+ export declare class ClockSubscriber {
13
+ private connection;
14
+ private latestSlot;
15
+ currentTs: number;
16
+ private subscriptionId;
17
+ commitment: Commitment;
18
+ eventEmitter: StrictEventEmitter<EventEmitter, ClockSubscriberEvent>;
19
+ private timeoutId?;
20
+ private resubTimeoutMs?;
21
+ private isUnsubscribing;
22
+ private receivingData;
23
+ constructor(connection: Connection, config?: ClockSubscriberConfig);
24
+ subscribe(): Promise<void>;
25
+ private setTimeout;
26
+ getUnixTs(): number;
27
+ unsubscribe(onResub?: boolean): Promise<void>;
28
+ }
29
+ export {};
@@ -0,0 +1,74 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.ClockSubscriber = void 0;
4
+ const web3_js_1 = require("@solana/web3.js");
5
+ const events_1 = require("events");
6
+ const __1 = require("..");
7
+ class ClockSubscriber {
8
+ constructor(connection, config) {
9
+ this.connection = connection;
10
+ this.isUnsubscribing = false;
11
+ this.receivingData = false;
12
+ this.eventEmitter = new events_1.EventEmitter();
13
+ this.resubTimeoutMs = config === null || config === void 0 ? void 0 : config.resubTimeoutMs;
14
+ this.commitment = (config === null || config === void 0 ? void 0 : config.commitment) || 'confirmed';
15
+ if (this.resubTimeoutMs < 1000) {
16
+ console.log('resubTimeoutMs should be at least 1000ms to avoid spamming resub');
17
+ }
18
+ }
19
+ async subscribe() {
20
+ if (this.subscriptionId != null) {
21
+ return;
22
+ }
23
+ this.subscriptionId = this.connection.onAccountChange(web3_js_1.SYSVAR_CLOCK_PUBKEY, (acctInfo, context) => {
24
+ if (!this.latestSlot || this.latestSlot < context.slot) {
25
+ if (this.resubTimeoutMs && !this.isUnsubscribing) {
26
+ this.receivingData = true;
27
+ clearTimeout(this.timeoutId);
28
+ this.setTimeout();
29
+ }
30
+ this.latestSlot = context.slot;
31
+ this.currentTs = new __1.BN(acctInfo.data.subarray(32, 39), undefined, 'le').toNumber();
32
+ this.eventEmitter.emit('clockUpdate', this.currentTs);
33
+ }
34
+ }, this.commitment);
35
+ if (this.resubTimeoutMs) {
36
+ this.receivingData = true;
37
+ this.setTimeout();
38
+ }
39
+ }
40
+ setTimeout() {
41
+ this.timeoutId = setTimeout(async () => {
42
+ if (this.isUnsubscribing) {
43
+ // If we are in the process of unsubscribing, do not attempt to resubscribe
44
+ return;
45
+ }
46
+ if (this.receivingData) {
47
+ console.log(`No new slot in ${this.resubTimeoutMs}ms, slot subscriber resubscribing`);
48
+ await this.unsubscribe(true);
49
+ this.receivingData = false;
50
+ await this.subscribe();
51
+ }
52
+ }, this.resubTimeoutMs);
53
+ }
54
+ getUnixTs() {
55
+ return this.currentTs;
56
+ }
57
+ async unsubscribe(onResub = false) {
58
+ if (!onResub) {
59
+ this.resubTimeoutMs = undefined;
60
+ }
61
+ this.isUnsubscribing = true;
62
+ clearTimeout(this.timeoutId);
63
+ this.timeoutId = undefined;
64
+ if (this.subscriptionId != null) {
65
+ await this.connection.removeAccountChangeListener(this.subscriptionId);
66
+ this.subscriptionId = undefined;
67
+ this.isUnsubscribing = false;
68
+ }
69
+ else {
70
+ this.isUnsubscribing = false;
71
+ }
72
+ }
73
+ }
74
+ exports.ClockSubscriber = ClockSubscriber;
@@ -556,6 +556,16 @@ exports.MainnetPerpMarkets = [
556
556
  launchTs: 1712593532000,
557
557
  oracleSource: __1.OracleSource.SWITCHBOARD,
558
558
  },
559
+ {
560
+ fullName: 'Drift',
561
+ category: ['DEX', 'Solana'],
562
+ symbol: 'DRIFT-PERP',
563
+ baseAssetSymbol: 'DRIFT',
564
+ marketIndex: 30,
565
+ oracle: new web3_js_1.PublicKey('PeNpQeGEm9UEFJ6MBCMauY4WW4h3YxoESPWbsqVKucE'),
566
+ launchTs: 1716595200000,
567
+ oracleSource: __1.OracleSource.SWITCHBOARD,
568
+ },
559
569
  ];
560
570
  exports.PerpMarkets = {
561
571
  devnet: exports.DevnetPerpMarkets,
@@ -197,6 +197,37 @@ exports.MainnetSpotMarkets = [
197
197
  phoenixMarket: new web3_js_1.PublicKey('AbJCZ9TAJiby5AY3cHcXS2gUdENC6mtsm6m7XpC2ZMvE'),
198
198
  launchTs: 1712593532000,
199
199
  },
200
+ {
201
+ symbol: 'DRIFT',
202
+ marketIndex: 15,
203
+ oracle: new web3_js_1.PublicKey('PeNpQeGEm9UEFJ6MBCMauY4WW4h3YxoESPWbsqVKucE'),
204
+ oracleSource: __1.OracleSource.SWITCHBOARD,
205
+ mint: new web3_js_1.PublicKey('DriFtupJYLTosbwoN8koMbEYSx54aFAVLddWsbksjwg7'),
206
+ precision: new __1.BN(10).pow(numericConstants_1.SIX),
207
+ precisionExp: numericConstants_1.SIX,
208
+ phoenixMarket: new web3_js_1.PublicKey('8BV6rrWsUabnTDA3dE6A69oUDJAj3hMhtBHTJyXB7czp'),
209
+ launchTs: 1715860800000,
210
+ },
211
+ {
212
+ symbol: 'INF',
213
+ marketIndex: 16,
214
+ oracle: new web3_js_1.PublicKey('6AQHz9mpGNjyVafcWdqzzgsJq14Cs8gG6MiQKmdAgCuP'),
215
+ oracleSource: __1.OracleSource.SWITCHBOARD,
216
+ mint: new web3_js_1.PublicKey('5oVNBeEEQvYi1cX3ir8Dx5n1P7pdxydbGF2X4TxVusJm'),
217
+ precision: new __1.BN(10).pow(numericConstants_1.NINE),
218
+ precisionExp: numericConstants_1.NINE,
219
+ launchTs: 1716595200000,
220
+ },
221
+ {
222
+ symbol: 'dSOL',
223
+ marketIndex: 17,
224
+ oracle: new web3_js_1.PublicKey('HJ9K9AamqVMp86j3uQgpA1tdJNRAwfVuL75FD9P3QBrn'),
225
+ oracleSource: __1.OracleSource.SWITCHBOARD,
226
+ mint: new web3_js_1.PublicKey('Dso1bDeDjCQxTrWHqUUi63oBvV7Mdm6WaobLbQ7gnPQ'),
227
+ precision: new __1.BN(10).pow(numericConstants_1.NINE),
228
+ precisionExp: numericConstants_1.NINE,
229
+ launchTs: 1716595200000,
230
+ },
200
231
  ];
201
232
  exports.SpotMarkets = {
202
233
  devnet: exports.DevnetSpotMarkets,
package/lib/dlob/DLOB.js CHANGED
@@ -528,7 +528,7 @@ class DLOB {
528
528
  ];
529
529
  for (const bidGenerator of bidGenerators) {
530
530
  for (const bid of bidGenerator) {
531
- if ((0, __1.isOrderExpired)(bid.order, ts, true)) {
531
+ if ((0, __1.isOrderExpired)(bid.order, ts, true, 25)) {
532
532
  nodesToFill.push({
533
533
  node: bid,
534
534
  makerNodes: [],
@@ -538,7 +538,7 @@ class DLOB {
538
538
  }
539
539
  for (const askGenerator of askGenerators) {
540
540
  for (const ask of askGenerator) {
541
- if ((0, __1.isOrderExpired)(ask.order, ts, true)) {
541
+ if ((0, __1.isOrderExpired)(ask.order, ts, true, 25)) {
542
542
  nodesToFill.push({
543
543
  node: ask,
544
544
  makerNodes: [],
@@ -246,6 +246,7 @@ function groupL2Levels(levels, grouping, direction, depth) {
246
246
  currentLevel.sources[source] = size;
247
247
  }
248
248
  }
249
+ groupedLevels[groupedLevels.length - 1] = currentLevel;
249
250
  }
250
251
  else {
251
252
  const groupedLevel = {
@@ -3,11 +3,12 @@
3
3
  import { AnchorProvider, BN, Program, ProgramAccount } from '@coral-xyz/anchor';
4
4
  import { StateAccount, IWallet, PositionDirection, UserAccount, PerpMarketAccount, OrderParams, Order, SpotMarketAccount, SpotPosition, MakerInfo, TakerInfo, OptionalOrderParams, ReferrerInfo, MarketType, TxParams, SerumV3FulfillmentConfigAccount, ReferrerNameAccount, OrderTriggerCondition, PerpMarketExtendedInfo, UserStatsAccount, PhoenixV1FulfillmentConfigAccount, ModifyOrderPolicy, SwapReduceOnly } from './types';
5
5
  import * as anchor from '@coral-xyz/anchor';
6
- import { Connection, PublicKey, TransactionSignature, ConfirmOptions, Transaction, TransactionInstruction, AccountMeta, Signer, AddressLookupTableAccount, TransactionVersion, VersionedTransaction } from '@solana/web3.js';
6
+ import { Connection, PublicKey, TransactionSignature, ConfirmOptions, Transaction, TransactionInstruction, AccountMeta, Signer, AddressLookupTableAccount, TransactionVersion, VersionedTransaction, BlockhashWithExpiryBlockHeight } from '@solana/web3.js';
7
7
  import { TokenFaucet } from './tokenFaucet';
8
8
  import { EventEmitter } from 'events';
9
9
  import StrictEventEmitter from 'strict-event-emitter-types';
10
- import { DriftClientAccountSubscriber, DriftClientAccountEvents, DataAndSlot, DriftClientMetricsEvents } from './accounts/types';
10
+ import { DriftClientAccountSubscriber, DriftClientAccountEvents, DataAndSlot } from './accounts/types';
11
+ import { DriftClientMetricsEvents } from './types';
11
12
  import { TxSender, TxSigAndSlot } from './tx/types';
12
13
  import { OraclePriceData } from './oracles/types';
13
14
  import { DriftClientConfig } from './driftClientConfig';
@@ -16,6 +17,7 @@ import { UserSubscriptionConfig } from './userConfig';
16
17
  import { UserStats } from './userStats';
17
18
  import { JupiterClient, QuoteResponse, Route, SwapMode } from './jupiter/jupiterClient';
18
19
  import { UserStatsSubscriptionConfig } from './userStatsConfig';
20
+ import { TxHandler } from './tx/txHandler';
19
21
  type RemainingAccountParams = {
20
22
  userAccounts: UserAccount[];
21
23
  writablePerpMarketIndexes?: number[];
@@ -57,6 +59,7 @@ export declare class DriftClient {
57
59
  txVersion: TransactionVersion;
58
60
  txParams: TxParams;
59
61
  enableMetricsEvents?: boolean;
62
+ txHandler: TxHandler;
60
63
  get isSubscribed(): boolean;
61
64
  set isSubscribed(val: boolean);
62
65
  constructor(config: DriftClientConfig);
@@ -112,7 +115,6 @@ export declare class DriftClient {
112
115
  * Adds and subscribes to users based on params set by the constructor or by updateWallet.
113
116
  */
114
117
  addAndSubscribeToUsers(): Promise<boolean>;
115
- private getProcessedTransactionParams;
116
118
  initializeUserAccount(subAccountId?: number, name?: string, referrerInfo?: ReferrerInfo, txParams?: TxParams): Promise<[TransactionSignature, PublicKey]>;
117
119
  getInitializeUserInstructions(subAccountId?: number, name?: string, referrerInfo?: ReferrerInfo): Promise<[PublicKey, TransactionInstruction]>;
118
120
  getInitializeUserStatsIx(): Promise<TransactionInstruction>;
@@ -289,7 +291,7 @@ export declare class DriftClient {
289
291
  * @deprecated use {@link placePerpOrder} or {@link placeAndTakePerpOrder} instead
290
292
  */
291
293
  openPosition(direction: PositionDirection, amount: BN, marketIndex: number, limitPrice?: BN, subAccountId?: number): Promise<TransactionSignature>;
292
- sendSignedTx(tx: Transaction): Promise<TransactionSignature>;
294
+ sendSignedTx(tx: Transaction, opts?: ConfirmOptions): Promise<TransactionSignature>;
293
295
  /**
294
296
  * Sends a market order and returns a signed tx which can fill the order against the vamm, which the caller can use to fill their own order if required.
295
297
  * @param orderParams
@@ -680,15 +682,10 @@ export declare class DriftClient {
680
682
  private handleSignedTransaction;
681
683
  private isVersionedTransaction;
682
684
  sendTransaction(tx: Transaction | VersionedTransaction, additionalSigners?: Array<Signer>, opts?: ConfirmOptions, preSigned?: boolean): Promise<TxSigAndSlot>;
683
- /**
684
- *
685
- * @param instructions
686
- * @param txParams
687
- * @param txVersion
688
- * @param lookupTables
689
- * @param forceVersionedTransaction Return a VersionedTransaction instance even if the version of the transaction is Legacy
690
- * @returns
691
- */
692
- buildTransaction(instructions: TransactionInstruction | TransactionInstruction[], txParams?: TxParams, txVersion?: TransactionVersion, lookupTables?: AddressLookupTableAccount[], forceVersionedTransaction?: boolean): Promise<Transaction | VersionedTransaction>;
685
+ buildTransaction(instructions: TransactionInstruction | TransactionInstruction[], txParams?: TxParams, txVersion?: TransactionVersion, lookupTables?: AddressLookupTableAccount[], forceVersionedTransaction?: boolean, recentBlockHash?: BlockhashWithExpiryBlockHeight): Promise<Transaction | VersionedTransaction>;
686
+ buildBulkTransactions(instructions: (TransactionInstruction | TransactionInstruction[])[], txParams?: TxParams, txVersion?: TransactionVersion, lookupTables?: AddressLookupTableAccount[], forceVersionedTransaction?: boolean): Promise<(Transaction | VersionedTransaction)[]>;
687
+ buildAndSignBulkTransactions(instructions: (TransactionInstruction | TransactionInstruction[])[], keys: string[], txParams?: TxParams, txVersion?: TransactionVersion, lookupTables?: AddressLookupTableAccount[], forceVersionedTransaction?: boolean): Promise<{
688
+ [key: string]: anchor.web3.Transaction | anchor.web3.VersionedTransaction;
689
+ }>;
693
690
  }
694
691
  export {};