@pushchain/core 5.1.5-alpha.1 → 5.1.6

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 (86) hide show
  1. package/CHANGELOG.md +21 -0
  2. package/package.json +1 -1
  3. package/src/lib/constants/abi/index.d.ts +2 -0
  4. package/src/lib/constants/abi/index.js +6 -1
  5. package/src/lib/constants/abi/uniswap-v3-router.evm.d.ts +58 -0
  6. package/src/lib/constants/abi/uniswap-v3-router.evm.js +41 -0
  7. package/src/lib/constants/abi/wpc.evm.d.ts +24 -0
  8. package/src/lib/constants/abi/wpc.evm.js +27 -0
  9. package/src/lib/constants/chain.d.ts +1 -0
  10. package/src/lib/constants/chain.js +8 -6
  11. package/src/lib/constants/tokens.js +3 -3
  12. package/src/lib/generated/uexecutor/v2/types.d.ts +14 -0
  13. package/src/lib/generated/uexecutor/v2/types.js +96 -3
  14. package/src/lib/orchestrator/internals/cascade.d.ts +1 -1
  15. package/src/lib/orchestrator/internals/cascade.js +521 -239
  16. package/src/lib/orchestrator/internals/confirmation.js +60 -15
  17. package/src/lib/orchestrator/internals/context.d.ts +23 -0
  18. package/src/lib/orchestrator/internals/context.js +58 -0
  19. package/src/lib/orchestrator/internals/execute-funds-only.js +47 -21
  20. package/src/lib/orchestrator/internals/execute-funds-payload.js +70 -37
  21. package/src/lib/orchestrator/internals/execute-standard.js +137 -26
  22. package/src/lib/orchestrator/internals/gas-calculator.d.ts +5 -2
  23. package/src/lib/orchestrator/internals/gas-calculator.js +59 -11
  24. package/src/lib/orchestrator/internals/gas-usd-sizer.d.ts +53 -0
  25. package/src/lib/orchestrator/internals/gas-usd-sizer.js +165 -0
  26. package/src/lib/orchestrator/internals/helpers.js +2 -0
  27. package/src/lib/orchestrator/internals/inbound-tracker.d.ts +83 -0
  28. package/src/lib/orchestrator/internals/inbound-tracker.js +322 -0
  29. package/src/lib/orchestrator/internals/index.d.ts +3 -1
  30. package/src/lib/orchestrator/internals/index.js +8 -2
  31. package/src/lib/orchestrator/internals/outbound-sync.d.ts +32 -1
  32. package/src/lib/orchestrator/internals/outbound-sync.js +154 -17
  33. package/src/lib/orchestrator/internals/pc-usd-oracle.d.ts +28 -0
  34. package/src/lib/orchestrator/internals/pc-usd-oracle.js +285 -0
  35. package/src/lib/orchestrator/internals/progress-route-hooks.d.ts +23 -0
  36. package/src/lib/orchestrator/internals/progress-route-hooks.js +72 -0
  37. package/src/lib/orchestrator/internals/push-chain-tx.d.ts +27 -1
  38. package/src/lib/orchestrator/internals/push-chain-tx.js +111 -15
  39. package/src/lib/orchestrator/internals/rescue.js +1 -1
  40. package/src/lib/orchestrator/internals/response-builder.d.ts +5 -0
  41. package/src/lib/orchestrator/internals/response-builder.js +242 -66
  42. package/src/lib/orchestrator/internals/route-handlers.js +480 -206
  43. package/src/lib/orchestrator/internals/tx-transformer.js +293 -35
  44. package/src/lib/orchestrator/orchestrator.d.ts +7 -1
  45. package/src/lib/orchestrator/orchestrator.js +108 -56
  46. package/src/lib/orchestrator/orchestrator.types.d.ts +111 -5
  47. package/src/lib/orchestrator/payload-builders.d.ts +16 -0
  48. package/src/lib/orchestrator/payload-builders.js +6 -5
  49. package/src/lib/orchestrator/route-detector.js +20 -8
  50. package/src/lib/orchestrator/svm-idl/normalize-address.d.ts +19 -0
  51. package/src/lib/orchestrator/svm-idl/normalize-address.js +56 -0
  52. package/src/lib/orchestrator/svm-idl/registry.d.ts +13 -4
  53. package/src/lib/orchestrator/svm-idl/registry.js +15 -14
  54. package/src/lib/orchestrator/svm-idl/resolve.js +5 -2
  55. package/src/lib/progress-hook/progress-hook.d.ts +28 -0
  56. package/src/lib/progress-hook/progress-hook.js +552 -133
  57. package/src/lib/progress-hook/progress-hook.types.d.ts +77 -29
  58. package/src/lib/progress-hook/progress-hook.types.js +75 -35
  59. package/src/lib/push-client/push-client.d.ts +7 -0
  60. package/src/lib/push-client/push-client.js +18 -1
  61. package/src/lib/universal-tx-detector/__tests__/fixtures/builders.d.ts +32 -0
  62. package/src/lib/universal-tx-detector/__tests__/fixtures/builders.js +65 -0
  63. package/src/lib/universal-tx-detector/__tests__/fixtures/scenarios.d.ts +72 -0
  64. package/src/lib/universal-tx-detector/__tests__/fixtures/scenarios.js +669 -0
  65. package/src/lib/universal-tx-detector/auto-detect.d.ts +37 -0
  66. package/src/lib/universal-tx-detector/auto-detect.js +112 -0
  67. package/src/lib/universal-tx-detector/cascade.d.ts +64 -0
  68. package/src/lib/universal-tx-detector/cascade.js +254 -0
  69. package/src/lib/universal-tx-detector/child-inbounds.d.ts +58 -0
  70. package/src/lib/universal-tx-detector/child-inbounds.js +145 -0
  71. package/src/lib/universal-tx-detector/classify.d.ts +33 -0
  72. package/src/lib/universal-tx-detector/classify.js +228 -0
  73. package/src/lib/universal-tx-detector/detector-svm.d.ts +46 -0
  74. package/src/lib/universal-tx-detector/detector-svm.js +324 -0
  75. package/src/lib/universal-tx-detector/detector.d.ts +13 -0
  76. package/src/lib/universal-tx-detector/detector.js +233 -0
  77. package/src/lib/universal-tx-detector/events.d.ts +765 -0
  78. package/src/lib/universal-tx-detector/events.js +241 -0
  79. package/src/lib/universal-tx-detector/index.d.ts +18 -0
  80. package/src/lib/universal-tx-detector/index.js +36 -0
  81. package/src/lib/universal-tx-detector/svm-events.d.ts +41 -0
  82. package/src/lib/universal-tx-detector/svm-events.js +68 -0
  83. package/src/lib/universal-tx-detector/types.d.ts +100 -0
  84. package/src/lib/universal-tx-detector/types.js +3 -0
  85. package/src/lib/utils.d.ts +30 -13
  86. package/src/lib/utils.js +47 -21
