@nktkas/hyperliquid 0.23.1 → 0.24.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 (165) hide show
  1. package/CONTRIBUTING.md +3 -2
  2. package/README.md +178 -194
  3. package/esm/mod.d.ts +2 -1
  4. package/esm/mod.d.ts.map +1 -1
  5. package/esm/src/base.d.ts +0 -5
  6. package/esm/src/base.d.ts.map +1 -1
  7. package/esm/src/clients/exchange.d.ts +485 -392
  8. package/esm/src/clients/exchange.d.ts.map +1 -1
  9. package/esm/src/clients/exchange.js +517 -912
  10. package/esm/src/clients/info.d.ts +249 -203
  11. package/esm/src/clients/info.d.ts.map +1 -1
  12. package/esm/src/clients/info.js +258 -368
  13. package/esm/src/clients/multiSign.d.ts +14 -1184
  14. package/esm/src/clients/multiSign.d.ts.map +1 -1
  15. package/esm/src/clients/multiSign.js +37 -2004
  16. package/esm/src/clients/subscription.d.ts +101 -99
  17. package/esm/src/clients/subscription.d.ts.map +1 -1
  18. package/esm/src/clients/subscription.js +107 -152
  19. package/esm/src/signing/_signTypedData/ethers.d.ts +16 -4
  20. package/esm/src/signing/_signTypedData/ethers.d.ts.map +1 -1
  21. package/esm/src/signing/_signTypedData/ethers.js +1 -1
  22. package/esm/src/signing/_signTypedData/mod.d.ts +12 -12
  23. package/esm/src/signing/_signTypedData/mod.d.ts.map +1 -1
  24. package/esm/src/signing/_signTypedData/mod.js +52 -24
  25. package/esm/src/signing/_signTypedData/private_key.d.ts +6 -5
  26. package/esm/src/signing/_signTypedData/private_key.d.ts.map +1 -1
  27. package/esm/src/signing/_signTypedData/private_key.js +40 -19
  28. package/esm/src/signing/_signTypedData/viem.d.ts +27 -6
  29. package/esm/src/signing/_signTypedData/viem.d.ts.map +1 -1
  30. package/esm/src/signing/_signTypedData/viem.js +1 -1
  31. package/esm/src/signing/_sorter.d.ts +18 -19
  32. package/esm/src/signing/_sorter.d.ts.map +1 -1
  33. package/esm/src/signing/_sorter.js +57 -59
  34. package/esm/src/signing/mod.d.ts +179 -129
  35. package/esm/src/signing/mod.d.ts.map +1 -1
  36. package/esm/src/signing/mod.js +184 -132
  37. package/esm/src/transports/base.d.ts +2 -1
  38. package/esm/src/transports/base.d.ts.map +1 -1
  39. package/esm/src/transports/http/http_transport.d.ts +3 -2
  40. package/esm/src/transports/http/http_transport.d.ts.map +1 -1
  41. package/esm/src/transports/http/http_transport.js +4 -4
  42. package/esm/src/transports/websocket/_hyperliquid_event_target.d.ts +14 -6
  43. package/esm/src/transports/websocket/_hyperliquid_event_target.d.ts.map +1 -1
  44. package/esm/src/transports/websocket/_hyperliquid_event_target.js +1 -2
  45. package/esm/src/transports/websocket/_reconnecting_websocket.d.ts +2 -1
  46. package/esm/src/transports/websocket/_reconnecting_websocket.d.ts.map +1 -1
  47. package/esm/src/transports/websocket/_reconnecting_websocket.js +1 -0
  48. package/esm/src/transports/websocket/_websocket_async_request.d.ts.map +1 -1
  49. package/esm/src/transports/websocket/_websocket_async_request.js +17 -21
  50. package/esm/src/transports/websocket/websocket_transport.d.ts +4 -4
  51. package/esm/src/transports/websocket/websocket_transport.d.ts.map +1 -1
  52. package/esm/src/transports/websocket/websocket_transport.js +6 -6
  53. package/esm/src/types/exchange/requests.d.ts +547 -306
  54. package/esm/src/types/exchange/requests.d.ts.map +1 -1
  55. package/esm/src/types/exchange/responses.d.ts +105 -25
  56. package/esm/src/types/exchange/responses.d.ts.map +1 -1
  57. package/esm/src/types/explorer/requests.d.ts +3 -3
  58. package/esm/src/types/explorer/requests.d.ts.map +1 -1
  59. package/esm/src/types/explorer/responses.d.ts +1 -1
  60. package/esm/src/types/explorer/responses.d.ts.map +1 -1
  61. package/esm/src/types/info/accounts.d.ts +405 -98
  62. package/esm/src/types/info/accounts.d.ts.map +1 -1
  63. package/esm/src/types/info/assets.d.ts +131 -35
  64. package/esm/src/types/info/assets.d.ts.map +1 -1
  65. package/esm/src/types/info/markets.d.ts +29 -8
  66. package/esm/src/types/info/markets.d.ts.map +1 -1
  67. package/esm/src/types/info/orders.d.ts +64 -17
  68. package/esm/src/types/info/orders.d.ts.map +1 -1
  69. package/esm/src/types/info/requests.d.ts +126 -51
  70. package/esm/src/types/info/requests.d.ts.map +1 -1
  71. package/esm/src/types/info/validators.d.ts +44 -14
  72. package/esm/src/types/info/validators.d.ts.map +1 -1
  73. package/esm/src/types/info/vaults.d.ts +25 -10
  74. package/esm/src/types/info/vaults.d.ts.map +1 -1
  75. package/esm/src/types/mod.d.ts +1 -1
  76. package/esm/src/types/mod.d.ts.map +1 -1
  77. package/esm/src/types/subscriptions/requests.d.ts +21 -66
  78. package/esm/src/types/subscriptions/requests.d.ts.map +1 -1
  79. package/esm/src/types/subscriptions/responses.d.ts +46 -55
  80. package/esm/src/types/subscriptions/responses.d.ts.map +1 -1
  81. package/package.json +2 -3
  82. package/script/mod.d.ts +2 -1
  83. package/script/mod.d.ts.map +1 -1
  84. package/script/src/base.d.ts +0 -5
  85. package/script/src/base.d.ts.map +1 -1
  86. package/script/src/clients/exchange.d.ts +485 -392
  87. package/script/src/clients/exchange.d.ts.map +1 -1
  88. package/script/src/clients/exchange.js +516 -911
  89. package/script/src/clients/info.d.ts +249 -203
  90. package/script/src/clients/info.d.ts.map +1 -1
  91. package/script/src/clients/info.js +258 -368
  92. package/script/src/clients/multiSign.d.ts +14 -1184
  93. package/script/src/clients/multiSign.d.ts.map +1 -1
  94. package/script/src/clients/multiSign.js +38 -2005
  95. package/script/src/clients/subscription.d.ts +101 -99
  96. package/script/src/clients/subscription.d.ts.map +1 -1
  97. package/script/src/clients/subscription.js +107 -152
  98. package/script/src/signing/_signTypedData/ethers.d.ts +16 -4
  99. package/script/src/signing/_signTypedData/ethers.d.ts.map +1 -1
  100. package/script/src/signing/_signTypedData/ethers.js +2 -2
  101. package/script/src/signing/_signTypedData/mod.d.ts +12 -12
  102. package/script/src/signing/_signTypedData/mod.d.ts.map +1 -1
  103. package/script/src/signing/_signTypedData/mod.js +51 -26
  104. package/script/src/signing/_signTypedData/private_key.d.ts +6 -5
  105. package/script/src/signing/_signTypedData/private_key.d.ts.map +1 -1
  106. package/script/src/signing/_signTypedData/private_key.js +40 -18
  107. package/script/src/signing/_signTypedData/viem.d.ts +27 -6
  108. package/script/src/signing/_signTypedData/viem.d.ts.map +1 -1
  109. package/script/src/signing/_signTypedData/viem.js +2 -2
  110. package/script/src/signing/_sorter.d.ts +18 -19
  111. package/script/src/signing/_sorter.d.ts.map +1 -1
  112. package/script/src/signing/_sorter.js +57 -59
  113. package/script/src/signing/mod.d.ts +179 -129
  114. package/script/src/signing/mod.d.ts.map +1 -1
  115. package/script/src/signing/mod.js +187 -150
  116. package/script/src/transports/base.d.ts +2 -1
  117. package/script/src/transports/base.d.ts.map +1 -1
  118. package/script/src/transports/http/http_transport.d.ts +3 -2
  119. package/script/src/transports/http/http_transport.d.ts.map +1 -1
  120. package/script/src/transports/http/http_transport.js +4 -4
  121. package/script/src/transports/websocket/_hyperliquid_event_target.d.ts +14 -6
  122. package/script/src/transports/websocket/_hyperliquid_event_target.d.ts.map +1 -1
  123. package/script/src/transports/websocket/_hyperliquid_event_target.js +1 -2
  124. package/script/src/transports/websocket/_reconnecting_websocket.d.ts +2 -1
  125. package/script/src/transports/websocket/_reconnecting_websocket.d.ts.map +1 -1
  126. package/script/src/transports/websocket/_reconnecting_websocket.js +1 -0
  127. package/script/src/transports/websocket/_websocket_async_request.d.ts.map +1 -1
  128. package/script/src/transports/websocket/_websocket_async_request.js +17 -21
  129. package/script/src/transports/websocket/websocket_transport.d.ts +4 -4
  130. package/script/src/transports/websocket/websocket_transport.d.ts.map +1 -1
  131. package/script/src/transports/websocket/websocket_transport.js +6 -6
  132. package/script/src/types/exchange/requests.d.ts +547 -306
  133. package/script/src/types/exchange/requests.d.ts.map +1 -1
  134. package/script/src/types/exchange/responses.d.ts +105 -25
  135. package/script/src/types/exchange/responses.d.ts.map +1 -1
  136. package/script/src/types/explorer/requests.d.ts +3 -3
  137. package/script/src/types/explorer/requests.d.ts.map +1 -1
  138. package/script/src/types/explorer/responses.d.ts +1 -1
  139. package/script/src/types/explorer/responses.d.ts.map +1 -1
  140. package/script/src/types/info/accounts.d.ts +405 -98
  141. package/script/src/types/info/accounts.d.ts.map +1 -1
  142. package/script/src/types/info/assets.d.ts +131 -35
  143. package/script/src/types/info/assets.d.ts.map +1 -1
  144. package/script/src/types/info/markets.d.ts +29 -8
  145. package/script/src/types/info/markets.d.ts.map +1 -1
  146. package/script/src/types/info/orders.d.ts +64 -17
  147. package/script/src/types/info/orders.d.ts.map +1 -1
  148. package/script/src/types/info/requests.d.ts +126 -51
  149. package/script/src/types/info/requests.d.ts.map +1 -1
  150. package/script/src/types/info/validators.d.ts +44 -14
  151. package/script/src/types/info/validators.d.ts.map +1 -1
  152. package/script/src/types/info/vaults.d.ts +25 -10
  153. package/script/src/types/info/vaults.d.ts.map +1 -1
  154. package/script/src/types/mod.d.ts +1 -1
  155. package/script/src/types/mod.d.ts.map +1 -1
  156. package/script/src/types/subscriptions/requests.d.ts +21 -66
  157. package/script/src/types/subscriptions/requests.d.ts.map +1 -1
  158. package/script/src/types/subscriptions/responses.d.ts +46 -55
  159. package/script/src/types/subscriptions/responses.d.ts.map +1 -1
  160. package/esm/src/signing/_signTypedData/window.d.ts +0 -29
  161. package/esm/src/signing/_signTypedData/window.d.ts.map +0 -1
  162. package/esm/src/signing/_signTypedData/window.js +0 -30
  163. package/script/src/signing/_signTypedData/window.d.ts +0 -29
  164. package/script/src/signing/_signTypedData/window.d.ts.map +0 -1
  165. package/script/src/signing/_signTypedData/window.js +0 -34
