@pushchain/core 5.1.3 → 5.1.4-alpha.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 (131) hide show
  1. package/package.json +29 -6
  2. package/src/lib/constants/abi/prc20.evm.d.ts +22 -2
  3. package/src/lib/constants/abi/prc20.evm.js +11 -3
  4. package/src/lib/constants/abi/universalGatewayPC.evm.d.ts +59 -0
  5. package/src/lib/constants/abi/universalGatewayPC.evm.js +26 -0
  6. package/src/lib/constants/chain.d.ts +4 -0
  7. package/src/lib/constants/chain.js +6 -2
  8. package/src/lib/index.d.ts +2 -2
  9. package/src/lib/internal/bs58.d.ts +2 -0
  10. package/src/lib/internal/bs58.js +7 -0
  11. package/src/lib/orchestrator/cea-utils.d.ts +0 -9
  12. package/src/lib/orchestrator/cea-utils.js +15 -4
  13. package/src/lib/orchestrator/internals/account-manager.d.ts +16 -0
  14. package/src/lib/orchestrator/internals/account-manager.js +191 -0
  15. package/src/lib/orchestrator/internals/cascade.d.ts +23 -0
  16. package/src/lib/orchestrator/internals/cascade.js +945 -0
  17. package/src/lib/orchestrator/internals/confirmation.d.ts +9 -0
  18. package/src/lib/orchestrator/internals/confirmation.js +123 -0
  19. package/src/lib/orchestrator/internals/context.d.ts +38 -0
  20. package/src/lib/orchestrator/internals/context.js +49 -0
  21. package/src/lib/orchestrator/internals/execute-funds-only.d.ts +11 -0
  22. package/src/lib/orchestrator/internals/execute-funds-only.js +219 -0
  23. package/src/lib/orchestrator/internals/execute-funds-payload.d.ts +11 -0
  24. package/src/lib/orchestrator/internals/execute-funds-payload.js +222 -0
  25. package/src/lib/orchestrator/internals/execute-standard.d.ts +13 -0
  26. package/src/lib/orchestrator/internals/execute-standard.js +225 -0
  27. package/src/lib/orchestrator/internals/gas-calculator.d.ts +38 -0
  28. package/src/lib/orchestrator/internals/gas-calculator.js +424 -0
  29. package/src/lib/orchestrator/internals/gateway-client.d.ts +24 -0
  30. package/src/lib/orchestrator/internals/gateway-client.js +191 -0
  31. package/src/lib/orchestrator/internals/helpers.d.ts +26 -0
  32. package/src/lib/orchestrator/internals/helpers.js +181 -0
  33. package/src/lib/orchestrator/internals/index.d.ts +24 -0
  34. package/src/lib/orchestrator/internals/index.js +132 -0
  35. package/src/lib/orchestrator/internals/outbound-sync.d.ts +49 -0
  36. package/src/lib/orchestrator/internals/outbound-sync.js +357 -0
  37. package/src/lib/orchestrator/internals/outbound-tracker.d.ts +8 -0
  38. package/src/lib/orchestrator/internals/outbound-tracker.js +64 -0
  39. package/src/lib/orchestrator/internals/payload-builder.d.ts +24 -0
  40. package/src/lib/orchestrator/internals/payload-builder.js +178 -0
  41. package/src/lib/orchestrator/internals/push-chain-tx.d.ts +32 -0
  42. package/src/lib/orchestrator/internals/push-chain-tx.js +207 -0
  43. package/src/lib/orchestrator/internals/quote.d.ts +9 -0
  44. package/src/lib/orchestrator/internals/quote.js +114 -0
  45. package/src/lib/orchestrator/internals/rescue.d.ts +20 -0
  46. package/src/lib/orchestrator/internals/rescue.js +112 -0
  47. package/src/lib/orchestrator/internals/response-builder.d.ts +26 -0
  48. package/src/lib/orchestrator/internals/response-builder.js +504 -0
  49. package/src/lib/orchestrator/internals/route-handlers.d.ts +77 -0
  50. package/src/lib/orchestrator/internals/route-handlers.js +1192 -0
  51. package/src/lib/orchestrator/internals/signing.d.ts +27 -0
  52. package/src/lib/orchestrator/internals/signing.js +258 -0
  53. package/src/lib/orchestrator/internals/svm-bridge.d.ts +21 -0
  54. package/src/lib/orchestrator/internals/svm-bridge.js +122 -0
  55. package/src/lib/orchestrator/internals/svm-helpers.d.ts +35 -0
  56. package/src/lib/orchestrator/internals/svm-helpers.js +143 -0
  57. package/src/lib/orchestrator/internals/tx-transformer.d.ts +12 -0
  58. package/src/lib/orchestrator/internals/tx-transformer.js +120 -0
  59. package/src/lib/orchestrator/internals/uea-manager.d.ts +17 -0
  60. package/src/lib/orchestrator/internals/uea-manager.js +164 -0
  61. package/src/lib/orchestrator/orchestrator.d.ts +33 -431
  62. package/src/lib/orchestrator/orchestrator.js +124 -6125
  63. package/src/lib/orchestrator/orchestrator.types.d.ts +11 -10
  64. package/src/lib/orchestrator/payload-builders.js +34 -8
  65. package/src/lib/price-fetch/price-fetch.js +19 -7
  66. package/src/lib/push-chain/push-chain.d.ts +6 -0
  67. package/src/lib/push-chain/push-chain.js +10 -2
  68. package/src/lib/push-client/push-client.d.ts +3 -0
  69. package/src/lib/push-client/push-client.js +21 -31
  70. package/src/lib/universal/account/account.d.ts +35 -16
  71. package/src/lib/universal/account/account.js +298 -16
  72. package/src/lib/universal/signer/signer.d.ts +2 -3
  73. package/src/lib/universal/signer/signer.js +65 -115
  74. package/src/lib/universal/universal.types.d.ts +41 -0
  75. package/src/lib/utils.d.ts +7 -2
  76. package/src/lib/utils.js +65 -34
  77. package/src/lib/vm-client/evm-client.js +3 -11
  78. package/src/lib/vm-client/svm-client.d.ts +0 -4
  79. package/src/lib/vm-client/svm-client.js +2 -8
  80. package/src/index.js.map +0 -1
  81. package/src/lib/cache/cache.js.map +0 -1
  82. package/src/lib/constants/abi/cea.evm.js.map +0 -1
  83. package/src/lib/constants/abi/ceaFactory.evm.js.map +0 -1
  84. package/src/lib/constants/abi/erc20.evm.js.map +0 -1
  85. package/src/lib/constants/abi/factoryV1.js.map +0 -1
  86. package/src/lib/constants/abi/feeLocker.evm.js.map +0 -1
  87. package/src/lib/constants/abi/index.js.map +0 -1
  88. package/src/lib/constants/abi/prc20.evm.js.map +0 -1
  89. package/src/lib/constants/abi/uea-factory.js.map +0 -1
  90. package/src/lib/constants/abi/uea.evm.js.map +0 -1
  91. package/src/lib/constants/abi/uea.svm.js.map +0 -1
  92. package/src/lib/constants/abi/universalGateway.evm.js.map +0 -1
  93. package/src/lib/constants/abi/universalGatewayPC.evm.js.map +0 -1
  94. package/src/lib/constants/abi/universalGatewayV0.evm.js.map +0 -1
  95. package/src/lib/constants/chain.js.map +0 -1
  96. package/src/lib/constants/enums.js.map +0 -1
  97. package/src/lib/constants/index.js.map +0 -1
  98. package/src/lib/constants/selectors.js.map +0 -1
  99. package/src/lib/constants/tokens.js.map +0 -1
  100. package/src/lib/generated/uexecutor/v1/query.js.map +0 -1
  101. package/src/lib/generated/uexecutor/v1/types.js.map +0 -1
  102. package/src/lib/generated/uexecutor/v2/index.js.map +0 -1
  103. package/src/lib/generated/uexecutor/v2/query.js.map +0 -1
  104. package/src/lib/generated/uexecutor/v2/types.js.map +0 -1
  105. package/src/lib/generated/v1/tx.js.map +0 -1
  106. package/src/lib/index.js.map +0 -1
  107. package/src/lib/internal/buffer.js.map +0 -1
  108. package/src/lib/internal/global-buffer-polyfill.js.map +0 -1
  109. package/src/lib/orchestrator/cea-utils.js.map +0 -1
  110. package/src/lib/orchestrator/orchestrator.js.map +0 -1
  111. package/src/lib/orchestrator/orchestrator.types.js.map +0 -1
  112. package/src/lib/orchestrator/payload-builders.js.map +0 -1
  113. package/src/lib/orchestrator/route-detector.js.map +0 -1
  114. package/src/lib/price-fetch/price-fetch.js.map +0 -1
  115. package/src/lib/progress-hook/progress-hook.js.map +0 -1
  116. package/src/lib/progress-hook/progress-hook.types.js.map +0 -1
  117. package/src/lib/push-chain/helpers/abis.js.map +0 -1
  118. package/src/lib/push-chain/helpers/addresses.js.map +0 -1
  119. package/src/lib/push-chain/push-chain.js.map +0 -1
  120. package/src/lib/push-client/push-client.js.map +0 -1
  121. package/src/lib/push-client/push-client.types.js.map +0 -1
  122. package/src/lib/universal/account/account.js.map +0 -1
  123. package/src/lib/universal/account/index.js.map +0 -1
  124. package/src/lib/universal/signer/index.js.map +0 -1
  125. package/src/lib/universal/signer/signer.js.map +0 -1
  126. package/src/lib/universal/signer/signer.types.js.map +0 -1
  127. package/src/lib/universal/universal.types.js.map +0 -1
  128. package/src/lib/utils.js.map +0 -1
  129. package/src/lib/vm-client/evm-client.js.map +0 -1
  130. package/src/lib/vm-client/svm-client.js.map +0 -1
  131. package/src/lib/vm-client/vm-client.types.js.map +0 -1
