@trustware/sdk-staging 1.1.10-staging.0 → 1.1.11-staging.2
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.
- package/README.md +54 -21
- package/dist/constants.cjs +1 -1
- package/dist/constants.mjs +1 -1
- package/dist/{core-BPLiD1UG.d.ts → core-B1WCJfDI.d.ts} +15 -2
- package/dist/{core-B7Ez-5-r.d.cts → core-CeNTuqPz.d.cts} +15 -2
- package/dist/core.cjs +365 -279
- package/dist/core.cjs.map +1 -1
- package/dist/core.d.cts +2 -2
- package/dist/core.d.ts +2 -2
- package/dist/core.mjs +363 -278
- package/dist/core.mjs.map +1 -1
- package/dist/index.cjs +375 -170
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +11 -5
- package/dist/index.d.ts +11 -5
- package/dist/index.mjs +373 -169
- package/dist/index.mjs.map +1 -1
- package/dist/{manager-B6NNV-E_.d.ts → manager-Bw8b1wSD.d.ts} +136 -21
- package/dist/{manager-BwjyFjjz.d.cts → manager-DNGk1YkR.d.cts} +136 -21
- package/dist/{metadata-BiTMMvlY.d.ts → metadata-C__KMeuz.d.ts} +1 -1
- package/dist/{metadata-HCflXcsF.d.cts → metadata-Dk4R8_-T.d.cts} +1 -1
- package/dist/smart-account.cjs +49 -44
- package/dist/smart-account.cjs.map +1 -1
- package/dist/smart-account.d.cts +17 -12
- package/dist/smart-account.d.ts +17 -12
- package/dist/smart-account.mjs +49 -44
- package/dist/smart-account.mjs.map +1 -1
- package/dist/wallet.cjs +54 -39
- package/dist/wallet.cjs.map +1 -1
- package/dist/wallet.d.cts +3 -3
- package/dist/wallet.d.ts +3 -3
- package/dist/wallet.mjs +54 -39
- package/dist/wallet.mjs.map +1 -1
- package/dist/widget.cjs +369 -170
- package/dist/widget.cjs.map +1 -1
- package/dist/widget.mjs +369 -169
- package/dist/widget.mjs.map +1 -1
- package/package.json +73 -5
package/dist/widget.mjs
CHANGED
|
@@ -535,16 +535,14 @@ var init_defaults = __esm({
|
|
|
535
535
|
});
|
|
536
536
|
|
|
537
537
|
// src/types/config.ts
|
|
538
|
-
var DEFAULT_RETRY_CONFIG, DEFAULT_FEATURE_FLAGS;
|
|
538
|
+
var DEFAULT_RETRY_CONFIG, RATE_LIMIT_WAIT_BUDGET_MS, DEFAULT_FEATURE_FLAGS;
|
|
539
539
|
var init_config = __esm({
|
|
540
540
|
"src/types/config.ts"() {
|
|
541
541
|
"use strict";
|
|
542
542
|
DEFAULT_RETRY_CONFIG = {
|
|
543
|
-
autoRetry: true,
|
|
544
|
-
maxRetries: 3,
|
|
545
|
-
baseDelayMs: 1e3,
|
|
546
543
|
approachingThreshold: 5
|
|
547
544
|
};
|
|
545
|
+
RATE_LIMIT_WAIT_BUDGET_MS = 1e4;
|
|
548
546
|
DEFAULT_FEATURE_FLAGS = {
|
|
549
547
|
tokensPagination: true,
|
|
550
548
|
balanceStreaming: false,
|
|
@@ -563,7 +561,7 @@ var init_constants = __esm({
|
|
|
563
561
|
"src/constants.ts"() {
|
|
564
562
|
"use strict";
|
|
565
563
|
SDK_NAME = "@trustware/sdk";
|
|
566
|
-
SDK_VERSION = "1.1.
|
|
564
|
+
SDK_VERSION = "1.1.11-staging.2";
|
|
567
565
|
API_ROOT = "https://bv-staging-api.trustware.io";
|
|
568
566
|
GTM_ID = "GTM-TZDGNCXB";
|
|
569
567
|
API_PREFIX = "/api";
|
|
@@ -607,6 +605,9 @@ async function assertOK(r) {
|
|
|
607
605
|
}
|
|
608
606
|
throw new Error(`HTTP ${r.status}: ${msg}`);
|
|
609
607
|
}
|
|
608
|
+
function isNotFoundError(err) {
|
|
609
|
+
return err instanceof Error && err.message.startsWith("HTTP 404");
|
|
610
|
+
}
|
|
610
611
|
async function validateSdkAccess() {
|
|
611
612
|
const r = await fetch(`${apiBase()}/sdk/validate`, {
|
|
612
613
|
method: "GET",
|
|
@@ -647,60 +648,66 @@ function notifyRateLimitCallbacks(info, isRateLimited, retryCount) {
|
|
|
647
648
|
retry.onRateLimitApproaching(info, retry.approachingThreshold);
|
|
648
649
|
}
|
|
649
650
|
}
|
|
650
|
-
function
|
|
651
|
-
if (
|
|
652
|
-
|
|
651
|
+
function serverDirectedWaitMs(info) {
|
|
652
|
+
if (!info) return null;
|
|
653
|
+
if (typeof info.retryAfter === "number" && info.retryAfter > 0) {
|
|
654
|
+
return info.retryAfter * 1e3;
|
|
655
|
+
}
|
|
656
|
+
if (typeof info.reset === "number" && info.reset > 0) {
|
|
657
|
+
const untilReset = info.reset * 1e3 - Date.now();
|
|
658
|
+
if (untilReset > 0) return untilReset;
|
|
653
659
|
}
|
|
654
|
-
return
|
|
660
|
+
return null;
|
|
655
661
|
}
|
|
656
662
|
function sleep(ms) {
|
|
657
663
|
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
658
664
|
}
|
|
659
|
-
async function
|
|
660
|
-
|
|
661
|
-
const cfg = TrustwareConfigStore.get();
|
|
662
|
-
if (!cfg.retry.autoRetry || skipRateLimit) {
|
|
663
|
-
return fetch(url, fetchOptions);
|
|
664
|
-
}
|
|
665
|
-
const { maxRetries, baseDelayMs } = cfg.retry;
|
|
665
|
+
async function withRateLimitRetry(attempt) {
|
|
666
|
+
let waitedMs = 0;
|
|
666
667
|
let retryCount = 0;
|
|
667
668
|
while (true) {
|
|
668
|
-
const response = await
|
|
669
|
+
const response = await attempt();
|
|
669
670
|
const rateLimitInfo = parseRateLimitHeaders(response);
|
|
670
|
-
if (response.status
|
|
671
|
+
if (response.status !== 429) {
|
|
671
672
|
if (rateLimitInfo) {
|
|
672
|
-
notifyRateLimitCallbacks(rateLimitInfo,
|
|
673
|
+
notifyRateLimitCallbacks(rateLimitInfo, false, 0);
|
|
673
674
|
}
|
|
674
|
-
|
|
675
|
-
throw new RateLimitError(
|
|
676
|
-
rateLimitInfo || { limit: 0, remaining: 0, reset: 0 },
|
|
677
|
-
true
|
|
678
|
-
);
|
|
679
|
-
}
|
|
680
|
-
const delay = calculateBackoffDelay(
|
|
681
|
-
baseDelayMs,
|
|
682
|
-
retryCount,
|
|
683
|
-
rateLimitInfo?.retryAfter
|
|
684
|
-
);
|
|
685
|
-
await sleep(delay);
|
|
686
|
-
retryCount++;
|
|
687
|
-
continue;
|
|
675
|
+
return response;
|
|
688
676
|
}
|
|
689
677
|
if (rateLimitInfo) {
|
|
690
|
-
notifyRateLimitCallbacks(rateLimitInfo,
|
|
678
|
+
notifyRateLimitCallbacks(rateLimitInfo, true, retryCount);
|
|
691
679
|
}
|
|
692
|
-
|
|
680
|
+
const waitMs = serverDirectedWaitMs(rateLimitInfo);
|
|
681
|
+
const info = rateLimitInfo || { limit: 0, remaining: 0, reset: 0 };
|
|
682
|
+
if (waitMs === null) {
|
|
683
|
+
throw new RateLimitError(info, true);
|
|
684
|
+
}
|
|
685
|
+
if (waitedMs + waitMs > RATE_LIMIT_WAIT_BUDGET_MS) {
|
|
686
|
+
throw new RateLimitError(info, false);
|
|
687
|
+
}
|
|
688
|
+
await sleep(waitMs);
|
|
689
|
+
waitedMs += waitMs;
|
|
690
|
+
retryCount++;
|
|
693
691
|
}
|
|
694
692
|
}
|
|
693
|
+
async function rateLimitedFetch(url, options = {}) {
|
|
694
|
+
const { skipRateLimit, ...fetchOptions } = options;
|
|
695
|
+
if (skipRateLimit) {
|
|
696
|
+
return fetch(url, fetchOptions);
|
|
697
|
+
}
|
|
698
|
+
return withRateLimitRetry(() => fetch(url, fetchOptions));
|
|
699
|
+
}
|
|
695
700
|
var RateLimitError;
|
|
696
701
|
var init_http = __esm({
|
|
697
702
|
"src/core/http.ts"() {
|
|
698
703
|
"use strict";
|
|
699
704
|
init_constants();
|
|
700
705
|
init_config2();
|
|
706
|
+
init_config();
|
|
701
707
|
RateLimitError = class extends Error {
|
|
702
708
|
constructor(info, retriesExhausted) {
|
|
703
|
-
const
|
|
709
|
+
const seconds = info.retryAfter ?? (info.reset > 0 ? Math.max(0, Math.ceil((info.reset * 1e3 - Date.now()) / 1e3)) : null);
|
|
710
|
+
const message = seconds === null ? "Rate limit exceeded. The server did not say when to retry." : `Rate limit exceeded. Try again in ${seconds} seconds.`;
|
|
704
711
|
super(message);
|
|
705
712
|
this.name = "RateLimitError";
|
|
706
713
|
this.rateLimitInfo = info;
|
|
@@ -2357,7 +2364,7 @@ async function getBalances(chainRef, address, opts) {
|
|
|
2357
2364
|
if (cached) return cached;
|
|
2358
2365
|
}
|
|
2359
2366
|
const url = `${apiBase()}/v1/data/wallets/${encodeURIComponent(chainKey)}/${trimmedAddress}/balances`;
|
|
2360
|
-
const response = await
|
|
2367
|
+
const response = await rateLimitedFetch(url, {
|
|
2361
2368
|
method: "GET",
|
|
2362
2369
|
credentials: "omit",
|
|
2363
2370
|
headers: jsonHeaders()
|
|
@@ -2579,6 +2586,19 @@ async function submitReceipt(intentId, txHash, sponsorshipRequestId, eoaAddress)
|
|
|
2579
2586
|
const j = await r.json();
|
|
2580
2587
|
return j.data;
|
|
2581
2588
|
}
|
|
2589
|
+
async function submitStepReceipt(intentId, stepIndex, txHash) {
|
|
2590
|
+
const r = await rateLimitedFetch(
|
|
2591
|
+
`${apiBase()}/v1/route-intent/${intentId}/steps/${stepIndex}/receipt`,
|
|
2592
|
+
{
|
|
2593
|
+
method: "POST",
|
|
2594
|
+
headers: jsonHeaders({ "Idempotency-Key": txHash }),
|
|
2595
|
+
body: JSON.stringify({ txHash })
|
|
2596
|
+
}
|
|
2597
|
+
);
|
|
2598
|
+
await assertOK(r);
|
|
2599
|
+
const j = await r.json();
|
|
2600
|
+
return j.data;
|
|
2601
|
+
}
|
|
2582
2602
|
async function getStatus(intentId) {
|
|
2583
2603
|
const r = await rateLimitedFetch(
|
|
2584
2604
|
`${apiBase()}/v1/route-intent/${intentId}/status`,
|
|
@@ -2588,7 +2608,18 @@ async function getStatus(intentId) {
|
|
|
2588
2608
|
);
|
|
2589
2609
|
await assertOK(r);
|
|
2590
2610
|
const j = await r.json();
|
|
2591
|
-
return j.data;
|
|
2611
|
+
return normalizeStatusPayload(j.data);
|
|
2612
|
+
}
|
|
2613
|
+
function normalizeStatusPayload(raw) {
|
|
2614
|
+
if (!raw || typeof raw !== "object") return raw;
|
|
2615
|
+
const wire = raw;
|
|
2616
|
+
const out = { ...wire };
|
|
2617
|
+
for (const [snake, camel] of Object.entries(STATUS_WIRE_TO_CAMEL)) {
|
|
2618
|
+
if (out[camel] !== void 0) continue;
|
|
2619
|
+
if (!(snake in wire)) continue;
|
|
2620
|
+
out[camel] = wire[snake];
|
|
2621
|
+
}
|
|
2622
|
+
return out;
|
|
2592
2623
|
}
|
|
2593
2624
|
async function pollStatus(intentId, { intervalMs = 2e3, timeoutMs = 5 * 6e4 } = {}) {
|
|
2594
2625
|
const t0 = Date.now();
|
|
@@ -2599,12 +2630,39 @@ async function pollStatus(intentId, { intervalMs = 2e3, timeoutMs = 5 * 6e4 } =
|
|
|
2599
2630
|
await new Promise((r) => setTimeout(r, intervalMs));
|
|
2600
2631
|
}
|
|
2601
2632
|
}
|
|
2633
|
+
var STATUS_WIRE_TO_CAMEL;
|
|
2602
2634
|
var init_routes = __esm({
|
|
2603
2635
|
"src/core/routes.ts"() {
|
|
2604
2636
|
"use strict";
|
|
2605
2637
|
init_http();
|
|
2606
2638
|
init_store();
|
|
2607
2639
|
init_address();
|
|
2640
|
+
STATUS_WIRE_TO_CAMEL = {
|
|
2641
|
+
intent_id: "intentId",
|
|
2642
|
+
from_address: "fromAddress",
|
|
2643
|
+
to_address: "toAddress",
|
|
2644
|
+
from_chain_id: "fromChainId",
|
|
2645
|
+
to_chain_id: "toChainId",
|
|
2646
|
+
source_tx_hash: "sourceTxHash",
|
|
2647
|
+
dest_tx_hash: "destTxHash",
|
|
2648
|
+
request_id: "requestId",
|
|
2649
|
+
provider_request_id: "providerRequestId",
|
|
2650
|
+
transaction_request: "transactionRequest",
|
|
2651
|
+
status_raw: "statusRaw",
|
|
2652
|
+
route_path: "routePath",
|
|
2653
|
+
route_status: "routeStatus",
|
|
2654
|
+
to_amount_wei: "toAmountWei",
|
|
2655
|
+
from_chain_block: "fromChainBlock",
|
|
2656
|
+
to_chain_block: "toChainBlock",
|
|
2657
|
+
from_chain_tx_url: "fromChainTxUrl",
|
|
2658
|
+
to_chain_tx_url: "toChainTxUrl",
|
|
2659
|
+
gas_status: "gasStatus",
|
|
2660
|
+
is_gmp_transaction: "isGMPTransaction",
|
|
2661
|
+
axelar_transaction_url: "axelarTransactionUrl",
|
|
2662
|
+
create_date: "createdDate",
|
|
2663
|
+
update_date: "updatedDate",
|
|
2664
|
+
time_spent_ms: "timeSpentMs"
|
|
2665
|
+
};
|
|
2608
2666
|
}
|
|
2609
2667
|
});
|
|
2610
2668
|
|
|
@@ -2895,12 +2953,9 @@ function useTrustwareConfig() {
|
|
|
2895
2953
|
title: "Trustware SDK",
|
|
2896
2954
|
description: "Seamlessly bridge assets across chains with Trustware."
|
|
2897
2955
|
},
|
|
2898
|
-
|
|
2899
|
-
|
|
2900
|
-
|
|
2901
|
-
baseDelayMs: 1e3,
|
|
2902
|
-
approachingThreshold: 5
|
|
2903
|
-
},
|
|
2956
|
+
// Shared with the resolver rather than restated, so this placeholder
|
|
2957
|
+
// can't drift from the real defaults.
|
|
2958
|
+
retry: { ...DEFAULT_RETRY_CONFIG },
|
|
2904
2959
|
features: {
|
|
2905
2960
|
tokensPagination: true,
|
|
2906
2961
|
balanceStreaming: false,
|
|
@@ -2925,6 +2980,7 @@ var init_useTrustwareConfig = __esm({
|
|
|
2925
2980
|
"src/hooks/useTrustwareConfig.ts"() {
|
|
2926
2981
|
"use strict";
|
|
2927
2982
|
"use client";
|
|
2983
|
+
init_config();
|
|
2928
2984
|
init_store();
|
|
2929
2985
|
}
|
|
2930
2986
|
});
|
|
@@ -5300,75 +5356,17 @@ var init_useTransactionSubmit = __esm({
|
|
|
5300
5356
|
|
|
5301
5357
|
// src/hooks/useGTM.ts
|
|
5302
5358
|
import { useEffect as useEffect5, useRef as useRef2, useCallback as useCallback2 } from "react";
|
|
5303
|
-
function
|
|
5304
|
-
|
|
5305
|
-
|
|
5306
|
-
|
|
5307
|
-
|
|
5308
|
-
|
|
5309
|
-
|
|
5310
|
-
|
|
5311
|
-
}
|
|
5312
|
-
}, []);
|
|
5313
|
-
useEffect5(() => {
|
|
5314
|
-
if (!isGA4Allowed()) {
|
|
5315
|
-
console.warn(
|
|
5316
|
-
"useGTM: GA4 tracking is disabled or Trustware config not initialized."
|
|
5317
|
-
);
|
|
5318
|
-
return;
|
|
5319
|
-
}
|
|
5320
|
-
if (!gtmId || typeof gtmId !== "string") {
|
|
5321
|
-
console.error(
|
|
5322
|
-
"useGTM: A valid GTM Container ID is required (format: GTM-XXXXX)."
|
|
5323
|
-
);
|
|
5324
|
-
return;
|
|
5325
|
-
}
|
|
5326
|
-
if (isInitialized.current) return;
|
|
5327
|
-
const alreadyLoaded = document.querySelector(
|
|
5328
|
-
`script[src*="googletagmanager.com/gtm.js?id=${gtmId}"]`
|
|
5329
|
-
);
|
|
5330
|
-
if (alreadyLoaded) {
|
|
5331
|
-
window.dataLayer = window.dataLayer || [];
|
|
5332
|
-
isInitialized.current = true;
|
|
5333
|
-
return;
|
|
5334
|
-
}
|
|
5335
|
-
window.dataLayer = window.dataLayer || [];
|
|
5336
|
-
window.dataLayer.push({
|
|
5337
|
-
"gtm.start": (/* @__PURE__ */ new Date()).getTime(),
|
|
5338
|
-
event: "gtm.js"
|
|
5339
|
-
});
|
|
5340
|
-
const firstScript = document.getElementsByTagName("script")[0];
|
|
5341
|
-
const script = document.createElement("script");
|
|
5342
|
-
script.async = true;
|
|
5343
|
-
script.src = `https://www.googletagmanager.com/gtm.js?id=${gtmId}`;
|
|
5344
|
-
firstScript.parentNode?.insertBefore(script, firstScript);
|
|
5345
|
-
scriptRef.current = script;
|
|
5346
|
-
isInitialized.current = true;
|
|
5347
|
-
return () => {
|
|
5348
|
-
if (scriptRef.current) {
|
|
5349
|
-
scriptRef.current.parentNode?.removeChild(scriptRef.current);
|
|
5350
|
-
scriptRef.current = null;
|
|
5351
|
-
}
|
|
5352
|
-
isInitialized.current = false;
|
|
5353
|
-
};
|
|
5354
|
-
}, [gtmId, isGA4Allowed]);
|
|
5355
|
-
const addNoscriptIframe = useCallback2(() => {
|
|
5356
|
-
if (!isGA4Allowed()) return;
|
|
5357
|
-
if (document.querySelector('iframe[src*="googletagmanager.com/ns.html"]'))
|
|
5358
|
-
return;
|
|
5359
|
-
const noscript = document.createElement("noscript");
|
|
5360
|
-
const iframe = document.createElement("iframe");
|
|
5361
|
-
iframe.src = `https://www.googletagmanager.com/ns.html?id=${gtmId}`;
|
|
5362
|
-
iframe.height = "0";
|
|
5363
|
-
iframe.width = "0";
|
|
5364
|
-
iframe.style.display = "none";
|
|
5365
|
-
iframe.style.visibility = "hidden";
|
|
5366
|
-
noscript.appendChild(iframe);
|
|
5367
|
-
document.body.insertBefore(noscript, document.body.firstChild);
|
|
5368
|
-
}, [gtmId, isGA4Allowed]);
|
|
5359
|
+
function isGA4Allowed() {
|
|
5360
|
+
try {
|
|
5361
|
+
return Trustware.getConfig().features.shouldAllowGA4;
|
|
5362
|
+
} catch {
|
|
5363
|
+
return false;
|
|
5364
|
+
}
|
|
5365
|
+
}
|
|
5366
|
+
function useGTMTracker() {
|
|
5369
5367
|
const trackEvent = useCallback2(
|
|
5370
5368
|
(eventName, eventParams = {}) => {
|
|
5371
|
-
if (!
|
|
5369
|
+
if (!isContainerInitialized) {
|
|
5372
5370
|
console.warn(
|
|
5373
5371
|
"useGTM: Not initialized. Ensure a valid GTM Container ID was provided."
|
|
5374
5372
|
);
|
|
@@ -5395,7 +5393,7 @@ function useGTM(gtmId) {
|
|
|
5395
5393
|
);
|
|
5396
5394
|
const setUserProperty = useCallback2(
|
|
5397
5395
|
(propertyName, value) => {
|
|
5398
|
-
if (!
|
|
5396
|
+
if (!isContainerInitialized) {
|
|
5399
5397
|
console.warn(
|
|
5400
5398
|
"useGTM: Not initialized. Ensure a valid GTM Container ID was provided."
|
|
5401
5399
|
);
|
|
@@ -5421,20 +5419,77 @@ function useGTM(gtmId) {
|
|
|
5421
5419
|
}
|
|
5422
5420
|
window.gtag(command, ...args);
|
|
5423
5421
|
},
|
|
5424
|
-
[
|
|
5422
|
+
[]
|
|
5425
5423
|
);
|
|
5426
|
-
return {
|
|
5427
|
-
|
|
5428
|
-
|
|
5429
|
-
|
|
5430
|
-
|
|
5431
|
-
|
|
5432
|
-
|
|
5424
|
+
return { trackEvent, trackPageView, setUserProperty, directGtag };
|
|
5425
|
+
}
|
|
5426
|
+
function useGTM(gtmId) {
|
|
5427
|
+
const scriptRef = useRef2(null);
|
|
5428
|
+
const tracker = useGTMTracker();
|
|
5429
|
+
useEffect5(() => {
|
|
5430
|
+
if (!isGA4Allowed()) {
|
|
5431
|
+
console.warn(
|
|
5432
|
+
"useGTM: GA4 tracking is disabled or Trustware config not initialized."
|
|
5433
|
+
);
|
|
5434
|
+
return;
|
|
5435
|
+
}
|
|
5436
|
+
if (!gtmId || typeof gtmId !== "string") {
|
|
5437
|
+
console.error(
|
|
5438
|
+
"useGTM: A valid GTM Container ID is required (format: GTM-XXXXX)."
|
|
5439
|
+
);
|
|
5440
|
+
return;
|
|
5441
|
+
}
|
|
5442
|
+
if (isContainerInitialized) return;
|
|
5443
|
+
const alreadyLoaded = document.querySelector(
|
|
5444
|
+
`script[src*="googletagmanager.com/gtm.js?id=${gtmId}"]`
|
|
5445
|
+
);
|
|
5446
|
+
if (alreadyLoaded) {
|
|
5447
|
+
window.dataLayer = window.dataLayer || [];
|
|
5448
|
+
isContainerInitialized = true;
|
|
5449
|
+
return;
|
|
5450
|
+
}
|
|
5451
|
+
window.dataLayer = window.dataLayer || [];
|
|
5452
|
+
window.dataLayer.push({
|
|
5453
|
+
"gtm.start": (/* @__PURE__ */ new Date()).getTime(),
|
|
5454
|
+
event: "gtm.js"
|
|
5455
|
+
});
|
|
5456
|
+
const firstScript = document.getElementsByTagName("script")[0];
|
|
5457
|
+
const script = document.createElement("script");
|
|
5458
|
+
script.async = true;
|
|
5459
|
+
script.src = `https://www.googletagmanager.com/gtm.js?id=${gtmId}`;
|
|
5460
|
+
firstScript.parentNode?.insertBefore(script, firstScript);
|
|
5461
|
+
scriptRef.current = script;
|
|
5462
|
+
isContainerInitialized = true;
|
|
5463
|
+
return () => {
|
|
5464
|
+
if (scriptRef.current) {
|
|
5465
|
+
scriptRef.current.parentNode?.removeChild(scriptRef.current);
|
|
5466
|
+
scriptRef.current = null;
|
|
5467
|
+
}
|
|
5468
|
+
isContainerInitialized = false;
|
|
5469
|
+
};
|
|
5470
|
+
}, [gtmId]);
|
|
5471
|
+
const addNoscriptIframe = useCallback2(() => {
|
|
5472
|
+
if (!isGA4Allowed()) return;
|
|
5473
|
+
if (document.querySelector('iframe[src*="googletagmanager.com/ns.html"]'))
|
|
5474
|
+
return;
|
|
5475
|
+
const noscript = document.createElement("noscript");
|
|
5476
|
+
const iframe = document.createElement("iframe");
|
|
5477
|
+
iframe.src = `https://www.googletagmanager.com/ns.html?id=${gtmId}`;
|
|
5478
|
+
iframe.height = "0";
|
|
5479
|
+
iframe.width = "0";
|
|
5480
|
+
iframe.style.display = "none";
|
|
5481
|
+
iframe.style.visibility = "hidden";
|
|
5482
|
+
noscript.appendChild(iframe);
|
|
5483
|
+
document.body.insertBefore(noscript, document.body.firstChild);
|
|
5484
|
+
}, [gtmId]);
|
|
5485
|
+
return { ...tracker, addNoscriptIframe };
|
|
5433
5486
|
}
|
|
5487
|
+
var isContainerInitialized;
|
|
5434
5488
|
var init_useGTM = __esm({
|
|
5435
5489
|
"src/hooks/useGTM.ts"() {
|
|
5436
5490
|
"use strict";
|
|
5437
5491
|
init_core2();
|
|
5492
|
+
isContainerInitialized = false;
|
|
5438
5493
|
}
|
|
5439
5494
|
});
|
|
5440
5495
|
|
|
@@ -5461,7 +5516,7 @@ function useTransactionPolling() {
|
|
|
5461
5516
|
return void 0;
|
|
5462
5517
|
}
|
|
5463
5518
|
})();
|
|
5464
|
-
const { trackEvent } =
|
|
5519
|
+
const { trackEvent } = useGTMTracker();
|
|
5465
5520
|
const [state, setState] = useState6({
|
|
5466
5521
|
isPolling: false,
|
|
5467
5522
|
apiStatus: null,
|
|
@@ -5561,8 +5616,21 @@ function useTransactionPolling() {
|
|
|
5561
5616
|
pollCountRef.current += 1;
|
|
5562
5617
|
const pollInterval = pollCountRef.current <= 10 ? FAST_POLL_INTERVAL_MS : NORMAL_POLL_INTERVAL_MS;
|
|
5563
5618
|
pollingRef.current = setTimeout(poll, pollInterval);
|
|
5564
|
-
} catch {
|
|
5619
|
+
} catch (err) {
|
|
5565
5620
|
if (abortRef.current) return;
|
|
5621
|
+
if (isNotFoundError(err)) {
|
|
5622
|
+
clearPolling();
|
|
5623
|
+
const notFoundError = "Transaction session expired. Please try again.";
|
|
5624
|
+
setState((prev) => ({
|
|
5625
|
+
...prev,
|
|
5626
|
+
isPolling: false,
|
|
5627
|
+
error: notFoundError
|
|
5628
|
+
}));
|
|
5629
|
+
setErrorMessage(notFoundError);
|
|
5630
|
+
setTransactionStatus("error");
|
|
5631
|
+
setCurrentStep("error");
|
|
5632
|
+
return;
|
|
5633
|
+
}
|
|
5566
5634
|
const elapsed = Date.now() - startTimeRef.current;
|
|
5567
5635
|
if (elapsed > POLL_TIMEOUT_MS) {
|
|
5568
5636
|
clearPolling();
|
|
@@ -5698,10 +5766,10 @@ var init_useTransactionPolling = __esm({
|
|
|
5698
5766
|
"use strict";
|
|
5699
5767
|
"use client";
|
|
5700
5768
|
init_routes();
|
|
5769
|
+
init_http();
|
|
5701
5770
|
init_DepositContext();
|
|
5702
5771
|
init_provider();
|
|
5703
5772
|
init_core2();
|
|
5704
|
-
init_constants();
|
|
5705
5773
|
init_hooks();
|
|
5706
5774
|
FAST_POLL_INTERVAL_MS = 1500;
|
|
5707
5775
|
NORMAL_POLL_INTERVAL_MS = 2500;
|
|
@@ -5783,6 +5851,20 @@ var init_eipWallets = __esm({
|
|
|
5783
5851
|
"src/wallets/eipWallets.ts"() {
|
|
5784
5852
|
"use strict";
|
|
5785
5853
|
CHAIN_PARAMS = {
|
|
5854
|
+
1: {
|
|
5855
|
+
chainIdHex: "0x1",
|
|
5856
|
+
chainName: "Ethereum",
|
|
5857
|
+
rpcUrls: ["https://eth.llamarpc.com"],
|
|
5858
|
+
nativeCurrency: { name: "Ether", symbol: "ETH", decimals: 18 },
|
|
5859
|
+
blockExplorerUrls: ["https://etherscan.io"]
|
|
5860
|
+
},
|
|
5861
|
+
137: {
|
|
5862
|
+
chainIdHex: "0x89",
|
|
5863
|
+
chainName: "Polygon",
|
|
5864
|
+
rpcUrls: ["https://polygon-rpc.com"],
|
|
5865
|
+
nativeCurrency: { name: "POL", symbol: "POL", decimals: 18 },
|
|
5866
|
+
blockExplorerUrls: ["https://polygonscan.com"]
|
|
5867
|
+
},
|
|
5786
5868
|
8453: {
|
|
5787
5869
|
chainIdHex: "0x2105",
|
|
5788
5870
|
chainName: "Base",
|
|
@@ -8887,9 +8969,6 @@ function resolveConfig(input) {
|
|
|
8887
8969
|
const theme = input.theme ?? "system";
|
|
8888
8970
|
const messages = deepMerge(DEFAULT_MESSAGES, input.messages);
|
|
8889
8971
|
const retry = {
|
|
8890
|
-
autoRetry: input.retry?.autoRetry ?? DEFAULT_RETRY_CONFIG.autoRetry,
|
|
8891
|
-
maxRetries: input.retry?.maxRetries ?? DEFAULT_RETRY_CONFIG.maxRetries,
|
|
8892
|
-
baseDelayMs: input.retry?.baseDelayMs ?? DEFAULT_RETRY_CONFIG.baseDelayMs,
|
|
8893
8972
|
approachingThreshold: input.retry?.approachingThreshold ?? DEFAULT_RETRY_CONFIG.approachingThreshold,
|
|
8894
8973
|
onRateLimitInfo: input.retry?.onRateLimitInfo,
|
|
8895
8974
|
onRateLimited: input.retry?.onRateLimited,
|
|
@@ -9063,18 +9142,27 @@ async function waitForTxConfirmation(chainId, txHash) {
|
|
|
9063
9142
|
}
|
|
9064
9143
|
throw new Error("Timed out waiting for approval confirmation");
|
|
9065
9144
|
}
|
|
9066
|
-
|
|
9145
|
+
function requiredApprovalAmount(planAmountWei, routeAmountWei) {
|
|
9146
|
+
if (planAmountWei >= UNLIMITED_APPROVAL_FLOOR && routeAmountWei !== void 0 && routeAmountWei > 0n) {
|
|
9147
|
+
return routeAmountWei;
|
|
9148
|
+
}
|
|
9149
|
+
return planAmountWei;
|
|
9150
|
+
}
|
|
9151
|
+
function approvalSatisfied(currentAllowance, requiredWei) {
|
|
9152
|
+
if (requiredWei === 0n) return currentAllowance === 0n;
|
|
9153
|
+
return currentAllowance >= requiredWei;
|
|
9154
|
+
}
|
|
9155
|
+
async function ensureApprovals(w, approvals, fallbackChainId, intentId, routeAmountWei) {
|
|
9067
9156
|
if (!approvals || approvals.length === 0) return;
|
|
9068
9157
|
const owner = await w.getAddress();
|
|
9069
|
-
for (const approval of approvals) {
|
|
9158
|
+
for (const [stepIndex, approval] of approvals.entries()) {
|
|
9070
9159
|
const spender = approval.spender;
|
|
9071
9160
|
const tokenAddress = approval.tokenAddress;
|
|
9072
9161
|
const amount = approval.amount;
|
|
9073
9162
|
if (!spender || !tokenAddress || !amount) continue;
|
|
9074
9163
|
const chainId = approval.chainId || String(fallbackChainId ?? "");
|
|
9075
9164
|
if (!chainId) continue;
|
|
9076
|
-
const amountWei = BigInt(amount);
|
|
9077
|
-
if (amountWei === 0n) continue;
|
|
9165
|
+
const amountWei = requiredApprovalAmount(BigInt(amount), routeAmountWei);
|
|
9078
9166
|
let currentAllowance = 0n;
|
|
9079
9167
|
try {
|
|
9080
9168
|
const { allowance } = await getEVMAllowance({
|
|
@@ -9086,7 +9174,7 @@ async function ensureApprovals(w, approvals, fallbackChainId) {
|
|
|
9086
9174
|
currentAllowance = BigInt(allowance || "0");
|
|
9087
9175
|
} catch {
|
|
9088
9176
|
}
|
|
9089
|
-
if (currentAllowance
|
|
9177
|
+
if (approvalSatisfied(currentAllowance, amountWei)) continue;
|
|
9090
9178
|
const data = encodeFunctionData({
|
|
9091
9179
|
abi: erc20ApproveAbi,
|
|
9092
9180
|
functionName: "approve",
|
|
@@ -9098,6 +9186,10 @@ async function ensureApprovals(w, approvals, fallbackChainId) {
|
|
|
9098
9186
|
value: 0n,
|
|
9099
9187
|
chainId: Number.isFinite(Number(chainId)) ? Number(chainId) : void 0
|
|
9100
9188
|
});
|
|
9189
|
+
if (intentId) {
|
|
9190
|
+
void submitStepReceipt(intentId, stepIndex, hash).catch(() => {
|
|
9191
|
+
});
|
|
9192
|
+
}
|
|
9101
9193
|
await waitForTxConfirmation(chainId, hash);
|
|
9102
9194
|
}
|
|
9103
9195
|
}
|
|
@@ -9107,7 +9199,7 @@ function isUserRejected(e2) {
|
|
|
9107
9199
|
const msg = String(e2?.message || e2)?.toLowerCase?.() || "";
|
|
9108
9200
|
return msg.includes("user rejected") || msg.includes("user denied");
|
|
9109
9201
|
}
|
|
9110
|
-
async function sendRouteTransaction(b, fallbackChainId) {
|
|
9202
|
+
async function sendRouteTransaction(b, fallbackChainId, options) {
|
|
9111
9203
|
const w = walletManager.wallet;
|
|
9112
9204
|
if (!w) throw new Error("Trustware.wallet not configured");
|
|
9113
9205
|
const txReq = b.txReq;
|
|
@@ -9134,11 +9226,13 @@ async function sendRouteTransaction(b, fallbackChainId) {
|
|
|
9134
9226
|
}
|
|
9135
9227
|
}
|
|
9136
9228
|
}
|
|
9137
|
-
if (!validatedSponsorship) {
|
|
9229
|
+
if (!validatedSponsorship && !options?.approvalsEnsured) {
|
|
9138
9230
|
await ensureApprovals(
|
|
9139
9231
|
w,
|
|
9140
9232
|
b.route?.execution?.approvals,
|
|
9141
|
-
Number.isFinite(target) ? target : void 0
|
|
9233
|
+
Number.isFinite(target) ? target : void 0,
|
|
9234
|
+
b.intentId,
|
|
9235
|
+
BigInt(b.route?.estimate?.fromAmount ?? "0")
|
|
9142
9236
|
);
|
|
9143
9237
|
}
|
|
9144
9238
|
if (w.type === "eip1193") {
|
|
@@ -9237,7 +9331,7 @@ async function runTopUp(params) {
|
|
|
9237
9331
|
}
|
|
9238
9332
|
}
|
|
9239
9333
|
}
|
|
9240
|
-
var erc20ApproveAbi;
|
|
9334
|
+
var erc20ApproveAbi, UNLIMITED_APPROVAL_FLOOR;
|
|
9241
9335
|
var init_tx = __esm({
|
|
9242
9336
|
"src/core/tx.ts"() {
|
|
9243
9337
|
"use strict";
|
|
@@ -9247,6 +9341,7 @@ var init_tx = __esm({
|
|
|
9247
9341
|
erc20ApproveAbi = parseAbi([
|
|
9248
9342
|
"function approve(address spender, uint256 amount) returns (bool)"
|
|
9249
9343
|
]);
|
|
9344
|
+
UNLIMITED_APPROVAL_FLOOR = 1n << 255n;
|
|
9250
9345
|
}
|
|
9251
9346
|
});
|
|
9252
9347
|
|
|
@@ -9392,6 +9487,7 @@ var init_core = __esm({
|
|
|
9392
9487
|
buildRoute,
|
|
9393
9488
|
buildDepositAddress,
|
|
9394
9489
|
submitReceipt,
|
|
9490
|
+
submitStepReceipt,
|
|
9395
9491
|
getStatus,
|
|
9396
9492
|
pollStatus,
|
|
9397
9493
|
getBalances,
|
|
@@ -30548,7 +30644,7 @@ import {
|
|
|
30548
30644
|
keccak256 as keccak2566,
|
|
30549
30645
|
stringToHex
|
|
30550
30646
|
} from "viem";
|
|
30551
|
-
async function
|
|
30647
|
+
async function fetchOnceWithTimeout(url, init) {
|
|
30552
30648
|
const controller = new AbortController();
|
|
30553
30649
|
const timer = setTimeout(() => controller.abort(), FETCH_TIMEOUT_MS);
|
|
30554
30650
|
try {
|
|
@@ -30569,6 +30665,9 @@ async function fetchWithTimeout(url, init) {
|
|
|
30569
30665
|
clearTimeout(timer);
|
|
30570
30666
|
}
|
|
30571
30667
|
}
|
|
30668
|
+
async function fetchWithTimeout(url, init) {
|
|
30669
|
+
return withRateLimitRetry(() => fetchOnceWithTimeout(url, init));
|
|
30670
|
+
}
|
|
30572
30671
|
function extractRevertHex(err) {
|
|
30573
30672
|
if (typeof err.data === "string" && err.data.startsWith("0x"))
|
|
30574
30673
|
return err.data;
|
|
@@ -31068,7 +31167,7 @@ async function estimateRelayFeeInToken(valueWei, fromAmountWei, fromAmountUSD, c
|
|
|
31068
31167
|
tokenUnitsPerDollar = Number(fromAmountWei) / fromUSD;
|
|
31069
31168
|
} else if (fromToken && fromDecimals !== void 0) {
|
|
31070
31169
|
try {
|
|
31071
|
-
const resp = await
|
|
31170
|
+
const resp = await rateLimitedFetch(
|
|
31072
31171
|
`${apiBase()}/v1/price/token?chainId=${cid}&address=${fromToken}`,
|
|
31073
31172
|
{ headers: jsonHeaders() }
|
|
31074
31173
|
);
|
|
@@ -31084,9 +31183,10 @@ async function estimateRelayFeeInToken(valueWei, fromAmountWei, fromAmountUSD, c
|
|
|
31084
31183
|
return 0n;
|
|
31085
31184
|
}
|
|
31086
31185
|
try {
|
|
31087
|
-
const resp = await
|
|
31088
|
-
|
|
31089
|
-
|
|
31186
|
+
const resp = await rateLimitedFetch(
|
|
31187
|
+
`${apiBase()}/v1/price/native?chainId=${cid}`,
|
|
31188
|
+
{ headers: jsonHeaders() }
|
|
31189
|
+
);
|
|
31090
31190
|
if (!resp.ok) throw new Error(`native price HTTP ${resp.status}`);
|
|
31091
31191
|
const json = await resp.json();
|
|
31092
31192
|
const ethPriceUSD = parseFloat(json.data?.priceUSD ?? "0");
|
|
@@ -31594,7 +31694,7 @@ function useTransactionActionModel({
|
|
|
31594
31694
|
}) {
|
|
31595
31695
|
const feeDataCacheRef = useRef13({});
|
|
31596
31696
|
const { isSubmitting, submitTransaction } = useTransactionSubmit();
|
|
31597
|
-
const { trackEvent } =
|
|
31697
|
+
const { trackEvent } = useGTMTracker();
|
|
31598
31698
|
const destinationConfig = (() => {
|
|
31599
31699
|
try {
|
|
31600
31700
|
return Trustware.getConfig();
|
|
@@ -32027,7 +32127,6 @@ var init_useTransactionActionModel = __esm({
|
|
|
32027
32127
|
init_chainHelpers();
|
|
32028
32128
|
init_utils2();
|
|
32029
32129
|
init_hooks();
|
|
32030
|
-
init_constants();
|
|
32031
32130
|
}
|
|
32032
32131
|
});
|
|
32033
32132
|
|
|
@@ -33379,6 +33478,16 @@ async function waitForApprovalConfirmation(chainId, txHash) {
|
|
|
33379
33478
|
}
|
|
33380
33479
|
throw new Error("Timed out waiting for approval confirmation");
|
|
33381
33480
|
}
|
|
33481
|
+
async function requireActiveAddress(wallet, plannedFor) {
|
|
33482
|
+
if (!wallet) throw new Error("Wallet not connected. Please reconnect.");
|
|
33483
|
+
const active = await wallet.getAddress();
|
|
33484
|
+
if (active?.toLowerCase() !== plannedFor?.toLowerCase()) {
|
|
33485
|
+
throw new Error(
|
|
33486
|
+
"Wallet account changed. Please review and confirm the swap again."
|
|
33487
|
+
);
|
|
33488
|
+
}
|
|
33489
|
+
return active;
|
|
33490
|
+
}
|
|
33382
33491
|
function useSwapExecution(fromChain) {
|
|
33383
33492
|
const [state, setState] = useState29({
|
|
33384
33493
|
txStatus: "idle",
|
|
@@ -33435,7 +33544,15 @@ function useSwapExecution(fromChain) {
|
|
|
33435
33544
|
if (tx.status === "bridging") {
|
|
33436
33545
|
setState((p) => ({ ...p, txStatus: "bridging" }));
|
|
33437
33546
|
}
|
|
33438
|
-
} catch {
|
|
33547
|
+
} catch (err) {
|
|
33548
|
+
if (abortRef.current) return;
|
|
33549
|
+
if (isNotFoundError(err)) {
|
|
33550
|
+
clearPolling();
|
|
33551
|
+
const msg = "Transaction session expired. Please try again.";
|
|
33552
|
+
setState((p) => ({ ...p, txStatus: "error", errorMessage: msg }));
|
|
33553
|
+
onError(msg);
|
|
33554
|
+
return;
|
|
33555
|
+
}
|
|
33439
33556
|
}
|
|
33440
33557
|
if (abortRef.current) return;
|
|
33441
33558
|
pollCountRef.current += 1;
|
|
@@ -33461,24 +33578,55 @@ function useSwapExecution(fromChain) {
|
|
|
33461
33578
|
}
|
|
33462
33579
|
const txReq = routeResult.txReq;
|
|
33463
33580
|
const chainIdStr = String(txReq?.chainId ?? fromChain?.chainId ?? "");
|
|
33464
|
-
const spender = txReq?.to ?? txReq?.target;
|
|
33465
33581
|
const amountWei = BigInt(routeResult.route?.estimate?.fromAmount ?? "0");
|
|
33466
|
-
|
|
33582
|
+
const plannedApprovals = routeResult.route?.execution?.approvals ?? [];
|
|
33583
|
+
const toCheck = plannedApprovals.length ? plannedApprovals.flatMap((a) => {
|
|
33584
|
+
const token = a.tokenAddress ?? fromTokenAddress;
|
|
33585
|
+
const required = requiredApprovalAmount(
|
|
33586
|
+
BigInt(a.amount || "0"),
|
|
33587
|
+
amountWei
|
|
33588
|
+
);
|
|
33589
|
+
if (!token || !a.spender) return [];
|
|
33590
|
+
return [
|
|
33591
|
+
{
|
|
33592
|
+
chainId: a.chainId || chainIdStr,
|
|
33593
|
+
token,
|
|
33594
|
+
spender: a.spender,
|
|
33595
|
+
required
|
|
33596
|
+
}
|
|
33597
|
+
];
|
|
33598
|
+
}) : (() => {
|
|
33599
|
+
const spender = txReq?.to ?? txReq?.target;
|
|
33600
|
+
if (!spender) return [];
|
|
33601
|
+
return [
|
|
33602
|
+
{
|
|
33603
|
+
chainId: chainIdStr,
|
|
33604
|
+
token: fromTokenAddress,
|
|
33605
|
+
spender,
|
|
33606
|
+
required: amountWei
|
|
33607
|
+
}
|
|
33608
|
+
];
|
|
33609
|
+
})();
|
|
33610
|
+
if (toCheck.length === 0 || !chainIdStr || amountWei === 0n) {
|
|
33467
33611
|
setState((p) => ({ ...p, allowanceStatus: "unknown" }));
|
|
33468
33612
|
return;
|
|
33469
33613
|
}
|
|
33470
33614
|
setState((p) => ({ ...p, allowanceStatus: "checking" }));
|
|
33471
33615
|
try {
|
|
33472
|
-
const
|
|
33473
|
-
|
|
33474
|
-
|
|
33475
|
-
|
|
33476
|
-
|
|
33477
|
-
|
|
33478
|
-
|
|
33616
|
+
const results = await Promise.all(
|
|
33617
|
+
toCheck.map(async (c) => {
|
|
33618
|
+
const { allowance } = await getEVMAllowance({
|
|
33619
|
+
chainId: c.chainId,
|
|
33620
|
+
tokenAddress: c.token,
|
|
33621
|
+
ownerAddress: walletAddress,
|
|
33622
|
+
spenderAddress: c.spender
|
|
33623
|
+
});
|
|
33624
|
+
return approvalSatisfied(BigInt(allowance || "0"), c.required);
|
|
33625
|
+
})
|
|
33626
|
+
);
|
|
33479
33627
|
setState((p) => ({
|
|
33480
33628
|
...p,
|
|
33481
|
-
allowanceStatus:
|
|
33629
|
+
allowanceStatus: results.every(Boolean) ? "sufficient" : "needed"
|
|
33482
33630
|
}));
|
|
33483
33631
|
} catch {
|
|
33484
33632
|
setState((p) => ({ ...p, allowanceStatus: "needed" }));
|
|
@@ -33582,19 +33730,49 @@ function useSwapExecution(fromChain) {
|
|
|
33582
33730
|
}
|
|
33583
33731
|
}
|
|
33584
33732
|
try {
|
|
33585
|
-
|
|
33733
|
+
const plannedApprovals = routeResult.route?.execution?.approvals ?? [];
|
|
33734
|
+
const requiredApprovals = plannedApprovals.length ? plannedApprovals.flatMap((a, index) => {
|
|
33735
|
+
const token = a.tokenAddress ?? fromTokenAddress;
|
|
33736
|
+
const approvalSpender = a.spender;
|
|
33737
|
+
if (!token || !approvalSpender) return [];
|
|
33738
|
+
const amountWei = requiredApprovalAmount(
|
|
33739
|
+
BigInt(a.amount || "0"),
|
|
33740
|
+
fromAmountWei
|
|
33741
|
+
);
|
|
33742
|
+
return [
|
|
33743
|
+
{
|
|
33744
|
+
stepIndex: index,
|
|
33745
|
+
token,
|
|
33746
|
+
spender: approvalSpender,
|
|
33747
|
+
amountWei,
|
|
33748
|
+
chainId: a.chainId || chainIdStr
|
|
33749
|
+
}
|
|
33750
|
+
];
|
|
33751
|
+
}) : spender && fromTokenAddress ? [
|
|
33752
|
+
{
|
|
33753
|
+
stepIndex: null,
|
|
33754
|
+
token: fromTokenAddress,
|
|
33755
|
+
spender,
|
|
33756
|
+
amountWei: fromAmountWei,
|
|
33757
|
+
chainId: chainIdStr
|
|
33758
|
+
}
|
|
33759
|
+
] : [];
|
|
33760
|
+
const ownsApprovals = !isNative && !!walletAddress && !!chainIdStr;
|
|
33761
|
+
const activeAddress = ownsApprovals ? await requireActiveAddress(wallet, walletAddress) : void 0;
|
|
33762
|
+
for (const required of requiredApprovals) {
|
|
33763
|
+
if (!ownsApprovals) break;
|
|
33586
33764
|
let allowanceWei = 0n;
|
|
33587
33765
|
try {
|
|
33588
33766
|
const { allowance } = await getEVMAllowance({
|
|
33589
|
-
chainId:
|
|
33590
|
-
tokenAddress:
|
|
33591
|
-
ownerAddress:
|
|
33592
|
-
spenderAddress: spender
|
|
33767
|
+
chainId: required.chainId,
|
|
33768
|
+
tokenAddress: required.token,
|
|
33769
|
+
ownerAddress: activeAddress,
|
|
33770
|
+
spenderAddress: required.spender
|
|
33593
33771
|
});
|
|
33594
33772
|
allowanceWei = BigInt(allowance || "0");
|
|
33595
33773
|
} catch {
|
|
33596
33774
|
}
|
|
33597
|
-
if (allowanceWei
|
|
33775
|
+
if (!approvalSatisfied(allowanceWei, required.amountWei)) {
|
|
33598
33776
|
setState((p) => ({ ...p, txStatus: "approving" }));
|
|
33599
33777
|
if (!wallet || wallet.ecosystem !== "evm") {
|
|
33600
33778
|
throw new Error("EVM wallet required for token approval");
|
|
@@ -33602,7 +33780,7 @@ function useSwapExecution(fromChain) {
|
|
|
33602
33780
|
if (!chainIdStr || chainIdStr === "0") {
|
|
33603
33781
|
throw new Error("Invalid chain ID for token approval");
|
|
33604
33782
|
}
|
|
33605
|
-
const targetChain = Number(
|
|
33783
|
+
const targetChain = Number(required.chainId ?? txReq.chainId);
|
|
33606
33784
|
if (Number.isFinite(targetChain)) {
|
|
33607
33785
|
const current = await wallet.getChainId();
|
|
33608
33786
|
if (current !== targetChain) {
|
|
@@ -33614,18 +33792,18 @@ function useSwapExecution(fromChain) {
|
|
|
33614
33792
|
}
|
|
33615
33793
|
const approveAmount = maxApproval ? BigInt(
|
|
33616
33794
|
"0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"
|
|
33617
|
-
) :
|
|
33795
|
+
) : required.amountWei;
|
|
33618
33796
|
const data = encodeFunctionData10({
|
|
33619
33797
|
abi: erc20Abi2,
|
|
33620
33798
|
functionName: "approve",
|
|
33621
|
-
args: [spender, approveAmount]
|
|
33799
|
+
args: [required.spender, approveAmount]
|
|
33622
33800
|
});
|
|
33623
33801
|
let approvalHash;
|
|
33624
33802
|
if (wallet.type === "eip1193") {
|
|
33625
33803
|
const from = await wallet.getAddress();
|
|
33626
33804
|
const params = {
|
|
33627
33805
|
from,
|
|
33628
|
-
to:
|
|
33806
|
+
to: required.token,
|
|
33629
33807
|
data,
|
|
33630
33808
|
value: "0x0"
|
|
33631
33809
|
};
|
|
@@ -33638,14 +33816,22 @@ function useSwapExecution(fromChain) {
|
|
|
33638
33816
|
});
|
|
33639
33817
|
} else {
|
|
33640
33818
|
const response = await wallet.sendTransaction({
|
|
33641
|
-
to:
|
|
33819
|
+
to: required.token,
|
|
33642
33820
|
data,
|
|
33643
33821
|
value: 0n,
|
|
33644
33822
|
chainId: Number.isFinite(targetChain) ? targetChain : void 0
|
|
33645
33823
|
});
|
|
33646
33824
|
approvalHash = response.hash;
|
|
33647
33825
|
}
|
|
33648
|
-
|
|
33826
|
+
if (required.stepIndex !== null) {
|
|
33827
|
+
void submitStepReceipt(
|
|
33828
|
+
routeResult.intentId,
|
|
33829
|
+
required.stepIndex,
|
|
33830
|
+
approvalHash
|
|
33831
|
+
).catch(() => {
|
|
33832
|
+
});
|
|
33833
|
+
}
|
|
33834
|
+
await waitForApprovalConfirmation(required.chainId, approvalHash);
|
|
33649
33835
|
setState((p) => ({
|
|
33650
33836
|
...p,
|
|
33651
33837
|
txStatus: "confirming",
|
|
@@ -33653,9 +33839,13 @@ function useSwapExecution(fromChain) {
|
|
|
33653
33839
|
}));
|
|
33654
33840
|
}
|
|
33655
33841
|
}
|
|
33842
|
+
if (ownsApprovals) {
|
|
33843
|
+
await requireActiveAddress(wallet, walletAddress);
|
|
33844
|
+
}
|
|
33656
33845
|
const hash = await Trustware.sendRouteTransaction(
|
|
33657
33846
|
routeResult,
|
|
33658
|
-
numericChainId
|
|
33847
|
+
numericChainId,
|
|
33848
|
+
{ approvalsEnsured: ownsApprovals }
|
|
33659
33849
|
);
|
|
33660
33850
|
try {
|
|
33661
33851
|
await submitReceipt(routeResult.intentId, hash);
|
|
@@ -33723,6 +33913,8 @@ var init_useSwapExecution = __esm({
|
|
|
33723
33913
|
"use client";
|
|
33724
33914
|
init_core2();
|
|
33725
33915
|
init_routes();
|
|
33916
|
+
init_http();
|
|
33917
|
+
init_tx();
|
|
33726
33918
|
init_sdkRpc();
|
|
33727
33919
|
init_chainHelpers();
|
|
33728
33920
|
FAST_POLL_MS = 1500;
|
|
@@ -33734,9 +33926,14 @@ var init_useSwapExecution = __esm({
|
|
|
33734
33926
|
|
|
33735
33927
|
// src/core/forex.ts
|
|
33736
33928
|
async function fetchForexRates(base2 = "USD") {
|
|
33737
|
-
|
|
33738
|
-
|
|
33739
|
-
|
|
33929
|
+
let r;
|
|
33930
|
+
try {
|
|
33931
|
+
r = await rateLimitedFetch(`${apiBase()}/v1/forex?base=${base2}`, {
|
|
33932
|
+
headers: jsonHeaders()
|
|
33933
|
+
});
|
|
33934
|
+
} catch {
|
|
33935
|
+
return {};
|
|
33936
|
+
}
|
|
33740
33937
|
if (!r.ok) return {};
|
|
33741
33938
|
const j = await r.json();
|
|
33742
33939
|
const rates = j?.data?.rates ?? j?.rates ?? j?.data ?? {};
|
|
@@ -39687,6 +39884,7 @@ function WidgetInner({
|
|
|
39687
39884
|
const { resolvedTheme } = useDepositUi();
|
|
39688
39885
|
const { status, revalidate, errors } = useTrustware();
|
|
39689
39886
|
const [showConfirmDialog, setShowConfirmDialog] = useState35(false);
|
|
39887
|
+
useGTM(GTM_ID);
|
|
39690
39888
|
const handleCloseRequest = useCallback23(() => {
|
|
39691
39889
|
if (ACTIVE_TRANSACTION_STATUSES.includes(transactionStatus)) {
|
|
39692
39890
|
setShowConfirmDialog(true);
|
|
@@ -39760,6 +39958,8 @@ var init_TrustwareWidgetV2 = __esm({
|
|
|
39760
39958
|
init_provider();
|
|
39761
39959
|
init_manager();
|
|
39762
39960
|
init_useTrustwareConfig();
|
|
39961
|
+
init_hooks();
|
|
39962
|
+
init_constants();
|
|
39763
39963
|
init_swap();
|
|
39764
39964
|
widgetContentContainerStyle = {
|
|
39765
39965
|
position: "relative",
|