@@ -9,7 +9,7 @@ exports.actionSorter = {
9
9
  signatureChainId: action.signatureChainId,
10
10
  hyperliquidChain: action.hyperliquidChain,
11
11
  agentAddress: action.agentAddress.toLowerCase(),
12
- agentName: action.agentName ?? "",
12
+ agentName: action.agentName,
13
13
  nonce: action.nonce,
14
14
  };
15
15
  },
@@ -94,7 +94,10 @@ exports.actionSorter = {
94
94
  type: action.type,
95
95
  signatureChainId: action.signatureChainId,
96
96
  hyperliquidChain: action.hyperliquidChain,
97
- signers: action.signers, // key order is not important
97
+ signers: typeof action.signers === "string" ? action.signers : JSON.stringify(action.signers === null ? action.signers : {
98
+ authorizedUsers: action.signers.authorizedUsers,
99
+ threshold: action.signers.threshold,
100
+ }),
98
101
  nonce: action.nonce,
99
102
  };
100
103
  },
@@ -132,13 +135,13 @@ exports.actionSorter = {
132
135
  return {
133
136
  type: action.type,
134
137
  changeProfile: {
135
- node_ip: action.changeProfile.node_ip ?? null,
136
- name: action.changeProfile.name ?? null,
137
- description: action.changeProfile.description ?? null,
138
+ node_ip: action.changeProfile.node_ip,
139
+ name: action.changeProfile.name,
140
+ description: action.changeProfile.description,
138
141
  unjailed: action.changeProfile.unjailed,
139
- disable_delegations: action.changeProfile.disable_delegations ?? null,
140
- commission_bps: action.changeProfile.commission_bps ?? null,
141
- signer: action.changeProfile.signer?.toLowerCase() ?? null,
142
+ disable_delegations: action.changeProfile.disable_delegations,
143
+ commission_bps: action.changeProfile.commission_bps,
144
+ signer: action.changeProfile.signer?.toLowerCase(),
142
145
  },
143
146
  };
144
147
  }