@@ -0,0 +1,233 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.computeUniversalTxId = exports.__internalStatusNames = void 0;
4
+ exports.detectUniversalTx = detectUniversalTx;
5
+ const tslib_1 = require("tslib");
6
+ /**
7
+ * detectUniversalTx — given a source-chain tx hash + chain, fetch the receipt,
8
+ * decode all universal-tx events, classify the tx, and (optionally) cross-
9
+ * reference the corresponding universalTx on Push Chain via cosmos.
10
+ *
11
+ * Read-only. No signer required. No Push block-explorer dependency.
12
+ *
13
+ * Dispatches on CHAIN_INFO[chain].vm — EVM uses viem's parseEventLogs below,
14
+ * SVM delegates to detector-svm.ts which decodes Anchor program-data logs
15
+ * with the gateway IDL. Both branches return an identical UniversalTxDetection
16
+ * shape so downstream consumers (classify, cascade, child-inbounds,
17
+ * inbound-tracker) are VM-agnostic.
18
+ */
19
+ const viem_1 = require("viem");
20
+ const chain_1 = require("../constants/chain");
21
+ const enums_1 = require("../constants/enums");
22
+ const outbound_tracker_1 = require("../orchestrator/internals/outbound-tracker");
23
+ Object.defineProperty(exports, "computeUniversalTxId", { enumerable: true, get: function () { return outbound_tracker_1.computeUniversalTxId; } });
24
+ const events_1 = require("./events");
25
+ const classify_1 = require("./classify");
26
+ const child_inbounds_1 = require("./child-inbounds");
27
+ const detector_svm_1 = require("./detector-svm");
28
+ // ── Status name table (copied from scripts/poll-outbound.ts:33-44) ────
29
+ const UNIVERSAL_TX_STATUS_NAMES = {
30
+ 0: 'UNIVERSAL_TX_STATUS_UNSPECIFIED',
31
+ 1: 'INBOUND_SUCCESS',
32
+ 2: 'PENDING_INBOUND_EXECUTION',
33
+ 3: 'PC_EXECUTED_SUCCESS',
34
+ 4: 'PC_EXECUTED_FAILED',
35
+ 5: 'PC_PENDING_REVERT',
36
+ 6: 'OUTBOUND_PENDING',
37
+ 7: 'OUTBOUND_SUCCESS',
38
+ 8: 'OUTBOUND_FAILED',
39
+ 9: 'CANCELED',
40
+ };
41
+ const INBOUND_KINDS = new Set([
42
+ 'INBOUND_FROM_EOA',
43
+ 'INBOUND_FROM_CEA',
44
+ ]);
45
+ function detectUniversalTx(txHash_1, chain_2) {
46
+ return tslib_1.__awaiter(this, arguments, void 0, function* (txHash, chain, opts = {}) {
47
+ var _a;
48
+ const notes = [];
49
+ const chainInfo = chain_1.CHAIN_INFO[chain];
50
+ if (!chainInfo) {
51
+ throw new Error(`detectUniversalTx: unknown chain ${chain}`);
52
+ }
53
+ if (chainInfo.vm === enums_1.VM.SVM) {
54
+ return (0, detector_svm_1.detectUniversalTxSvm)(txHash, chain, opts);
55
+ }
56
+ if (chainInfo.vm !== enums_1.VM.EVM) {
57
+ throw new Error(`detectUniversalTx: unsupported vm=${chainInfo.vm} for ${chain}`);
58
+ }
59
+ const rpcUrls = ((_a = opts.rpcUrls) === null || _a === void 0 ? void 0 : _a[chain]) && opts.rpcUrls[chain].length > 0
60
+ ? opts.rpcUrls[chain]
61
+ : chainInfo.defaultRPC.filter((r) => r && r.length > 0);
62
+ if (rpcUrls.length === 0) {
63
+ throw new Error(`detectUniversalTx: no RPC URL configured for chain ${chain}`);
64
+ }
65
+ const publicClient = (0, viem_1.createPublicClient)({
66
+ transport: (0, viem_1.fallback)(rpcUrls.map((url) => (0, viem_1.http)(url))),
67
+ });
68
+ let receipt;
69
+ try {
70
+ receipt = yield publicClient.getTransactionReceipt({ hash: txHash });
71
+ }
72
+ catch (err) {
73
+ // viem throws if the tx isn't found yet; treat as no-receipt.
74
+ notes.push(`receipt fetch failed: ${err instanceof Error ? err.message : String(err)}`);
75
+ return emptyDetection(txHash, chain, notes);
76
+ }
77
+ if (!receipt) {
78
+ notes.push('no receipt returned by RPC');
79
+ return emptyDetection(txHash, chain, notes);
80
+ }
81
+ if (receipt.status === 'reverted' && receipt.logs.length === 0) {
82
+ notes.push('tx reverted with no logs');
83
+ return emptyDetection(txHash, chain, notes);
84
+ }
85
+ const parsed = (0, viem_1.parseEventLogs)({
86
+ abi: events_1.UNIVERSAL_TX_EVENT_ABI,
87
+ logs: receipt.logs,
88
+ strict: false,
89
+ });
90
+ const matchingLogs = parsed.map((p) => {
91
+ var _a, _b;
92
+ return ({
93
+ eventName: p.eventName,
94
+ address: p.address,
95
+ logIndex: typeof p.logIndex ===
96
+ 'bigint'
97
+ ? Number(p.logIndex)
98
+ : (_a = p.logIndex) !== null && _a !== void 0 ? _a : -1,
99
+ args: ((_b = p.args) !== null && _b !== void 0 ? _b : {}),
100
+ });
101
+ });
102
+ const classified = (0, classify_1.classify)(matchingLogs);
103
+ notes.push(...classified.notes);
104
+ const decoded = Object.assign({}, classified.decoded);
105
+ // Deterministic universalTxId derivation for primary kinds whose event
106
+ // doesn't carry it. Formulas from push-chain/x/uexecutor/types/keys.go:
107
+ // - Inbound (any external-chain UniversalTx log):
108
+ // sha256(`<caip>:<txHash>:<logIndex>`) — GetInboundUniversalTxKey:49
109
+ // - Push-initiated outbound (UniversalTxOutbound on Push Chain):
110
+ // sha256(`<caip>:<txHash>`) — GetPcUniversalTxKey:63
111
+ if (!decoded.universalTxId) {
112
+ const caip = chain; // CHAIN enum values are CAIP-2 strings.
113
+ if (INBOUND_KINDS.has(classified.kind) &&
114
+ classified.primaryLog &&
115
+ classified.primaryLog.logIndex >= 0) {
116
+ decoded.universalTxId = (0, child_inbounds_1.deriveChildUniversalTxId)(caip, txHash, classified.primaryLog.logIndex);
117
+ notes.push(`universalTxId derived via sha256("${caip}:<txHash>:${classified.primaryLog.logIndex}")`);
118
+ }
119
+ else if (classified.kind === 'OUTBOUND_INITIATED') {
120
+ decoded.universalTxId = (0, child_inbounds_1.derivePcUniversalTxId)(caip, txHash);
121
+ notes.push(`universalTxId derived via sha256("${caip}:<txHash>") — pc outbound`);
122
+ }
123
+ }
124
+ // Optional cosmos cross-reference.
125
+ let pushChainTx;
126
+ if (opts.pushClient &&
127
+ !opts.skipPushChainLookup &&
128
+ decoded.universalTxId) {
129
+ pushChainTx = yield crossReferencePushChain(opts.pushClient, decoded.universalTxId, classified.kind, notes);
130
+ }
131
+ else if (decoded.universalTxId && !opts.pushClient) {
132
+ notes.push('push cross-reference skipped (no pushClient provided)');
133
+ }
134
+ const detections = (0, classify_1.classifyAll)(classified.matchingLogs);
135
+ return {
136
+ txHash,
137
+ chain,
138
+ kind: classified.kind,
139
+ emitters: classified.emitters,
140
+ decoded,
141
+ matchingLogs: classified.matchingLogs,
142
+ detections,
143
+ pushChainTx,
144
+ notes,
145
+ };
146
+ });
147
+ }
148
+ // ── Helpers ───────────────────────────────────────────────────────────
149
+ function emptyDetection(txHash, chain, notes) {
150
+ return {
151
+ txHash,
152
+ chain,
153
+ kind: 'UNKNOWN',
154
+ emitters: [],
155
+ decoded: {},
156
+ matchingLogs: [],
157
+ detections: [],
158
+ notes,
159
+ };
160
+ }
161
+ function crossReferencePushChain(pushClient, universalTxId, kind, notes) {
162
+ return tslib_1.__awaiter(this, void 0, void 0, function* () {
163
+ var _a, _b, _c, _d;
164
+ const id = universalTxId.startsWith('0x')
165
+ ? universalTxId.slice(2)
166
+ : universalTxId;
167
+ try {
168
+ const resp = yield pushClient.getUniversalTxByIdV2(id);
169
+ const utx = resp === null || resp === void 0 ? void 0 : resp.universalTx;
170
+ if (!utx || !utx.id) {
171
+ return {
172
+ id,
173
+ status: 0,
174
+ statusName: UNIVERSAL_TX_STATUS_NAMES[0],
175
+ pcTxHashes: [],
176
+ outboundHashes: [],
177
+ notFound: true,
178
+ };
179
+ }
180
+ const status = ((_a = utx.universalStatus) !== null && _a !== void 0 ? _a : 0);
181
+ const statusName = (_b = UNIVERSAL_TX_STATUS_NAMES[status]) !== null && _b !== void 0 ? _b : `UNKNOWN(${status})`;
182
+ const pcTxHashes = ((_c = utx.pcTx) !== null && _c !== void 0 ? _c : [])
183
+ .map((p) => p === null || p === void 0 ? void 0 : p.txHash)
184
+ .filter((h) => Boolean(h));
185
+ const outboundHashes = ((_d = utx.outboundTx) !== null && _d !== void 0 ? _d : []).map((ob) => {
186
+ var _a, _b, _c;
187
+ return ({
188
+ subTxId: (_a = ob.id) !== null && _a !== void 0 ? _a : '',
189
+ status: outboundStatusName(ob.outboundStatus),
190
+ destinationChain: (_b = ob.destinationChain) !== null && _b !== void 0 ? _b : '',
191
+ externalTxHash: ((_c = ob.observedTx) === null || _c === void 0 ? void 0 : _c.txHash) || undefined,
192
+ amount: ob.amount,
193
+ recipient: ob.recipient,
194
+ });
195
+ });
196
+ let stuckObservation;
197
+ if (INBOUND_KINDS.has(kind)) {
198
+ if (status === 0)
199
+ stuckObservation = 'UNSPECIFIED';
200
+ else if (status === 2 && outboundHashes.length === 0)
201
+ stuckObservation = 'PENDING_INBOUND_ONLY';
202
+ }
203
+ return {
204
+ id,
205
+ status,
206
+ statusName,
207
+ pcTxHashes,
208
+ outboundHashes,
209
+ stuckObservation,
210
+ };
211
+ }
212
+ catch (err) {
213
+ notes.push(`push cross-reference failed: ${err instanceof Error ? err.message : String(err)}`);
214
+ return undefined;
215
+ }
216
+ });
217
+ }
218
+ function outboundStatusName(n) {
219
+ switch (n) {
220
+ case 0:
221
+ return 'OUTBOUND_STATUS_UNSPECIFIED';
222
+ case 1:
223
+ return 'PENDING';
224
+ case 2:
225
+ return 'OBSERVED';
226
+ case 3:
227
+ return 'REVERTED';
228
+ default:
229
+ return `UNKNOWN(${n !== null && n !== void 0 ? n : '?'})`;
230
+ }
231
+ }
232
+ exports.__internalStatusNames = UNIVERSAL_TX_STATUS_NAMES;
233
+ //# sourceMappingURL=detector.js.map