@@ -360,6 +360,17 @@ export interface UniversalOutboundTxRequest {
360
360
  /** Address to receive funds on revert */
361
361
  revertRecipient: `0x${string}`;
362
362
  }
363
+ /**
364
+ * Parameters for rescuing stuck funds on a source chain.
365
+ * Used when a CEA-to-Push inbound transaction fails and tokens are
366
+ * locked in the Vault on the source chain.
367
+ */
368
+ export interface RescueFundsParams {
369
+ /** The universalTxId of the failed inbound transaction (bytes32 hash, 0x-prefixed) */
370
+ universalTxId: `0x${string}`;
371
+ /** PRC-20 token address on Push Chain whose source-chain counterpart is locked */
372
+ prc20: `0x${string}`;
373
+ }
363
374
  /**
364
375
  * Internal metadata attached to each prepared transaction.
365
376
  * Carries all information needed to nest this hop into a cascade.
@@ -459,16 +470,6 @@ export interface PreparedUniversalTx {
459
470
  /** Execute this prepared transaction */
460
471
  send: () => Promise<UniversalTxResponse>;
461
472
  }
462
- /**
463
- * @deprecated Use CascadedTransactionBuilder instead.
464
- * Kept for backward compatibility.
465
- */
466
- export interface ChainedTransactionBuilder {
467
- /** Add another transaction to the chain */
468
- thenOn: (nextTx: UniversalExecuteParams) => ChainedTransactionBuilder;
469
- /** Execute all chained transactions */
470
- send: () => Promise<MultiChainTxResponse>;
471
- }
472
473
  /**
473
474
  * @deprecated Use CascadedTxResponse instead.
474
475
  * Kept for backward compatibility.
@@ -20,7 +20,10 @@ exports.encodeSvmExecutePayload = encodeSvmExecutePayload;
20
20
  exports.encodeSvmCeaToUeaPayload = encodeSvmCeaToUeaPayload;
21
21
  const viem_1 = require("viem");
22
22
  const push_chain_1 = require("../push-chain/push-chain");
23
- const abi_1 = require("../constants/abi");
23
+ const cea_evm_1 = require("../constants/abi/cea.evm");
24
+ const erc20_evm_1 = require("../constants/abi/erc20.evm");
25
+ const universalGatewayV0_evm_1 = require("../constants/abi/universalGatewayV0.evm");
26
+ const universalGatewayPC_evm_1 = require("../constants/abi/universalGatewayPC.evm");
24
27
  const selectors_1 = require("../constants/selectors");
25
28
  const chain_1 = require("../constants/chain");
26
29
  const enums_1 = require("../constants/enums");
@@ -66,7 +69,7 @@ function buildExecuteMulticall({ execute, ueaAddress, logger, }) {
66
69
  // - When execute.data is an array (explicit multicall), user handles fund transfers in their calls
67
70
  if (!isNative && !isArrayMulticall) {
68
71
  const erc20Transfer = (0, viem_1.encodeFunctionData)({
69
- abi: abi_1.ERC20_EVM,
72
+ abi: erc20_evm_1.ERC20_EVM,
70
73
  functionName: 'transfer',
71
74
  args: [execute.to, (_q = execute.funds) === null || _q === void 0 ? void 0 : _q.amount],
72
75
  });
@@ -219,12 +222,24 @@ function buildSingleCeaCall(target, value, data) {
219
222
  * @returns Array of multicall operations
220
223
  */