@@ -161,7 +164,7 @@ exports.actionSorter = {
161
164
  },
162
165
  };
163
166
  }
164
- else { // "unregister" in action
167
+ else {
165
168
  return {
166
169
  type: action.type,
167
170
  unregister: action.unregister,
@@ -225,10 +228,17 @@ exports.actionSorter = {
225
228
  payload: {
226
229
  multiSigUser: action.payload.multiSigUser.toLowerCase(),
227
230
  outerSigner: action.payload.outerSigner.toLowerCase(),
228
- action: structuredClone(action.payload.action),
231
+ action: exports.actionSorter[action.payload.action.type](
232
+ // @ts-ignore - TypeScript cannot infer the type correctly
233
+ action.payload.action),
229
234
  },
230
235
  };
231
236
  },
237
+ noop: (action) => {
238
+ return {
239
+ type: action.type,
240
+ };
241
+ },
232
242
  order: (action) => {
233
243
  const sortedAction = {
234
244
  type: action.type,
@@ -275,7 +285,7 @@ exports.actionSorter = {
275
285
  return {
276
286
  type: action.type,
277
287
  registerAsset: {
278
- maxGas: action.registerAsset.maxGas ?? null,
288
+ maxGas: action.registerAsset.maxGas,
279
289
  assetRequest: {
280
290
  coin: action.registerAsset.assetRequest.coin,
281
291
  szDecimals: action.registerAsset.assetRequest.szDecimals,
@@ -288,9 +298,9 @@ exports.actionSorter = {
288
298
  ? {
289
299
  fullName: action.registerAsset.schema.fullName,
290
300
  collateralToken: action.registerAsset.schema.collateralToken,
291
- oracleUpdater: action.registerAsset.schema.oracleUpdater?.toLowerCase() ?? null,
301
+ oracleUpdater: action.registerAsset.schema.oracleUpdater?.toLowerCase(),
292
302
  }
293
- : null,
303
+ : action.registerAsset.schema,
294
304
  },
295
305
  };
296
306
  }
@@ -300,34 +310,11 @@ exports.actionSorter = {
300
310
  setOracle: {
301
311
  dex: action.setOracle.dex,
302
312
  oraclePxs: action.setOracle.oraclePxs.map((el) => [...el]),
303
- markPxs: action.setOracle.markPxs.map((el) => [...el]),
313
+ markPxs: action.setOracle.markPxs.map((el) => el.map((el2) => [...el2])),
304
314
  },
305
315
  };
306
316
  }
307
317
  },
308
- PerpDexClassTransfer: (action) => {
309
- return {
310
- type: action.type,
311
- signatureChainId: action.signatureChainId,
312
- hyperliquidChain: action.hyperliquidChain,
313
- dex: action.dex,
314
- token: action.token,
315
- amount: action.amount,
316
- toPerp: action.toPerp,
317
- nonce: action.nonce,
318
- };
319
- },
320
- PerpDexTransfer: (action) => {
321
- return {
322
- type: action.type,
323
- signatureChainId: action.signatureChainId,
324
- hyperliquidChain: action.hyperliquidChain,
325
- sourceDex: action.sourceDex,
326
- destinationDex: action.destinationDex,
327
- amount: action.amount,
328
- nonce: action.nonce,
329
- };
330
- },
331
318
  registerReferrer: (action) => {
332
319
  return {
333
320
  type: action.type,
@@ -349,6 +336,20 @@ exports.actionSorter = {
349
336
  delete sortedAction.time;
350
337
  return sortedAction;
351
338
  },
339
+ sendAsset: (action) => {
340
+ return {
341
+ type: action.type,
342
+ signatureChainId: action.signatureChainId,
343
+ hyperliquidChain: action.hyperliquidChain,
344
+ destination: action.destination.toLowerCase(),
345
+ sourceDex: action.sourceDex,
346
+ destinationDex: action.destinationDex,
347
+ token: action.token,
348
+ amount: action.amount,
349
+ fromSubAccount: action.fromSubAccount.toLowerCase(),
350
+ nonce: action.nonce,
351
+ };
352
+ },
352
353
  setDisplayName: (action) => {
353
354
  return {
354
355
  type: action.type,
@@ -371,9 +372,8 @@ exports.actionSorter = {
371
372
  noHyperliquidity: action.genesis.noHyperliquidity,
372
373
  },
373
374
  };
374
- if (sortedAction.genesis.noHyperliquidity === undefined) {
375
+ if (sortedAction.genesis.noHyperliquidity === undefined)
375
376
  delete sortedAction.genesis.noHyperliquidity;
376
- }
377
377
  return sortedAction;
378
378
  }
379
379
  else if ("registerHyperliquidity" in action) {
@@ -413,9 +413,8 @@ exports.actionSorter = {
413
413
  fullName: action.registerToken2.fullName,
414
414
  },
415
415
  };
416
- if (sortedAction.registerToken2.fullName === undefined) {
416
+ if (sortedAction.registerToken2.fullName === undefined)
417
417
  delete sortedAction.registerToken2.fullName;
418
- }
419
418
  return sortedAction;
420
419
  }
421
420
  else if ("setDeployerTradingFeeShare" in action) {
@@ -427,7 +426,7 @@ exports.actionSorter = {
427
426
  },
428
427
  };
429
428
  }
430
- else { // "userGenesis" in action
429
+ else {
431
430
  const sortedAction = {
432
431
  type: action.type,
433
432
  userGenesis: {
@@ -437,9 +436,8 @@ exports.actionSorter = {
437
436
  blacklistUsers: action.userGenesis.blacklistUsers?.map((el) => [...el]),
438
437
  },
439
438
  };
440
- if (sortedAction.userGenesis.blacklistUsers === undefined) {
439
+ if (sortedAction.userGenesis.blacklistUsers === undefined)
441
440
  delete sortedAction.userGenesis.blacklistUsers;
442
- }
443
441
  return sortedAction;
444
442
  }
445
443
  },
@@ -462,6 +460,13 @@ exports.actionSorter = {
462
460
  },
463
461
  };
464
462
  },
463
+ subAccountModify: (action) => {
464
+ return {
465
+ type: action.type,
466
+ subAccountUser: action.subAccountUser.toLowerCase(),
467
+ name: action.name,
468
+ };
469
+ },
465
470
  subAccountSpotTransfer: (action) => {
466
471
  return {
467
472
  type: action.type,
@@ -627,29 +632,22 @@ exports.userSignedActionEip712Types = {
627
632
  { name: "nonce", type: "uint64" },
628
633
  ],
629
634
  },
630
- PerpDexClassTransfer: {
631
- "HyperliquidTransaction:PerpDexClassTransfer": [
635
+ multiSig: {
636
+ "HyperliquidTransaction:SendMultiSig": [
632
637
  { name: "hyperliquidChain", type: "string" },
633
- { name: "dex", type: "string" },
634
- { name: "token", type: "string" },
635
- { name: "amount", type: "string" },
636
- { name: "toPerp", type: "bool" },
638
+ { name: "multiSigActionHash", type: "bytes32" },
637
639
  { name: "nonce", type: "uint64" },
638
640
  ],
639
641
  },
640
- PerpDexTransfer: {
641
- "HyperliquidTransaction:PerpDexTransfer": [
642
+ sendAsset: {
643
+ "HyperliquidTransaction:SendAsset": [
642
644
  { name: "hyperliquidChain", type: "string" },
645
+ { name: "destination", type: "string" },
643
646
  { name: "sourceDex", type: "string" },
644
647
  { name: "destinationDex", type: "string" },
648
+ { name: "token", type: "string" },
645
649
  { name: "amount", type: "string" },
646
- { name: "nonce", type: "uint64" },
647
- ],
648
- },
649
- multiSig: {
650
- "HyperliquidTransaction:SendMultiSig": [
651
- { name: "hyperliquidChain", type: "string" },
652
- { name: "multiSigActionHash", type: "bytes32" },
650
+ { name: "fromSubAccount", type: "string" },
653
651
  { name: "nonce", type: "uint64" },
654
652
  ],
655
653
  },
@@ -6,108 +6,135 @@
6
6
  * ```ts
7
7
  * import { actionSorter, signL1Action } from "@nktkas/hyperliquid/signing";
8
8
  *
9
- * const privateKey = "0x..."; // or `viem`, `ethers`
9
+ * const privateKey = "0x..."; // `viem`, `ethers`, or private key directly`
10
10
  *
11
+ * const action = actionSorter.cancel({
12
+ * type: "cancel",
13
+ * cancels: [
14
+ * { a: 0, o: 12345 },
15
+ * ],
16
+ * });
11
17
  * const nonce = Date.now();
12
- * const action = {
13
- * type: "cancel",
14
- * cancels: [
15
- * { a: 0, o: 12345 },
16
- * ],
17
- * } as const;
18
- *
19
- * const signature = await signL1Action({
20
- * wallet: privateKey,
21
- * action: actionSorter[action.type](action),
22
- * nonce,
18
+ *
19
+ * const signature = await signL1Action({ wallet: privateKey, action, nonce });
20
+ *
21
+ * // Send the signed action to the Hyperliquid API
22
+ * const response = await fetch("https://api.hyperliquid.xyz/exchange", {
23
+ * method: "POST",
24
+ * headers: { "Content-Type": "application/json" },
25
+ * body: JSON.stringify({ action, signature, nonce }), // recommended to send the same formatted action
23
26
  * });
27
+ * const body = await response.json();
24
28
  * ```
25
29
  *
26
30
  * @example Signing a user-signed action
27
31
  * ```ts
28
- * import { signUserSignedAction, userSignedActionEip712Types } from "@nktkas/hyperliquid/signing";
32
+ * import { actionSorter, signUserSignedAction, userSignedActionEip712Types } from "@nktkas/hyperliquid/signing";
29
33
  *
30
- * const privateKey = "0x..."; // or `viem`, `ethers`
34
+ * const privateKey = "0x..."; // `viem`, `ethers`, or private key directly`
31
35
  *
32
- * const action = {
33
- * type: "approveAgent",
34
- * signatureChainId: "0x66eee",
35
- * hyperliquidChain: "Mainnet",
36
- * agentAddress: "0x...",
37
- * agentName: "Agent",
38
- * nonce: Date.now(),
39
- * } as const;
36
+ * const action = actionSorter.approveAgent({
37
+ * type: "approveAgent",
38
+ * signatureChainId: "0x66eee",
39
+ * hyperliquidChain: "Mainnet",
40
+ * agentAddress: "0x...",
41
+ * agentName: "Agent",
42
+ * nonce: Date.now(),
43
+ * });
40
44
  *
41
45
  * const signature = await signUserSignedAction({
42
- * wallet: privateKey,
43
- * action,
44
- * types: userSignedActionEip712Types[action.type],
46
+ * wallet: privateKey,
47
+ * action,
48
+ * types: userSignedActionEip712Types[action.type],
49
+ * });
50
+ *
51
+ * // Send the signed action to the Hyperliquid API
52
+ * const response = await fetch("https://api.hyperliquid.xyz/exchange", {
53
+ * method: "POST",
54
+ * headers: { "Content-Type": "application/json" },
55
+ * body: JSON.stringify({ action, signature, nonce: action.nonce }), // recommended to send the same formatted action
45
56
  * });
57
+ * const body = await response.json();
46
58
  * ```
47
59
  *
48
60
  * @example Signing a multi-signature action
49
61
  * ```ts
50
62
  * import { actionSorter, signL1Action, signMultiSigAction } from "@nktkas/hyperliquid/signing";
51
- * import { privateKeyToAccount } from "viem/accounts";
63
+ * import { privateKeyToAccount } from "npm:viem/accounts";
52
64
  *
53
- * const wallet = privateKeyToAccount("0x..."); // or `ethers`, private key with address
65
+ * const wallet = privateKeyToAccount("0x..."); // or `ethers`, private key directly
54
66
  * const multiSigUser = "0x...";
55
67
  *
68
+ * const action = actionSorter.scheduleCancel({
69
+ * type: "scheduleCancel",
70
+ * time: Date.now() + 10000,
71
+ * });
56
72
  * const nonce = Date.now();
57
- * const action = {
58
- * type: "scheduleCancel",
59
- * time: Date.now() + 10000,
60
- * } as const;
61
- *
62
- * // First, create the required number of signatures
63
- * const signature = await signL1Action({
64
- * wallet,
65
- * action: [multiSigUser.toLowerCase(), wallet.address.toLowerCase(), actionSorter[action.type](action)],
73
+ *
74
+ * // Create the required number of signatures
75
+ * const signatures = await Promise.all(["0x...", "0x..."].map(async (signerPrivKey) => {
76
+ * return await signL1Action({
77
+ * wallet: signerPrivKey as `0x${string}`,
78
+ * action: [multiSigUser.toLowerCase(), wallet.address.toLowerCase(), action],
66
79
  * nonce,
67
- * });
80
+ * });
81
+ * }));
82
+ *
83
+ * // or user-signed action
84
+ * // const signatures = await Promise.all(["0x...", "0x..."].map(async (signerPrivKey) => {
85
+ * // return await signUserSignedAction({
86
+ * // wallet: signerPrivKey as `0x${string}`,
87
+ * // action: {
88
+ * // ...action,
89
+ * // payloadMultiSigUser: multiSigUser,
90
+ * // outerSigner: wallet.address,
91
+ * // },
92
+ * // types: userSignedActionEip712Types[action.type],
93
+ * // });
94
+ * // }));
68
95
  *
69
96
  * // Then use signatures in the multi-sig action
70
- * const multiSigSignature = await signMultiSigAction({
71
- * wallet,
72
- * action: {
73
- * signatureChainId: "0x66eee",
74
- * signatures: [signature],
75
- * payload: {
76
- * multiSigUser,
77
- * outerSigner: wallet.address,
78
- * action,
79
- * },
80
- * },
81
- * nonce,
97
+ * const multiSigAction = actionSorter.multiSig({
98
+ * type: "multiSig",
99
+ * signatureChainId: "0x66eee",
100
+ * signatures,
101
+ * payload: {
102
+ * multiSigUser,
103
+ * outerSigner: wallet.address,
104
+ * action,
105
+ * },
106
+ * });
107
+ * const multiSigSignature = await signMultiSigAction({ wallet, action: multiSigAction, nonce });
108
+ *
109
+ * // Send the multi-sig action to the Hyperliquid API
110
+ * const response = await fetch("https://api.hyperliquid.xyz/exchange", {
111
+ * method: "POST",
112
+ * headers: { "Content-Type": "application/json" },
113
+ * body: JSON.stringify({ action: multiSigAction, signature: multiSigSignature, nonce }), // recommended to send the same formatted action
82
114
  * });
115
+ * const body = await response.json();
83
116
  * ```
84
117
  *
85
118
  * @module
86
119
  */
87
- import type { Hex } from "../base.js";
88
- import { type AbstractEthersSigner, type AbstractEthersV5Signer, type AbstractViemWalletClient, type AbstractWallet, type AbstractWindowEthereum, isAbstractEthersSigner, isAbstractEthersV5Signer, isAbstractViemWalletClient, isAbstractWindowEthereum, isValidPrivateKey, type Signature } from "./_signTypedData/mod.js";
89
- export { type AbstractEthersSigner, type AbstractEthersV5Signer, type AbstractViemWalletClient, type AbstractWallet, type AbstractWindowEthereum, type Hex, isAbstractEthersSigner, isAbstractEthersV5Signer, isAbstractViemWalletClient, isAbstractWindowEthereum, isValidPrivateKey, type Signature, };
90
- export * from "./_sorter.js";
120
+ import { type AbstractWallet, getWalletAddress, getWalletChainId, type Signature } from "./_signTypedData/mod.js";
121
+ import { actionSorter, userSignedActionEip712Types } from "./_sorter.js";
122
+ export { type AbstractWallet, actionSorter, getWalletAddress, getWalletChainId, type Signature, userSignedActionEip712Types, };
91
123
  /**
92
124
  * Create a hash of the L1 action.
93
125
  * @example
94
126
  * ```ts
95
127
  * import { actionSorter, createL1ActionHash } from "@nktkas/hyperliquid/signing";
96
128
  *
97
- * const action = {
98
- * type: "cancel",
99
- * cancels: [
100
- * { a: 0, o: 12345 },
101
- * ],
102
- * } as const;
129
+ * const action = actionSorter.cancel({
130
+ * type: "cancel",
131
+ * cancels: [
132
+ * { a: 0, o: 12345 },
133
+ * ],
134
+ * });
103
135
  * const nonce = Date.now();
104
136
  *
105
- * const actionHash = createL1ActionHash({
106
- * action: actionSorter[action.type](action),
107
- * nonce,
108
- * vaultAddress: "0x...", // optional
109
- * expiresAfter: Date.now() + 10_000, // optional
110
- * });
137
+ * const actionHash = createL1ActionHash({ action, nonce });
111
138
  * ```
112
139
  */
113
140
  export declare function createL1ActionHash(args: {
@@ -116,37 +143,33 @@ export declare function createL1ActionHash(args: {
116
143
  /** The current timestamp in ms. */
117
144
  nonce: number;
118
145
  /** Optional vault address used in the action. */
119
- vaultAddress?: Hex;
146
+ vaultAddress?: `0x${string}`;
120
147
  /** Optional expiration time of the action in ms since the epoch. */
121
148
  expiresAfter?: number;
122
- }): Hex;
149
+ }): `0x${string}`;
123
150
  /**
124
151
  * Sign an L1 action.
125
152
  * @example
126
153
  * ```ts
127
154
  * import { actionSorter, signL1Action } from "@nktkas/hyperliquid/signing";
128
155
  *
129
- * const privateKey = "0x..."; // or `viem`, `ethers`
156
+ * const privateKey = "0x..."; // `viem`, `ethers`, or private key directly`
130
157
  *
131
- * const nonce = Date.now();
132
- * const action = {
133
- * type: "cancel",
134
- * cancels: [
135
- * { a: 0, o: 12345 },
136
- * ],
137
- * } as const;
138
- *
139
- * const signature = await signL1Action({
140
- * wallet: privateKey,
141
- * action: actionSorter[action.type](action),
142
- * nonce,
158
+ * const action = actionSorter.cancel({
159
+ * type: "cancel",
160
+ * cancels: [
161
+ * { a: 0, o: 12345 },
162
+ * ],
143
163
  * });
164
+ * const nonce = Date.now();
165
+ *
166
+ * const signature = await signL1Action({ wallet: privateKey, action, nonce });
144
167
  *
145
168
  * // Send the signed action to the Hyperliquid API
146
169
  * const response = await fetch("https://api.hyperliquid.xyz/exchange", {
147
- * method: "POST",
148
- * headers: { "Content-Type": "application/json" },
149
- * body: JSON.stringify({ action, signature, nonce }),
170
+ * method: "POST",
171
+ * headers: { "Content-Type": "application/json" },
172
+ * body: JSON.stringify({ action, signature, nonce }), // recommended to send the same formatted action
150
173
  * });
151
174
  * const body = await response.json();
152
175
  * ```
@@ -161,7 +184,7 @@ export declare function signL1Action(args: {
161
184
  /** Indicates if the action is for the testnet. (default: false) */
162
185
  isTestnet?: boolean;
163
186
  /** Optional vault address used in the action. */
164
- vaultAddress?: Hex;
187
+ vaultAddress?: `0x${string}`;
165
188
  /** Optional expiration time of the action in ms since the epoch. */
166
189
  expiresAfter?: number;
167
190
  }): Promise<Signature>;
@@ -169,30 +192,30 @@ export declare function signL1Action(args: {
169
192
  * Sign a user-signed action.
170
193
  * @example
171
194
  * ```ts
172
- * import { signUserSignedAction, userSignedActionEip712Types } from "@nktkas/hyperliquid/signing";
195
+ * import { actionSorter, signUserSignedAction, userSignedActionEip712Types } from "@nktkas/hyperliquid/signing";
173
196
  *
174
- * const privateKey = "0x..."; // or `viem`, `ethers`
197
+ * const privateKey = "0x..."; // `viem`, `ethers`, or private key directly`
175
198
  *
176
- * const action = {
177
- * type: "approveAgent",
178
- * signatureChainId: "0x66eee",
179
- * hyperliquidChain: "Mainnet",
180
- * agentAddress: "0x...",
181
- * agentName: "Agent",
182
- * nonce: Date.now(),
183
- * } as const;
199
+ * const action = actionSorter.approveAgent({
200
+ * type: "approveAgent",
201
+ * signatureChainId: "0x66eee",
202
+ * hyperliquidChain: "Mainnet",
203
+ * agentAddress: "0x...",
204
+ * agentName: "Agent",
205
+ * nonce: Date.now(),
206
+ * });
184
207
  *
185
208
  * const signature = await signUserSignedAction({
186
- * wallet: privateKey,
187
- * action,
188
- * types: userSignedActionEip712Types[action.type],
209
+ * wallet: privateKey,
210
+ * action,
211
+ * types: userSignedActionEip712Types[action.type],
189
212
  * });
190
213
  *
191
214
  * // Send the signed action to the Hyperliquid API
192
215
  * const response = await fetch("https://api.hyperliquid.xyz/exchange", {
193
- * method: "POST",
194
- * headers: { "Content-Type": "application/json" },
195
- * body: JSON.stringify({ action, signature, nonce: action.nonce }),
216
+ * method: "POST",
217
+ * headers: { "Content-Type": "application/json" },
218
+ * body: JSON.stringify({ action, signature, nonce: action.nonce }), // recommended to send the same formatted action
196
219
  * });
197
220
  * const body = await response.json();
198
221
  * ```
@@ -200,11 +223,17 @@ export declare function signL1Action(args: {
200
223
  export declare function signUserSignedAction(args: {
201
224
  /** Wallet to sign the action. */
202
225
  wallet: AbstractWallet;
203
- /** The action to be signed. */
226
+ /** The action to be signed (hex strings must be in lower case). */
204
227
  action: {
205
- signatureChainId: Hex;
228
+ signatureChainId: `0x${string}`;
206
229
  [key: string]: unknown;
207
- };
230
+ } & ({
231
+ payloadMultiSigUser: `0x${string}`;
232
+ outerSigner: `0x${string}`;
233
+ } | {
234
+ payloadMultiSigUser?: undefined;
235
+ outerSigner?: undefined;
236
+ });
208
237
  /** The types of the action (hash depends on key order). */
209
238
  types: {
210
239
  [key: string]: {
@@ -218,38 +247,59 @@ export declare function signUserSignedAction(args: {
218
247
  * @example
219
248
  * ```ts
220
249
  * import { actionSorter, signL1Action, signMultiSigAction } from "@nktkas/hyperliquid/signing";
221
- * import { privateKeyToAccount } from "viem/accounts";
250
+ * import { privateKeyToAccount } from "npm:viem/accounts";
222
251
  *
223
- * const wallet = privateKeyToAccount("0x..."); // or `ethers`, private key with address
252
+ * const wallet = privateKeyToAccount("0x..."); // or ethers, private key directly
224
253
  * const multiSigUser = "0x...";
225
254
  *
255
+ * const action = actionSorter.scheduleCancel({
256
+ * type: "scheduleCancel",
257
+ * time: Date.now() + 10000,
258
+ * });
226
259
  * const nonce = Date.now();
227
- * const action = {
228
- * type: "scheduleCancel",
229
- * time: Date.now() + 10000,
230
- * } as const;
231
- *
232
- * // First, create the required number of signatures
233
- * const signature = await signL1Action({
234
- * wallet,
235
- * action: [multiSigUser.toLowerCase(), wallet.address.toLowerCase(), actionSorter[action.type](action)],
260
+ *
261
+ * // Create the required number of signatures
262
+ * const signatures = await Promise.all(["0x...", "0x..."].map(async (signerPrivKey) => {
263
+ * return await signL1Action({
264
+ * wallet: signerPrivKey as `0x${string}`,
265
+ * action: [multiSigUser.toLowerCase(), wallet.address.toLowerCase(), action],
236
266
  * nonce,
237
- * });
267
+ * });
268
+ * }));
269
+ *
270
+ * // or user-signed action
271
+ * // const signatures = await Promise.all(["0x...", "0x..."].map(async (signerPrivKey) => {
272
+ * // return await signUserSignedAction({
273
+ * // wallet: signerPrivKey as `0x${string}`,
274
+ * // action: {
275
+ * // ...action,
276
+ * // payloadMultiSigUser: multiSigUser,
277
+ * // outerSigner: wallet.address,
278
+ * // },
279
+ * // types: userSignedActionEip712Types[action.type],
280
+ * // });
281
+ * // }));
238
282
  *
239
283
  * // Then use signatures in the multi-sig action
240
- * const multiSigSignature = await signMultiSigAction({
241
- * wallet,
242
- * action: {
243
- * signatureChainId: "0x66eee",
244
- * signatures: [signature],
245
- * payload: {
246
- * multiSigUser,
247
- * outerSigner: wallet.address,
248
- * action,
249
- * },
250
- * },
251
- * nonce,
284
+ * const multiSigAction = actionSorter.multiSig({
285
+ * type: "multiSig",
286
+ * signatureChainId: "0x66eee",
287
+ * signatures,
288
+ * payload: {
289
+ * multiSigUser,
290
+ * outerSigner: wallet.address,
291
+ * action,
292
+ * },
252
293
  * });
294
+ * const multiSigSignature = await signMultiSigAction({ wallet, action: multiSigAction, nonce });
295
+ *
296
+ * // Send the multi-sig action to the Hyperliquid API
297
+ * const response = await fetch("https://api.hyperliquid.xyz/exchange", {
298
+ * method: "POST",
299
+ * headers: { "Content-Type": "application/json" },
300
+ * body: JSON.stringify({ action: multiSigAction, signature: multiSigSignature, nonce }), // recommended to send the same formatted action
301
+ * });
302
+ * const body = await response.json();
253
303
  * ```
254
304
  */
255
305
  export declare function signMultiSigAction(args: {
@@ -257,7 +307,7 @@ export declare function signMultiSigAction(args: {
257
307
  wallet: AbstractWallet;
258
308
  /** The action to be signed (hash depends on key order). */
259
309
  action: {
260
- signatureChainId: Hex;
310
+ signatureChainId: `0x${string}`;
261
311
  [key: string]: unknown;
262
312
  };
263
313
  /** The current timestamp in ms. */
@@ -265,7 +315,7 @@ export declare function signMultiSigAction(args: {
265
315
  /** Indicates if the action is for the testnet. (default: false) */
266
316
  isTestnet?: boolean;
267
317
  /** Optional vault address used in the action. */
268
- vaultAddress?: Hex;
318
+ vaultAddress?: `0x${string}`;
269
319
  /** Optional expiration time of the action in ms since the epoch. */
270
320
  expiresAfter?: number;
271
321
  }): Promise<Signature>;