221
224
  function buildApproveAndInteract(tokenAddress, spender, amount, interactCall) {
225
+ // Reset allowance to 0 first to handle non-standard ERC-20 tokens (e.g. USDT)
226
+ // that revert if approve is called with non-zero value when current allowance is non-zero.
227
+ const approveZeroData = (0, viem_1.encodeFunctionData)({
228
+ abi: erc20_evm_1.ERC20_EVM,
229
+ functionName: 'approve',
230
+ args: [spender, BigInt(0)],
231
+ });
222
232
  const approveData = (0, viem_1.encodeFunctionData)({
223
- abi: abi_1.ERC20_EVM,
233
+ abi: erc20_evm_1.ERC20_EVM,
224
234
  functionName: 'approve',
225
235
  args: [spender, amount],
226
236
  });
227
237
  return [
238
+ {
239
+ to: tokenAddress,
240
+ value: BigInt(0),
241
+ data: approveZeroData,
242
+ },
228
243
  {
229
244
  to: tokenAddress,
230
245
  value: BigInt(0),
@@ -248,7 +263,7 @@ function buildApproveAndInteract(tokenAddress, spender, amount, interactCall) {
248
263
  */
249
264
  function buildSendUniversalTxFromCEA(gatewayAddress, recipient, token, amount, payload, revertRecipient, signatureData = '0x', nativeValue = BigInt(0)) {
250
265
  const calldata = (0, viem_1.encodeFunctionData)({
251
- abi: abi_1.UNIVERSAL_GATEWAY_V0,
266
+ abi: universalGatewayV0_evm_1.UNIVERSAL_GATEWAY_V0,
252
267
  functionName: 'sendUniversalTxFromCEA',
253
268
  args: [
254
269
  {
@@ -286,7 +301,7 @@ function buildSendUniversalTxFromCEA(gatewayAddress, recipient, token, amount, p
286
301
  */
287
302
  function buildSendUniversalTxToUEA(ceaAddress, token, amount, payload, revertRecipient) {
288
303
  const calldata = (0, viem_1.encodeFunctionData)({
289
- abi: abi_1.CEA_EVM,
304
+ abi: cea_evm_1.CEA_EVM,
290
305
  functionName: 'sendUniversalTxToUEA',
291
306
  args: [token, amount, payload, revertRecipient],
292
307
  });
@@ -344,7 +359,7 @@ function buildNativeTransfer(to, value) {
344
359
  */
345
360
  function buildErc20Transfer(tokenAddress, to, amount) {
346
361
  const transferData = (0, viem_1.encodeFunctionData)({
347
- abi: abi_1.ERC20_EVM,
362
+ abi: erc20_evm_1.ERC20_EVM,
348
363
  functionName: 'transfer',
349
364
  args: [to, amount],
350
365
  });
@@ -406,13 +421,24 @@ function buildOutboundApprovalAndCall(opts) {
406
421
  const { prc20Token, burnAmount, gasFee, gatewayPcAddress, outboundRequest } = opts;
407
422
  const multicalls = [];
408
423
  // ERC20 approve for burn amount (contract calls transferFrom for PRC20 burn)
424
+ // Reset to 0 first for USDT-style tokens that revert on non-zero to non-zero approve.
409
425
  if (burnAmount > BigInt(0) &&
410
426
  prc20Token.toLowerCase() !== selectors_1.ZERO_ADDRESS.toLowerCase()) {
427
+ const approveZeroData = (0, viem_1.encodeFunctionData)({
428
+ abi: erc20_evm_1.ERC20_EVM,
429
+ functionName: 'approve',
430
+ args: [gatewayPcAddress, BigInt(0)],
431
+ });
411
432
  const approveData = (0, viem_1.encodeFunctionData)({
412
- abi: abi_1.ERC20_EVM,
433
+ abi: erc20_evm_1.ERC20_EVM,
413
434
  functionName: 'approve',
414
435
  args: [gatewayPcAddress, burnAmount],
415
436
  });
437
+ multicalls.push({
438
+ to: prc20Token,
439
+ value: BigInt(0),
440
+ data: approveZeroData,
441
+ });
416
442
  multicalls.push({
417
443
  to: prc20Token,
418
444
  value: BigInt(0),
@@ -421,7 +447,7 @@ function buildOutboundApprovalAndCall(opts) {
421
447
  }
422
448
  // Gas fee + protocol fee paid as native msg.value (no ERC20 approve for gas)
423
449
  const outboundCallData = (0, viem_1.encodeFunctionData)({
424
- abi: abi_1.UNIVERSAL_GATEWAY_PC,
450
+ abi: universalGatewayPC_evm_1.UNIVERSAL_GATEWAY_PC,
425
451
  functionName: 'sendUniversalTxOutbound',
426
452
  args: [outboundRequest],
427
453
  });
@@ -5,36 +5,46 @@ const tslib_1 = require("tslib");
5
5
  const enums_1 = require("../constants/enums");
6
6
  const chain_1 = require("../constants/chain");
7
7
  const evm_client_1 = require("../vm-client/evm-client");
8
- const abi_1 = require("../constants/abi");
8
+ const feeLocker_evm_1 = require("../constants/abi/feeLocker.evm");
9
+ const feeLocker_json_1 = tslib_1.__importDefault(require("../constants/abi/feeLocker.json"));
9
10
  const anchor_1 = require("@coral-xyz/anchor");
10
11
  const web3_js_1 = require("@solana/web3.js");
11
12
  const web3_js_2 = require("@solana/web3.js");
12
13
  const anchor_2 = require("@coral-xyz/anchor");
14
+ // Module-level price cache — survives across PriceFetch instances.
15
+ // Chainlink feeds update every 1-2h or on 0.5% price move; 30s TTL is safe.
16
+ const PRICE_CACHE_TTL_MS = 30000;
17
+ const priceCache = new Map();
13
18
  class PriceFetch {
14
19
  constructor(rpcUrls = {}) {
15
20
  this.rpcUrls = rpcUrls;
16
21
  }
17
22
  getPrice(chain) {
18
23
  return tslib_1.__awaiter(this, void 0, void 0, function* () {
24
+ const cached = priceCache.get(chain);
25
+ if (cached && Date.now() < cached.expiry) {
26
+ return cached.price;
27
+ }
19
28
  const rpcUrls = this.rpcUrls[chain] || chain_1.CHAIN_INFO[chain].defaultRPC;
20
29
  const vm = chain_1.CHAIN_INFO[chain].vm;
21
30
  const { lockerContract } = chain_1.CHAIN_INFO[chain];
22
31
  if (!lockerContract) {
23
32
  throw new Error(`Locker contract not configured for chain: ${chain}`);
24
33
  }
34
+ let price;
25
35
  switch (vm) {
26
36
  case enums_1.VM.EVM: {
27
37
  const evmClient = new evm_client_1.EvmClient({ rpcUrls });
28
38
  const result = yield evmClient.readContract({
29
- abi: abi_1.FEE_LOCKER_EVM,
39
+ abi: feeLocker_evm_1.FEE_LOCKER_EVM,
30
40
  address: lockerContract,
31
41
  functionName: 'getEthUsdPrice',
32
42
  });
33
43
  // getEthUsdPrice returns price scaled to 1e18 and the chainlink feed decimals.
34
44
  // Downstream lockFee math expects the price in 8 decimals, so scale down from 1e18 to 1e8.
35
45
  const [price1e18] = result;
36
- const price = price1e18 / BigInt(Math.pow(10, 10)); // 1e18 -> 1e8
37
- return price;
46
+ price = price1e18 / BigInt(Math.pow(10, 10)); // 1e18 -> 1e8
47
+ break;
38
48
  }
39
49
  case enums_1.VM.SVM: {
40
50
  const PRICE_ACCOUNT = new web3_js_2.PublicKey('7UVimffxr9ow1uXYxsr4LHAcV58mLzhmwaeKvJ1pjLiE');
@@ -43,7 +53,7 @@ class PriceFetch {
43
53
  publicKey: new web3_js_2.PublicKey('EfQYRThwBu4MsU7Lf3D2e68tCtdwfYj6f66ot1e2HNrq'),
44
54
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
45
55
  }, { commitment: 'confirmed' });
46
- const program = new anchor_1.Program(abi_1.FEE_LOCKER_SVM, provider);
56
+ const program = new anchor_1.Program(feeLocker_json_1.default, provider);
47
57
  const result = yield program.methods['getSolPrice']()
48
58
  .accounts({
49
59
  priceUpdate: PRICE_ACCOUNT,
@@ -53,13 +63,15 @@ class PriceFetch {
53
63
  throw new Error('Invalid price data returned');
54
64
  }
55
65
  // Exponent on this function is always NEGATIVE
56
- const price = result.price.toNumber();
57
- return BigInt(price);
66
+ price = BigInt(result.price.toNumber());
67
+ break;
58
68
  }
59
69
  default: {
60
70
  throw new Error(`Unsupported VM ${vm}`);
61
71
  }
62
72
  }
73
+ priceCache.set(chain, { price, expiry: Date.now() + PRICE_CACHE_TTL_MS });
74
+ return price;
63
75
  });
64
76
  }
65
77
  }
@@ -91,6 +91,12 @@ export declare class PushChain {
91
91
  * @param chain - The external chain where the CEA should be migrated
92
92
  */
93
93
  migrateCEA: Orchestrator['migrateCEA'];
94
+ /**
95
+ * Rescue stuck funds on a source chain.
96
+ * When a CEA-to-Push inbound tx fails, tokens get locked in the Vault.
97
+ * This triggers a manual revert via TSS to release those funds.
98
+ */
99
+ rescueFunds: Orchestrator['rescueFunds'];
94
100
  /**
95
101
  * Signs an arbitrary message
96
102
  */
@@ -9,7 +9,7 @@ const chain_1 = require("../constants/chain");
9
9
  const orchestrator_1 = require("../orchestrator/orchestrator");
10
10
  const signer_1 = require("../universal/signer");
11
11
  const utils_1 = require("../utils");
12
- const anchor_1 = require("@coral-xyz/anchor");
12
+ const bs58_1 = require("../internal/bs58");
13
13
  const viem_1 = require("viem");
14
14
  const evm_client_1 = require("../vm-client/evm-client");
15
15
  const tokens_1 = require("../constants/tokens");
@@ -102,6 +102,12 @@ class PushChain {
102
102
  }
103
103
  return orchestrator.migrateCEA.bind(orchestrator)(chain);
104
104
  },
105
+ rescueFunds: (params) => {
106
+ if (this.isReadMode) {
107
+ throw new Error('Read only mode cannot call rescueFunds function');
108
+ }
109
+ return orchestrator.rescueFunds.bind(orchestrator)(params);
110
+ },
105
111
  signMessage: (data) => tslib_1.__awaiter(this, void 0, void 0, function* () {
106
112
  if (this.isReadMode) {
107
113
  throw new Error('Read only mode cannot call signMessage function');
@@ -112,7 +118,7 @@ class PushChain {
112
118
  return (0, viem_1.bytesToHex)(sigBytes);
113
119
  }
114
120
  else if (chain_1.CHAIN_INFO[chain].vm === enums_1.VM.SVM) {
115
- return anchor_1.utils.bytes.bs58.encode(sigBytes);
121
+ return bs58_1.bs58.encode(Buffer.from(sigBytes));
116
122
  }
117
123
  return (0, viem_1.bytesToHex)(sigBytes);
118
124
  }),
@@ -399,6 +405,8 @@ class PushChain {
399
405
  ]).catch(() => {
400
406
  // Silently ignore — lazy check in execute() will retry if needed
401
407
  });
408
+ // Let execute() await the background fetch instead of re-fetching
409
+ orchestrator.accountStatusReadyPromise = instance.accountStatusReady;
402
410
  return instance;
403
411
  });
404
412
  }
@@ -7,6 +7,8 @@ import { QueryGetUniversalTxResponseV2 } from '../generated/uexecutor/v2/query';
7
7
  import { EvmClient } from '../vm-client/evm-client';
8
8
  import { PushClientOptions } from './push-client.types';
9
9
  export declare class PushClient extends EvmClient {
10
+ /** Gas limit for Cosmos transactions on Push Chain */
11
+ private static readonly COSMOS_GAS_LIMIT;
10
12
  pushChainInfo: {
11
13
  chainId: string;
12
14
  vm: import("../constants/enums").VM;
@@ -33,6 +35,7 @@ export declare class PushClient extends EvmClient {
33
35
  pushToUsdcDenominator: bigint;
34
36
  };
35
37
  private readonly ephemeralKey;
38
+ private readonly ephemeralAccount;
36
39
  private currentRpcIndex;
37
40
  constructor(clientOptions: PushClientOptions);
38
41
  /**
@@ -5,7 +5,6 @@ const tslib_1 = require("tslib");
5
5
  const viem_1 = require("viem");
6
6
  const tx_1 = require("../generated/v1/tx");
7
7
  const tx_2 = require("cosmjs-types/cosmos/tx/v1beta1/tx");
8
- const protobufjs_1 = require("protobufjs");
9
8
  const proto_signing_1 = require("@cosmjs/proto-signing");
10
9
  const stargate_1 = require("@cosmjs/stargate");
11
10
  const query_1 = require("../generated/uexecutor/v1/query");
@@ -33,6 +32,7 @@ class PushClient extends evm_client_1.EvmClient {
33
32
  this.pushChainInfo = chain_1.PUSH_CHAIN_INFO[enums_1.CHAIN.PUSH_LOCALNET];
34
33
  }
35
34
  this.ephemeralKey = (0, accounts_1.generatePrivateKey)();
35
+ this.ephemeralAccount = (0, accounts_1.privateKeyToAccount)(this.ephemeralKey);
36
36
  }
37
37
  /**
38
38
  * Executes an operation with automatic fallback to next RPC endpoint on failure.
@@ -110,10 +110,9 @@ class PushClient extends evm_client_1.EvmClient {
110
110
  }
111
111
  // --- Tx Signer ---
112
112
  getSignerAddress() {
113
- const account = (0, accounts_1.privateKeyToAccount)(this.ephemeralKey);
114
113
  return {
115
- evmAddress: account.address,
116
- cosmosAddress: (0, encoding_1.toBech32)(this.pushChainInfo.prefix, (0, viem_1.hexToBytes)(account.address)),
114
+ evmAddress: this.ephemeralAccount.address,
115
+ cosmosAddress: (0, encoding_1.toBech32)(this.pushChainInfo.prefix, (0, viem_1.hexToBytes)(this.ephemeralAccount.address)),
117
116
  };
118
117
  }
119
118
  /**
@@ -122,10 +121,8 @@ class PushClient extends evm_client_1.EvmClient {
122
121
  */
123
122
  signCosmosTx(txBody) {
124
123
  return tslib_1.__awaiter(this, void 0, void 0, function* () {
125
- const account = (0, accounts_1.privateKeyToAccount)(this.ephemeralKey);
126
- const sender = (0, encoding_1.toBech32)(this.pushChainInfo.prefix, (0, viem_1.hexToBytes)(account.address));
124
+ const sender = (0, encoding_1.toBech32)(this.pushChainInfo.prefix, (0, viem_1.hexToBytes)(this.ephemeralAccount.address));
127
125
  return this.executeWithRpcFallback((rpcUrl) => tslib_1.__awaiter(this, void 0, void 0, function* () {
128
- // 🔍 Get on-chain account info
129
126
  const tmClient = yield tendermint_rpc_1.Tendermint34Client.connect(rpcUrl);
130
127
  const status = yield tmClient.status();
131
128
  const chainId = status.nodeInfo.network;
@@ -136,26 +133,32 @@ class PushClient extends evm_client_1.EvmClient {
136
133
  baseAccount = auth_1.BaseAccount.decode(accountResp.value);
137
134
  }
138
135
  catch (err) {
139
- // Ignore
136
+ // Account may not exist on-chain yet; default to sequence=0 / accountNumber=0
137
+ console.warn(`[PushClient:signCosmosTx] Account lookup failed for ${sender}, defaulting to sequence=0:`, err);
140
138
  }
141
139
  // 📦 Encode pubkey
142
- const uncompressedPubKey = (0, viem_1.hexToBytes)(account.publicKey);
140
+ const uncompressedPubKey = (0, viem_1.hexToBytes)(this.ephemeralAccount.publicKey);
143
141
  const compressedPubKey = crypto_1.Secp256k1.compressPubkey(uncompressedPubKey);
142
+ // Manual protobuf encode: field 1 (tag=10), length-delimited bytes
143
+ const keyLen = compressedPubKey.length;
144
+ const pubkeyValue = new Uint8Array(2 + keyLen);
145
+ pubkeyValue[0] = 10; // field 1, wire type 2 (length-delimited)
146
+ pubkeyValue[1] = keyLen;
147
+ pubkeyValue.set(compressedPubKey, 2);
144
148
  const pubkeyEncoded = {
145
149
  typeUrl: '/cosmos.evm.crypto.v1.ethsecp256k1.PubKey',
146
- value: protobufjs_1.Writer.create().uint32(10).bytes(compressedPubKey).finish(),
150
+ value: pubkeyValue,
147
151
  };
148
152
  const authInfoBytes = (0, proto_signing_1.makeAuthInfoBytes)([
149
153
  {
150
154
  pubkey: pubkeyEncoded,
151
155
  sequence: baseAccount ? Number(baseAccount.sequence) : 0,
152
156
  },
153
- ], [], 100000000000, // gas
154
- undefined, undefined);
157
+ ], [], PushClient.COSMOS_GAS_LIMIT, undefined, undefined);
155
158
  const txBodyBytes = tx_2.TxBody.encode(txBody).finish();
156
159
  const signDoc = (0, proto_signing_1.makeSignDoc)(txBodyBytes, authInfoBytes, chainId, baseAccount ? Number(baseAccount.accountNumber) : 0);
157
160
  const digest = (0, viem_1.keccak256)(tx_2.SignDoc.encode(signDoc).finish());
158
- const signature = yield account.sign({ hash: digest });
161
+ const signature = yield this.ephemeralAccount.sign({ hash: digest });
159
162
  return tx_2.TxRaw.fromPartial({
160
163
  bodyBytes: txBodyBytes,
161
164
  authInfoBytes,
@@ -168,8 +171,7 @@ class PushClient extends evm_client_1.EvmClient {
168
171
  return tslib_1.__awaiter(this, void 0, void 0, function* () {
169
172
  return this.executeWithRpcFallback((rpcUrl) => tslib_1.__awaiter(this, void 0, void 0, function* () {
170
173
  const client = yield stargate_1.StargateClient.connect(rpcUrl);
171
- const result = yield client.broadcastTx(tx_2.TxRaw.encode(txRaw).finish());
172
- return result;
174
+ return client.broadcastTx(tx_2.TxRaw.encode(txRaw).finish());
173
175
  }), 'broadcastCosmosTx');
174
176
  });
175
177
  }
@@ -184,8 +186,7 @@ class PushClient extends evm_client_1.EvmClient {
184
186
  const rpc = (0, stargate_1.createProtobufRpcClient)(queryClient);
185
187
  const request = query_1.QueryGetUniversalTxRequest.fromPartial({ id });
186
188
  const responseBytes = yield rpc.request('uexecutor.v1.Query', 'GetUniversalTx', query_1.QueryGetUniversalTxRequest.encode(request).finish());
187
- const response = query_1.QueryGetUniversalTxResponse.decode(responseBytes);
188
- return response;
189
+ return query_1.QueryGetUniversalTxResponse.decode(responseBytes);
189
190
  }), 'getUniversalTxById');
190
191
  });
191
192
  }
@@ -196,24 +197,12 @@ class PushClient extends evm_client_1.EvmClient {
196
197
  getUniversalTxByIdV2(id) {
197
198
  return tslib_1.__awaiter(this, void 0, void 0, function* () {
198
199
  return this.executeWithRpcFallback((rpcUrl) => tslib_1.__awaiter(this, void 0, void 0, function* () {
199
- var _a, _b, _c;
200
- console.log(`[PushClient:getUniversalTxByIdV2] Querying v2 API | ID: ${id} | RPC: ${rpcUrl}`);
201
- const t0 = Date.now();
202
200
  const tmClient = yield tendermint_rpc_1.Tendermint34Client.connect(rpcUrl);
203
201
  const queryClient = new stargate_1.QueryClient(tmClient);
204
202
  const rpc = (0, stargate_1.createProtobufRpcClient)(queryClient);
205
203
  const request = query_2.QueryGetUniversalTxRequestV2.fromPartial({ id });
206
204
  const responseBytes = yield rpc.request('uexecutor.v2.Query', 'GetUniversalTx', query_2.QueryGetUniversalTxRequestV2.encode(request).finish());
207
- const response = query_2.QueryGetUniversalTxResponseV2.decode(responseBytes);
208
- const utx = response === null || response === void 0 ? void 0 : response.universalTx;
209
- console.log(`[PushClient:getUniversalTxByIdV2] v2 response in ${Date.now() - t0}ms | universalTx exists: ${!!utx} | status: ${utx === null || utx === void 0 ? void 0 : utx.universalStatus} | outboundTx count: ${(_b = (_a = utx === null || utx === void 0 ? void 0 : utx.outboundTx) === null || _a === void 0 ? void 0 : _a.length) !== null && _b !== void 0 ? _b : 0}`);
210
- if ((_c = utx === null || utx === void 0 ? void 0 : utx.outboundTx) === null || _c === void 0 ? void 0 : _c.length) {
211
- utx.outboundTx.forEach((ob, i) => {
212
- var _a;
213
- console.log(`[PushClient:getUniversalTxByIdV2] outbound[${i}]: id=${ob.id} | outboundStatus=${ob.outboundStatus} | observedTx.txHash=${((_a = ob.observedTx) === null || _a === void 0 ? void 0 : _a.txHash) || 'EMPTY'} | dest=${ob.destinationChain} | recipient=${ob.recipient}`);
214
- });
215
- }
216
- return response;
205
+ return query_2.QueryGetUniversalTxResponseV2.decode(responseBytes);
217
206
  }), 'getUniversalTxByIdV2');
218
207
  });
219
208
  }
@@ -227,7 +216,6 @@ class PushClient extends evm_client_1.EvmClient {
227
216
  return tslib_1.__awaiter(this, void 0, void 0, function* () {
228
217
  return this.executeWithRpcFallback((rpcUrl) => tslib_1.__awaiter(this, void 0, void 0, function* () {
229
218
  const client = yield stargate_1.StargateClient.connect(rpcUrl);
230
- // Raw string query—must be one string, not a KV array:
231
219
  const query = `ethereum_tx.ethereumTxHash='${txHash}'`;
232
220
  const results = yield client.searchTx(query);
233
221
  // Convert bigint values to strings in the results. This is done to avoid JSON.stringify()
@@ -243,4 +231,6 @@ class PushClient extends evm_client_1.EvmClient {
243
231
  }
244
232
  }
245
233
  exports.PushClient = PushClient;
234
+ /** Gas limit for Cosmos transactions on Push Chain */
235
+ PushClient.COSMOS_GAS_LIMIT = 100000000000;
246
236
  //# sourceMappingURL=push-client.js.map
@@ -1,5 +1,5 @@
1
- import { CHAIN } from '../../constants/enums';
2
- import { ExecutorAccountInfo, OriginAccountInfo, UniversalAccount } from '../universal.types';
1
+ import { CHAIN, PUSH_NETWORK } from '../../constants/enums';
2
+ import { DerivedExecutorAccount, ExecutorAccountInfo, OriginAccountInfo, ResolvedControllerAccounts, UniversalAccount } from '../universal.types';
3
3
  /**
4
4
  * Creates a `UniversalAccount` object from an address and chain options.
5
5
  * Alternative to createUniversalAccount with a different parameter structure.
@@ -51,28 +51,47 @@ export declare function toChainAgnostic(address: string, options: {
51
51
  * // → { chain: CHAIN.ETHEREUM_SEPOLIA, address: '0xabc...' }
52
52
  */
53
53
  export declare function fromChainAgnostic(caip: string): UniversalAccount;
54
+ /**
55
+ * @deprecated Use `deriveExecutorAccount()` instead, which accepts a CAIP-10
56
+ * string and uses `options.chain` to control UEA vs CEA derivation.
57
+ */
54
58
  export declare function convertOriginToExecutor(account: UniversalAccount, options?: {
55
59
  chain?: CHAIN;
56
60
  onlyCompute?: boolean;
57
61
  }): Promise<ExecutorAccountInfo>;
62
+ export declare function convertExecutorToOriginAccount(ueaAddress: `0x${string}`, options?: {
63
+ network?: PUSH_NETWORK;
64
+ }): Promise<OriginAccountInfo>;
65
+ export declare function convertExecutorToOrigin(executorAddress: string, options?: {
66
+ chain?: CHAIN;
67
+ network?: PUSH_NETWORK;
68
+ /** @internal Skip deprecation warning for SDK-internal calls */
69
+ _internal?: boolean;
70
+ }): Promise<OriginAccountInfo>;
58
71
  /**
59
- * Convert Executor to Origin Account
72
+ * Derive the executor account (UEA or CEA) for a given origin account.
60
73
  *
61
- * Given a UEA (executor) address on Push Chain, returns the mapped origin
62
- * account and an existence flag.
63
- *
64
- * @deprecated Use `convertExecutorToOrigin()` instead, which supports both
65
- * UEA and CEA lookups via the optional `options.chain` parameter.
74
+ * @param account - CAIP-10 formatted address string (e.g., "eip155:11155111:0xABC...")
75
+ * @param options.chain - Target chain for CEA derivation. If omitted, derives UEA on Push Chain.
76
+ * @param options.skipNetworkCheck - If true, skip deployment check and return deployed: false.
77
+ * @returns The derived executor account address and deployment status.
66
78
  */
67
- export declare function convertExecutorToOriginAccount(ueaAddress: `0x${string}`): Promise<OriginAccountInfo>;
79
+ export declare function deriveExecutorAccount(account: string, options?: {
80
+ chain?: CHAIN;
81
+ skipNetworkCheck?: boolean;
82
+ }): Promise<DerivedExecutorAccount>;
68
83
  /**
69
- * Convert Executor to Origin Account (with optional chain context)
84
+ * Resolve the controller (origin) accounts for a given executor address.
85
+ *
86
+ * Given a UEA or CEA address (as CAIP-10), resolves the full controller chain
87
+ * back to the origin account.
70
88
  *
71
- * - Without `chain`: treats the address as a UEA on Push Chain and returns
72
- * the mapped origin account (same as convertExecutorToOriginAccount).
73
- * - With `chain`: treats the address as a CEA on the specified external chain,
74
- * looks up the corresponding PushAccount (UEA) on Push Chain, and returns it.
89
+ * @param account - CAIP-10 formatted address string of the executor account
90
+ * @param options.chain - Supplementary chain context (chain info is in CAIP-10)
91
+ * @param options.skipNetworkCheck - If true, skip existence checks, set exists: false
92
+ * @returns Resolved accounts in the controller chain
75
93
  */
76
- export declare function convertExecutorToOrigin(executorAddress: string, options?: {
94
+ export declare function resolveControllerAccount(account: string, options?: {
77
95
  chain?: CHAIN;
78
- }): Promise<OriginAccountInfo>;
96
+ skipNetworkCheck?: boolean;
97
+ }): Promise<ResolvedControllerAccounts>;