@rash2x/bridge-widget 0.1.4 → 0.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.
- package/dist/evaa-bridge.cjs +697 -389
- package/dist/evaa-bridge.cjs.map +1 -1
- package/dist/evaa-bridge.mjs +703 -395
- package/dist/evaa-bridge.mjs.map +1 -1
- package/dist/index.d.ts +8 -3
- package/package.json +7 -11
package/dist/evaa-bridge.cjs
CHANGED
|
@@ -44,10 +44,11 @@ const reactWindow = require("react-window");
|
|
|
44
44
|
const SwitchPrimitive = require("@radix-ui/react-switch");
|
|
45
45
|
const lucideReact = require("lucide-react");
|
|
46
46
|
const AccordionPrimitive = require("@radix-ui/react-accordion");
|
|
47
|
-
const connectkit = require("connectkit");
|
|
48
47
|
const i18next = require("i18next");
|
|
49
48
|
const sonner = require("sonner");
|
|
50
49
|
const ethers = require("ethers");
|
|
50
|
+
const viem = require("viem");
|
|
51
|
+
const ton = require("@ton/ton");
|
|
51
52
|
const tronwalletAdapters = require("@tronweb3/tronwallet-adapters");
|
|
52
53
|
function _interopNamespaceDefault(e) {
|
|
53
54
|
const n = Object.create(null, { [Symbol.toStringTag]: { value: "Module" } });
|
|
@@ -551,7 +552,7 @@ function cn(...inputs) {
|
|
|
551
552
|
return tailwindMerge.twMerge(clsx.clsx(inputs));
|
|
552
553
|
}
|
|
553
554
|
const buttonVariants = classVarianceAuthority.cva(
|
|
554
|
-
"inline-flex items-center rounded-full justify-center gap-2 whitespace-nowrap text-sm font-medium transition-all disabled:pointer-events-none disabled:opacity-50 [&_svg]:pointer-events-none [&_svg:not([class*='size-'])]:size-4 shrink-0 [&_svg]:shrink-0 outline-none focus-visible:border-ring focus-visible:ring-ring/50 focus-visible:ring-[3px] aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 aria-invalid:border-destructive",
|
|
555
|
+
"inline-flex items-center rounded-full text-lg justify-center gap-2 whitespace-nowrap text-sm font-medium transition-all disabled:pointer-events-none disabled:opacity-50 [&_svg]:pointer-events-none [&_svg:not([class*='size-'])]:size-4 shrink-0 [&_svg]:shrink-0 outline-none focus-visible:border-ring focus-visible:ring-ring/50 focus-visible:ring-[3px] aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 aria-invalid:border-destructive",
|
|
555
556
|
{
|
|
556
557
|
variants: {
|
|
557
558
|
variant: {
|
|
@@ -591,6 +592,23 @@ const Button = require$$0__namespace.forwardRef(
|
|
|
591
592
|
}
|
|
592
593
|
);
|
|
593
594
|
Button.displayName = "Button";
|
|
595
|
+
const ModalContainerContext = require$$0.createContext(void 0);
|
|
596
|
+
const ModalContainerProvider = ({
|
|
597
|
+
containerId,
|
|
598
|
+
children
|
|
599
|
+
}) => {
|
|
600
|
+
return /* @__PURE__ */ jsxRuntime.jsx(ModalContainerContext.Provider, { value: containerId, children });
|
|
601
|
+
};
|
|
602
|
+
const useModalContainer = () => {
|
|
603
|
+
const containerId = require$$0.useContext(ModalContainerContext);
|
|
604
|
+
if (typeof document === "undefined") {
|
|
605
|
+
return null;
|
|
606
|
+
}
|
|
607
|
+
if (!containerId) {
|
|
608
|
+
return document.body;
|
|
609
|
+
}
|
|
610
|
+
return document.getElementById(containerId) || document.body;
|
|
611
|
+
};
|
|
594
612
|
const ModalContent = ({ children, className }) => {
|
|
595
613
|
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: cn("p-5 flex flex-col h-full", className), children });
|
|
596
614
|
};
|
|
@@ -644,11 +662,11 @@ const Modal = ({
|
|
|
644
662
|
isOpen,
|
|
645
663
|
onClose,
|
|
646
664
|
children,
|
|
647
|
-
className
|
|
648
|
-
modalContainer
|
|
665
|
+
className
|
|
649
666
|
}) => {
|
|
650
667
|
const panelRef = require$$0.useRef(null);
|
|
651
668
|
const lastActiveRef = require$$0.useRef(null);
|
|
669
|
+
const container = useModalContainer();
|
|
652
670
|
require$$0.useEffect(() => {
|
|
653
671
|
if (!isOpen) return;
|
|
654
672
|
lastActiveRef.current = document.activeElement;
|
|
@@ -670,7 +688,6 @@ const Modal = ({
|
|
|
670
688
|
return () => window.removeEventListener("keydown", onKey);
|
|
671
689
|
}, [isOpen, onClose]);
|
|
672
690
|
if (typeof document === "undefined") return null;
|
|
673
|
-
const container = modalContainer || document.body;
|
|
674
691
|
return reactDom.createPortal(
|
|
675
692
|
/* @__PURE__ */ jsxRuntime.jsx(framerMotion.AnimatePresence, { children: isOpen && /* @__PURE__ */ jsxRuntime.jsx(
|
|
676
693
|
framerMotion.motion.div,
|
|
@@ -824,19 +841,6 @@ const Tip = (props) => {
|
|
|
824
841
|
/* @__PURE__ */ jsxRuntime.jsx(TooltipContent, { children: /* @__PURE__ */ jsxRuntime.jsx("p", { children: text }) })
|
|
825
842
|
] });
|
|
826
843
|
};
|
|
827
|
-
function toLD(human, decimals) {
|
|
828
|
-
const [i = "0", f = ""] = human.replace(",", ".").split(".");
|
|
829
|
-
const frac = (f + "0".repeat(decimals)).slice(0, decimals);
|
|
830
|
-
return BigInt(i + frac).toString();
|
|
831
|
-
}
|
|
832
|
-
function fromLD(ld, decimals) {
|
|
833
|
-
const bi = BigInt(ld || "0");
|
|
834
|
-
if (decimals === 0) return Number(bi);
|
|
835
|
-
const base = BigInt(10) ** BigInt(decimals);
|
|
836
|
-
const int = bi / base;
|
|
837
|
-
const frac = Number(bi % base) / Number(base);
|
|
838
|
-
return Number(int) + frac;
|
|
839
|
-
}
|
|
840
844
|
async function getChains() {
|
|
841
845
|
const res = await fetch("https://stargate.finance/api/v1/chains", {
|
|
842
846
|
credentials: "same-origin"
|
|
@@ -884,49 +888,16 @@ async function getDestTokens(srcChainKey, srcTokenAddr) {
|
|
|
884
888
|
});
|
|
885
889
|
return unique;
|
|
886
890
|
}
|
|
887
|
-
|
|
888
|
-
function normalizeTickerSymbol(s) {
|
|
891
|
+
function normalizeTickerSymbol$1(s) {
|
|
889
892
|
return s.toUpperCase().replace(/₮/g, "T").replace(/[^A-Z0-9]/g, "");
|
|
890
893
|
}
|
|
891
|
-
async function getSwapBalances(accountFriendly) {
|
|
892
|
-
if (!isTonFriendly(accountFriendly)) throw new Error("Invalid TON address");
|
|
893
|
-
const accRes = await fetch(
|
|
894
|
-
`https://tonapi.io/v2/accounts/${accountFriendly}`
|
|
895
|
-
);
|
|
896
|
-
if (!accRes.ok) throw new Error(`TON account fetch failed: ${accRes.status}`);
|
|
897
|
-
const acc = await accRes.json();
|
|
898
|
-
const ton = fromLD(String(acc?.balance ?? "0"), 9);
|
|
899
|
-
const result = {
|
|
900
|
-
TON: { balance: ton, address: "ton-native" }
|
|
901
|
-
};
|
|
902
|
-
const jetsRes = await fetch(
|
|
903
|
-
`https://tonapi.io/v2/accounts/${accountFriendly}/jettons?limit=200`
|
|
904
|
-
);
|
|
905
|
-
if (!jetsRes.ok) return result;
|
|
906
|
-
const jets = await jetsRes.json();
|
|
907
|
-
const items = jets?.balances ?? jets?.jettons ?? jets?.items ?? [];
|
|
908
|
-
for (const it of items) {
|
|
909
|
-
const rawSym = (it?.jetton?.symbol ?? it?.symbol ?? "").toString();
|
|
910
|
-
if (!rawSym) continue;
|
|
911
|
-
const symUpper = rawSym.toUpperCase();
|
|
912
|
-
const symNorm = normalizeTickerSymbol(symUpper);
|
|
913
|
-
const master = (it?.jetton?.address ?? it?.address ?? "").toString();
|
|
914
|
-
const decimals = Number(it?.jetton?.decimals ?? it?.decimals ?? 9) || 9;
|
|
915
|
-
const raw = (it?.balance ?? "0").toString();
|
|
916
|
-
const human = fromLD(raw, decimals);
|
|
917
|
-
const entry = { balance: human, address: master };
|
|
918
|
-
result[symUpper] = entry;
|
|
919
|
-
if (symNorm !== symUpper) result[symNorm] = entry;
|
|
920
|
-
}
|
|
921
|
-
return result;
|
|
922
|
-
}
|
|
923
894
|
const BASE_URL$1 = "https://icons-ckg.pages.dev/stargate-light/tokens";
|
|
924
895
|
const TokenSymbol = ({
|
|
925
896
|
symbol,
|
|
926
897
|
className = "w-4 h-4",
|
|
927
898
|
alt
|
|
928
899
|
}) => {
|
|
929
|
-
const normalizedSymbol = normalizeTickerSymbol(symbol).toLowerCase();
|
|
900
|
+
const normalizedSymbol = normalizeTickerSymbol$1(symbol).toLowerCase();
|
|
930
901
|
const src = `${BASE_URL$1}/${normalizedSymbol}.svg`;
|
|
931
902
|
return /* @__PURE__ */ jsxRuntime.jsx("img", { src, alt: alt ?? symbol, className });
|
|
932
903
|
};
|
|
@@ -1136,8 +1107,7 @@ const routePresets = [
|
|
|
1136
1107
|
];
|
|
1137
1108
|
const SettingModal = ({
|
|
1138
1109
|
isOpen,
|
|
1139
|
-
onClose
|
|
1140
|
-
modalContainer
|
|
1110
|
+
onClose
|
|
1141
1111
|
}) => {
|
|
1142
1112
|
const { t } = reactI18next.useTranslation();
|
|
1143
1113
|
const { toChain } = useChainsStore();
|
|
@@ -1171,7 +1141,7 @@ const SettingModal = ({
|
|
|
1171
1141
|
);
|
|
1172
1142
|
const activeBtn = "bg-settings-active hover:bg-settings-active/80 text-settings-active-foreground";
|
|
1173
1143
|
const notActiveBtn = "bg-settings-button hover:bg-settings-button/80 text-settings-button-foreground";
|
|
1174
|
-
return /* @__PURE__ */ jsxRuntime.jsx(Modal, { isOpen, onClose,
|
|
1144
|
+
return /* @__PURE__ */ jsxRuntime.jsx(Modal, { isOpen, onClose, children: /* @__PURE__ */ jsxRuntime.jsxs(ModalContent, { children: [
|
|
1175
1145
|
/* @__PURE__ */ jsxRuntime.jsxs(ModalHeader, { children: [
|
|
1176
1146
|
/* @__PURE__ */ jsxRuntime.jsx(ModalTitle, { children: t("settings.title", { defaultValue: "Settings" }) }),
|
|
1177
1147
|
/* @__PURE__ */ jsxRuntime.jsx(ModalClose, { className: "", onClick: onClose, children: /* @__PURE__ */ jsxRuntime.jsx(CloseIcon, { className: "size-6 p-0 [&>rect]:fill-modal-x [&>path]:stroke-modal-x-foreground" }) })
|
|
@@ -1340,6 +1310,19 @@ function useChainStrategies() {
|
|
|
1340
1310
|
}
|
|
1341
1311
|
return context;
|
|
1342
1312
|
}
|
|
1313
|
+
function toLD(human, decimals) {
|
|
1314
|
+
const [i = "0", f = ""] = human.replace(",", ".").split(".");
|
|
1315
|
+
const frac = (f + "0".repeat(decimals)).slice(0, decimals);
|
|
1316
|
+
return BigInt(i + frac).toString();
|
|
1317
|
+
}
|
|
1318
|
+
function fromLD(ld, decimals) {
|
|
1319
|
+
const bi = BigInt(ld || "0");
|
|
1320
|
+
if (decimals === 0) return Number(bi);
|
|
1321
|
+
const base = BigInt(10) ** BigInt(decimals);
|
|
1322
|
+
const int = bi / base;
|
|
1323
|
+
const frac = Number(bi % base) / Number(base);
|
|
1324
|
+
return Number(int) + frac;
|
|
1325
|
+
}
|
|
1343
1326
|
function resolveTokenOnChainFromMatrix$2(assetMatrix, assetSymbol, chainKey) {
|
|
1344
1327
|
if (!assetMatrix || !assetSymbol || !chainKey) return void 0;
|
|
1345
1328
|
const byChain = assetMatrix[assetSymbol.toUpperCase()];
|
|
@@ -1521,20 +1504,17 @@ function useBalances(chainKey, address) {
|
|
|
1521
1504
|
const data = query.data;
|
|
1522
1505
|
if (data) {
|
|
1523
1506
|
for (const [sum, v] of Object.entries(data)) {
|
|
1524
|
-
map.set(normalizeTickerSymbol(sum), Number(v.balance ?? 0));
|
|
1507
|
+
map.set(normalizeTickerSymbol$1(sum), Number(v.balance ?? 0));
|
|
1525
1508
|
}
|
|
1526
1509
|
}
|
|
1527
1510
|
return map;
|
|
1528
1511
|
}, [query.data]);
|
|
1529
1512
|
const getBalance = require$$0.useCallback(
|
|
1530
|
-
(symbol) => balanceBySymbol.get(normalizeTickerSymbol(symbol)) ?? 0,
|
|
1513
|
+
(symbol) => balanceBySymbol.get(normalizeTickerSymbol$1(symbol)) ?? 0,
|
|
1531
1514
|
[balanceBySymbol]
|
|
1532
1515
|
);
|
|
1533
1516
|
const isLoading = query.isLoading || query.isFetching;
|
|
1534
|
-
const balances = require$$0.useMemo(
|
|
1535
|
-
() => query.data || {},
|
|
1536
|
-
[query.data]
|
|
1537
|
-
);
|
|
1517
|
+
const balances = require$$0.useMemo(() => query.data || {}, [query.data]);
|
|
1538
1518
|
return {
|
|
1539
1519
|
balances,
|
|
1540
1520
|
getBalance,
|
|
@@ -1764,8 +1744,7 @@ const TokenSelectModal = ({
|
|
|
1764
1744
|
isOpen,
|
|
1765
1745
|
onClose,
|
|
1766
1746
|
items,
|
|
1767
|
-
onChangeAsset
|
|
1768
|
-
modalContainer
|
|
1747
|
+
onChangeAsset
|
|
1769
1748
|
}) => {
|
|
1770
1749
|
const { t } = reactI18next.useTranslation();
|
|
1771
1750
|
const {
|
|
@@ -1850,7 +1829,6 @@ const TokenSelectModal = ({
|
|
|
1850
1829
|
{
|
|
1851
1830
|
isOpen,
|
|
1852
1831
|
onClose: handleClose,
|
|
1853
|
-
modalContainer,
|
|
1854
1832
|
children: /* @__PURE__ */ jsxRuntime.jsxs(ModalContent, { children: [
|
|
1855
1833
|
/* @__PURE__ */ jsxRuntime.jsxs(ModalHeader, { children: [
|
|
1856
1834
|
/* @__PURE__ */ jsxRuntime.jsx(ModalTitle, { children: t("bridge.selectToken") }),
|
|
@@ -1990,17 +1968,17 @@ const RefreshButton = () => {
|
|
|
1990
1968
|
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
1991
1969
|
Button,
|
|
1992
1970
|
{
|
|
1993
|
-
className: `cursor-pointer py-1.5 h-8.5 hover:scale-110 shadow-none px-8.5 hover:bg-secondary bg-secondary !rounded-40 ${spinning ? "opacity-70" : ""}`,
|
|
1994
1971
|
onClick: handleRefresh,
|
|
1995
1972
|
disabled: spinning,
|
|
1973
|
+
variant: "secondary",
|
|
1974
|
+
size: "sm",
|
|
1996
1975
|
children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
1997
1976
|
ReloadIcon,
|
|
1998
1977
|
{
|
|
1999
1978
|
style: {
|
|
2000
1979
|
transform: `rotate(${turns * 180}deg)`,
|
|
2001
1980
|
transition: "transform 300ms linear"
|
|
2002
|
-
}
|
|
2003
|
-
className: "size-4 text-foreground m-1 will-change-transform"
|
|
1981
|
+
}
|
|
2004
1982
|
}
|
|
2005
1983
|
)
|
|
2006
1984
|
}
|
|
@@ -2008,7 +1986,6 @@ const RefreshButton = () => {
|
|
|
2008
1986
|
};
|
|
2009
1987
|
const SelectTokenButton = ({
|
|
2010
1988
|
onClick,
|
|
2011
|
-
className,
|
|
2012
1989
|
token
|
|
2013
1990
|
}) => {
|
|
2014
1991
|
const { t } = reactI18next.useTranslation();
|
|
@@ -2019,7 +1996,8 @@ const SelectTokenButton = ({
|
|
|
2019
1996
|
Button,
|
|
2020
1997
|
{
|
|
2021
1998
|
onClick,
|
|
2022
|
-
|
|
1999
|
+
size: "sm",
|
|
2000
|
+
variant: "secondary",
|
|
2023
2001
|
type: "button",
|
|
2024
2002
|
"aria-label": label,
|
|
2025
2003
|
children: [
|
|
@@ -2039,7 +2017,76 @@ const SelectTokenButton = ({
|
|
|
2039
2017
|
}
|
|
2040
2018
|
);
|
|
2041
2019
|
};
|
|
2042
|
-
|
|
2020
|
+
function Card({ className, ...props }) {
|
|
2021
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
2022
|
+
"div",
|
|
2023
|
+
{
|
|
2024
|
+
"data-slot": "card",
|
|
2025
|
+
className: cn(
|
|
2026
|
+
"bg-card text-card-foreground flex flex-col gap-6 rounded-xl border py-6 shadow-sm",
|
|
2027
|
+
className
|
|
2028
|
+
),
|
|
2029
|
+
...props
|
|
2030
|
+
}
|
|
2031
|
+
);
|
|
2032
|
+
}
|
|
2033
|
+
function CardHeader({ className, ...props }) {
|
|
2034
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
2035
|
+
"div",
|
|
2036
|
+
{
|
|
2037
|
+
"data-slot": "card-header",
|
|
2038
|
+
className: cn(
|
|
2039
|
+
"@container/card-header grid auto-rows-min grid-rows-[auto_auto] items-start gap-2 px-6 has-data-[slot=card-action]:grid-cols-[1fr_auto] [.border-b]:pb-6",
|
|
2040
|
+
className
|
|
2041
|
+
),
|
|
2042
|
+
...props
|
|
2043
|
+
}
|
|
2044
|
+
);
|
|
2045
|
+
}
|
|
2046
|
+
function CardTitle({ className, ...props }) {
|
|
2047
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
2048
|
+
"div",
|
|
2049
|
+
{
|
|
2050
|
+
"data-slot": "card-title",
|
|
2051
|
+
className: cn("leading-none font-semibold", className),
|
|
2052
|
+
...props
|
|
2053
|
+
}
|
|
2054
|
+
);
|
|
2055
|
+
}
|
|
2056
|
+
function CardAction({ className, ...props }) {
|
|
2057
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
2058
|
+
"div",
|
|
2059
|
+
{
|
|
2060
|
+
"data-slot": "card-action",
|
|
2061
|
+
className: cn(
|
|
2062
|
+
"col-start-2 row-span-2 row-start-1 self-start justify-self-end",
|
|
2063
|
+
className
|
|
2064
|
+
),
|
|
2065
|
+
...props
|
|
2066
|
+
}
|
|
2067
|
+
);
|
|
2068
|
+
}
|
|
2069
|
+
function CardContent({ className, ...props }) {
|
|
2070
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
2071
|
+
"div",
|
|
2072
|
+
{
|
|
2073
|
+
"data-slot": "card-content",
|
|
2074
|
+
className: cn("px-6", className),
|
|
2075
|
+
...props
|
|
2076
|
+
}
|
|
2077
|
+
);
|
|
2078
|
+
}
|
|
2079
|
+
function CardFooter({ className, ...props }) {
|
|
2080
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
2081
|
+
"div",
|
|
2082
|
+
{
|
|
2083
|
+
"data-slot": "card-footer",
|
|
2084
|
+
className: cn("flex items-center px-6 [.border-t]:pt-6", className),
|
|
2085
|
+
...props
|
|
2086
|
+
}
|
|
2087
|
+
);
|
|
2088
|
+
}
|
|
2089
|
+
const FormHeaderComponent = () => {
|
|
2043
2090
|
const { t } = reactI18next.useTranslation();
|
|
2044
2091
|
const { isOpen, onClose, onOpen } = useModal();
|
|
2045
2092
|
const {
|
|
@@ -2055,29 +2102,14 @@ const FormHeaderComponent = ({ modalContainer }) => {
|
|
|
2055
2102
|
const sum = selectedAssetSymbol.toUpperCase();
|
|
2056
2103
|
return assets.find((a) => a.symbol.toUpperCase() === sum) ?? assets[0];
|
|
2057
2104
|
}, [assets, selectedAssetSymbol]);
|
|
2058
|
-
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
2059
|
-
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
2060
|
-
/* @__PURE__ */ jsxRuntime.
|
|
2061
|
-
|
|
2062
|
-
|
|
2063
|
-
|
|
2064
|
-
/* @__PURE__ */ jsxRuntime.
|
|
2065
|
-
|
|
2066
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
2067
|
-
Button,
|
|
2068
|
-
{
|
|
2069
|
-
className: "cursor-pointer py-1.5 h-8.5 hover:scale-110 shadow-none px-8.5 hover:bg-secondary bg-secondary !rounded-40",
|
|
2070
|
-
onClick: onOpenSettings,
|
|
2071
|
-
children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
2072
|
-
BoltIcon,
|
|
2073
|
-
{
|
|
2074
|
-
className: "size-4 text-foreground m-1",
|
|
2075
|
-
stroke: "currentColor"
|
|
2076
|
-
}
|
|
2077
|
-
)
|
|
2078
|
-
}
|
|
2079
|
-
)
|
|
2080
|
-
] })
|
|
2105
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(CardHeader, { className: "gap-y-0 flex justify-between items-center", children: [
|
|
2106
|
+
/* @__PURE__ */ jsxRuntime.jsxs(CardTitle, { className: "flex items-center gap-2.5", children: [
|
|
2107
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-sm font-normal leading-3.5 text-muted-foreground", children: t("bridge.selectToken") }),
|
|
2108
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectTokenButton, { token: current, onClick: onOpen })
|
|
2109
|
+
] }),
|
|
2110
|
+
/* @__PURE__ */ jsxRuntime.jsxs(CardAction, { className: "flex items-center gap-2.5", children: [
|
|
2111
|
+
/* @__PURE__ */ jsxRuntime.jsx(RefreshButton, {}),
|
|
2112
|
+
/* @__PURE__ */ jsxRuntime.jsx(Button, { onClick: onOpenSettings, size: "sm", variant: "secondary", children: /* @__PURE__ */ jsxRuntime.jsx(BoltIcon, { stroke: "currentColor" }) })
|
|
2081
2113
|
] }),
|
|
2082
2114
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
2083
2115
|
TokenSelectModal,
|
|
@@ -2088,24 +2120,19 @@ const FormHeaderComponent = ({ modalContainer }) => {
|
|
|
2088
2120
|
onChangeAsset: (symbol) => {
|
|
2089
2121
|
setSelectedAssetSymbol(symbol);
|
|
2090
2122
|
onClose();
|
|
2091
|
-
}
|
|
2092
|
-
modalContainer
|
|
2123
|
+
}
|
|
2093
2124
|
}
|
|
2094
2125
|
),
|
|
2095
2126
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
2096
2127
|
SettingModal,
|
|
2097
2128
|
{
|
|
2098
2129
|
isOpen: isOpenSettings,
|
|
2099
|
-
onClose: onCloseSettings
|
|
2100
|
-
modalContainer
|
|
2130
|
+
onClose: onCloseSettings
|
|
2101
2131
|
}
|
|
2102
2132
|
)
|
|
2103
2133
|
] });
|
|
2104
2134
|
};
|
|
2105
|
-
const FormHeader = require$$0.memo(
|
|
2106
|
-
FormHeaderComponent,
|
|
2107
|
-
(prev, next) => prev.modalContainer === next.modalContainer
|
|
2108
|
-
);
|
|
2135
|
+
const FormHeader = require$$0.memo(FormHeaderComponent);
|
|
2109
2136
|
async function fetchQuotes(req) {
|
|
2110
2137
|
const params = {
|
|
2111
2138
|
srcChainKey: req.srcChainKey,
|
|
@@ -2653,8 +2680,7 @@ const ChainSelectModal = ({
|
|
|
2653
2680
|
onClose,
|
|
2654
2681
|
items,
|
|
2655
2682
|
allowedItems,
|
|
2656
|
-
onChangeChain
|
|
2657
|
-
modalContainer
|
|
2683
|
+
onChangeChain
|
|
2658
2684
|
}) => {
|
|
2659
2685
|
const { t } = reactI18next.useTranslation();
|
|
2660
2686
|
const [query, setQuery] = require$$0.useState("");
|
|
@@ -2743,7 +2769,6 @@ const ChainSelectModal = ({
|
|
|
2743
2769
|
{
|
|
2744
2770
|
isOpen,
|
|
2745
2771
|
onClose: handleClose,
|
|
2746
|
-
modalContainer,
|
|
2747
2772
|
children: /* @__PURE__ */ jsxRuntime.jsxs(ModalContent, { children: [
|
|
2748
2773
|
/* @__PURE__ */ jsxRuntime.jsxs(ModalHeader, { children: [
|
|
2749
2774
|
/* @__PURE__ */ jsxRuntime.jsx(ModalTitle, { children: t("bridge.selectNetwork") }),
|
|
@@ -2881,8 +2906,7 @@ const SwapSection = ({
|
|
|
2881
2906
|
disableNetworkSelect,
|
|
2882
2907
|
isSource,
|
|
2883
2908
|
onSelect,
|
|
2884
|
-
onAmountChange
|
|
2885
|
-
modalContainer
|
|
2909
|
+
onAmountChange
|
|
2886
2910
|
}) => {
|
|
2887
2911
|
const { isOpen, onClose, onOpen } = useModal();
|
|
2888
2912
|
const { assetMatrix, selectedAssetSymbol } = useTokensStore();
|
|
@@ -2915,9 +2939,9 @@ const SwapSection = ({
|
|
|
2915
2939
|
"div",
|
|
2916
2940
|
{
|
|
2917
2941
|
className: cn(
|
|
2918
|
-
"p-4 flex flex-col gap-4 transition-colors bg-
|
|
2942
|
+
"p-4 flex flex-col gap-4 transition-colors bg-input",
|
|
2919
2943
|
{
|
|
2920
|
-
"bg-
|
|
2944
|
+
"bg-input-focus": isSource && isFocused
|
|
2921
2945
|
},
|
|
2922
2946
|
className
|
|
2923
2947
|
),
|
|
@@ -2977,8 +3001,7 @@ const SwapSection = ({
|
|
|
2977
3001
|
onClose,
|
|
2978
3002
|
items: chains,
|
|
2979
3003
|
allowedItems: allowedChains,
|
|
2980
|
-
onChangeChain
|
|
2981
|
-
modalContainer
|
|
3004
|
+
onChangeChain
|
|
2982
3005
|
}
|
|
2983
3006
|
)
|
|
2984
3007
|
] });
|
|
@@ -3963,7 +3986,7 @@ function useSilentValidations(amountString) {
|
|
|
3963
3986
|
]);
|
|
3964
3987
|
return validationResult;
|
|
3965
3988
|
}
|
|
3966
|
-
|
|
3989
|
+
const SubmitButton = () => {
|
|
3967
3990
|
const { t } = reactI18next.useTranslation();
|
|
3968
3991
|
const { chainRegistry } = useChainStrategies();
|
|
3969
3992
|
const { srcAddress, dstAddress } = useAddresses();
|
|
@@ -4039,7 +4062,7 @@ function useTransferAction() {
|
|
|
4039
4062
|
maximumAmountFormatted,
|
|
4040
4063
|
chainRegistry
|
|
4041
4064
|
]);
|
|
4042
|
-
const
|
|
4065
|
+
const handleClick = async () => {
|
|
4043
4066
|
if (isBusy) return;
|
|
4044
4067
|
if (missingSrc && srcChainKey) {
|
|
4045
4068
|
onOpen("src");
|
|
@@ -4059,33 +4082,15 @@ function useTransferAction() {
|
|
|
4059
4082
|
}
|
|
4060
4083
|
};
|
|
4061
4084
|
const disabled = isBusy || amountNum <= 0 || status === "loading" || isBalanceLoading || hasInsufficientBalance || hasAmountTooLarge || !gas.hasEnoughGas || noRoute || !isValidForTransfer;
|
|
4062
|
-
return {
|
|
4063
|
-
// состояния
|
|
4064
|
-
isBusy,
|
|
4065
|
-
canTransfer,
|
|
4066
|
-
missingSrc,
|
|
4067
|
-
missingDst,
|
|
4068
|
-
hasEnoughGas: gas.hasEnoughGas,
|
|
4069
|
-
noRoute,
|
|
4070
|
-
// представление
|
|
4071
|
-
label,
|
|
4072
|
-
disabled,
|
|
4073
|
-
// действие
|
|
4074
|
-
onClick
|
|
4075
|
-
};
|
|
4076
|
-
}
|
|
4077
|
-
const SubmitButton = () => {
|
|
4078
|
-
const { label, disabled, onClick } = useTransferAction();
|
|
4079
|
-
return /* @__PURE__ */ jsxRuntime.jsx(Button, { onClick, disabled, size: "lg", children: label });
|
|
4085
|
+
return /* @__PURE__ */ jsxRuntime.jsx(Button, { onClick: handleClick, disabled, className: "w-full", children: label });
|
|
4080
4086
|
};
|
|
4081
4087
|
function short(addr) {
|
|
4082
4088
|
return addr.slice(0, 4) + "…" + addr.slice(-4);
|
|
4083
4089
|
}
|
|
4084
|
-
const WalletSelectModal = ({
|
|
4085
|
-
modalContainer
|
|
4086
|
-
}) => {
|
|
4090
|
+
const WalletSelectModal = () => {
|
|
4087
4091
|
const { t } = reactI18next.useTranslation();
|
|
4088
4092
|
const { isOpen, onClose } = useWalletSelectModal();
|
|
4093
|
+
const { connect, connectors, isPending } = wagmi.useConnect();
|
|
4089
4094
|
const { chainRegistry } = useChainStrategies();
|
|
4090
4095
|
const tonWallet = chainRegistry.getStrategyByType("ton");
|
|
4091
4096
|
const metaMaskWallet = chainRegistry.getStrategyByType("evm");
|
|
@@ -4118,7 +4123,13 @@ const WalletSelectModal = ({
|
|
|
4118
4123
|
onDisconnect: () => tronWallet.disconnect()
|
|
4119
4124
|
});
|
|
4120
4125
|
}
|
|
4121
|
-
const isWalletConnected = (walletId) =>
|
|
4126
|
+
const isWalletConnected = (walletId) => {
|
|
4127
|
+
const isEvmConnector = connectors.some((c) => c.id === walletId);
|
|
4128
|
+
if (isEvmConnector && metaMaskWallet?.isConnected()) {
|
|
4129
|
+
return true;
|
|
4130
|
+
}
|
|
4131
|
+
return connectedWallets.some((w) => w.id === walletId);
|
|
4132
|
+
};
|
|
4122
4133
|
const tonWallets = [
|
|
4123
4134
|
{
|
|
4124
4135
|
id: "ton",
|
|
@@ -4127,14 +4138,15 @@ const WalletSelectModal = ({
|
|
|
4127
4138
|
enabled: true
|
|
4128
4139
|
}
|
|
4129
4140
|
];
|
|
4130
|
-
const evmWallets =
|
|
4131
|
-
|
|
4132
|
-
|
|
4133
|
-
|
|
4134
|
-
|
|
4135
|
-
|
|
4136
|
-
|
|
4137
|
-
|
|
4141
|
+
const evmWallets = connectors.filter(
|
|
4142
|
+
(connector) => connector.id === "walletConnect" || connector.id === "metaMaskSDK"
|
|
4143
|
+
).map((connector) => ({
|
|
4144
|
+
id: connector.id,
|
|
4145
|
+
name: connector.name,
|
|
4146
|
+
icon: MetaMaskIcon,
|
|
4147
|
+
// You can add a WalletConnect icon here
|
|
4148
|
+
enabled: true
|
|
4149
|
+
}));
|
|
4138
4150
|
const tronWallets = [
|
|
4139
4151
|
{
|
|
4140
4152
|
id: "tronlink",
|
|
@@ -4164,9 +4176,6 @@ const WalletSelectModal = ({
|
|
|
4164
4176
|
case "ton":
|
|
4165
4177
|
await tonWallet?.connect();
|
|
4166
4178
|
break;
|
|
4167
|
-
case "metamask":
|
|
4168
|
-
await metaMaskWallet?.connect();
|
|
4169
|
-
break;
|
|
4170
4179
|
case "tronlink":
|
|
4171
4180
|
await tronWallet?.connect();
|
|
4172
4181
|
break;
|
|
@@ -4178,7 +4187,7 @@ const WalletSelectModal = ({
|
|
|
4178
4187
|
console.error("Failed to connect wallet:", error);
|
|
4179
4188
|
}
|
|
4180
4189
|
};
|
|
4181
|
-
return /* @__PURE__ */ jsxRuntime.jsx(Modal, { isOpen, onClose,
|
|
4190
|
+
return /* @__PURE__ */ jsxRuntime.jsx(Modal, { isOpen, onClose, children: /* @__PURE__ */ jsxRuntime.jsxs(ModalContent, { children: [
|
|
4182
4191
|
/* @__PURE__ */ jsxRuntime.jsxs(ModalHeader, { children: [
|
|
4183
4192
|
/* @__PURE__ */ jsxRuntime.jsx(ModalTitle, { children: t("wallets.chooseWallet", { defaultValue: "Choose wallet" }) }),
|
|
4184
4193
|
/* @__PURE__ */ jsxRuntime.jsx(ModalDescription, { children: t("wallets.oneWalletPerEnv", {
|
|
@@ -4191,56 +4200,47 @@ const WalletSelectModal = ({
|
|
|
4191
4200
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "px-5 py-2 leading-4 text-base font-semibold text-muted-foreground uppercase", children: t("wallets.connected") }),
|
|
4192
4201
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "", children: connectedWallets.map((wallet) => {
|
|
4193
4202
|
const IconComponent = wallet.icon;
|
|
4194
|
-
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "", children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
4195
|
-
|
|
4196
|
-
|
|
4197
|
-
|
|
4198
|
-
|
|
4199
|
-
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "
|
|
4200
|
-
|
|
4201
|
-
|
|
4202
|
-
|
|
4203
|
-
|
|
4204
|
-
|
|
4205
|
-
|
|
4206
|
-
/* @__PURE__ */ jsxRuntime.jsx("div", { onClick: () => {
|
|
4203
|
+
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "", children: /* @__PURE__ */ jsxRuntime.jsxs(Button, { className: "w-full cursor-pointer bg-transparent flex shadow-none items-center justify-between gap-2.5 px-5 py-2.5 hover:bg-muted h-auto rounded-12 transition-[300]", children: [
|
|
4204
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex items-center gap-3 min-w-0", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2.5", children: [
|
|
4205
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-7.5 h-7.5 flex items-center justify-center", children: /* @__PURE__ */ jsxRuntime.jsx(IconComponent, { className: "size-7.5" }) }),
|
|
4206
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-start min-w-0", children: [
|
|
4207
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "font-extrabold text-foreground text-sm leading-4 truncate", children: short(wallet.address) }),
|
|
4208
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "text-xs leading-3 font-semibold text-muted-foreground", children: wallet.name })
|
|
4209
|
+
] })
|
|
4210
|
+
] }) }),
|
|
4211
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
4212
|
+
"div",
|
|
4213
|
+
{
|
|
4214
|
+
onClick: () => {
|
|
4207
4215
|
wallet.onDisconnect();
|
|
4208
4216
|
onClose();
|
|
4209
|
-
},
|
|
4210
|
-
|
|
4211
|
-
|
|
4212
|
-
|
|
4217
|
+
},
|
|
4218
|
+
className: "text-sm font-medium text-muted-foreground",
|
|
4219
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(ExitIcon, { className: "text-[#808080] size-6" })
|
|
4220
|
+
}
|
|
4221
|
+
)
|
|
4222
|
+
] }) }, wallet.id);
|
|
4213
4223
|
}) })
|
|
4214
4224
|
] }),
|
|
4215
4225
|
categories.map((category) => /* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
4216
4226
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "px-5 py-2 leading-4 text-base font-semibold text-muted-foreground uppercase", children: category.title }),
|
|
4217
4227
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "", children: category.wallets.map((wallet) => {
|
|
4218
4228
|
const IconComponent = wallet.icon;
|
|
4219
|
-
|
|
4220
|
-
|
|
4221
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
4222
|
-
Button,
|
|
4223
|
-
{
|
|
4224
|
-
type: "button",
|
|
4225
|
-
onClick: show,
|
|
4226
|
-
disabled: isConnecting,
|
|
4227
|
-
className: "w-full cursor-pointer bg-transparent flex shadow-none items-center justify-between gap-2.5 px-5 py-2.5 hover:bg-muted h-auto rounded-12 transition-[300] disabled:opacity-50 disabled:cursor-not-allowed",
|
|
4228
|
-
children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-3 min-w-0", children: [
|
|
4229
|
-
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-7.5 h-7.5 flex items-center justify-center", children: /* @__PURE__ */ jsxRuntime.jsx(IconComponent, { className: "size-7.5" }) }),
|
|
4230
|
-
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-start min-w-0", children: [
|
|
4231
|
-
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "font-extrabold text-foreground text-sm leading-4 truncate", children: wallet.name }),
|
|
4232
|
-
wallet.comingSoon ? /* @__PURE__ */ jsxRuntime.jsx("div", { className: "text-xs leading-3 font-semibold text-muted-foreground", children: t("wallets.comingSoon") }) : /* @__PURE__ */ jsxRuntime.jsx("div", { className: "text-xs leading-3 font-semibold text-muted-foreground", children: t("wallets.connect") })
|
|
4233
|
-
] })
|
|
4234
|
-
] })
|
|
4235
|
-
}
|
|
4236
|
-
);
|
|
4237
|
-
} }) }, wallet.id);
|
|
4238
|
-
}
|
|
4229
|
+
const isEvmConnector = category.title === t("wallets.evmWallets");
|
|
4230
|
+
const connector = isEvmConnector ? connectors.find((c) => c.id === wallet.id) : null;
|
|
4239
4231
|
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
4240
4232
|
Button,
|
|
4241
4233
|
{
|
|
4242
|
-
|
|
4243
|
-
|
|
4234
|
+
type: "button",
|
|
4235
|
+
onClick: () => {
|
|
4236
|
+
if (connector) {
|
|
4237
|
+
connect({ connector });
|
|
4238
|
+
onClose();
|
|
4239
|
+
} else {
|
|
4240
|
+
handleWalletSelect(wallet.id);
|
|
4241
|
+
}
|
|
4242
|
+
},
|
|
4243
|
+
disabled: isEvmConnector ? isPending : !wallet.enabled,
|
|
4244
4244
|
className: "w-full cursor-pointer bg-transparent flex shadow-none items-center justify-between gap-2.5 px-5 py-2.5 hover:bg-muted h-auto rounded-12 transition-[300] disabled:opacity-50 disabled:cursor-not-allowed",
|
|
4245
4245
|
children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-3 min-w-0", children: [
|
|
4246
4246
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-7.5 h-7.5 flex items-center justify-center", children: /* @__PURE__ */ jsxRuntime.jsx(IconComponent, { className: "size-7.5" }) }),
|
|
@@ -4256,39 +4256,6 @@ const WalletSelectModal = ({
|
|
|
4256
4256
|
] })
|
|
4257
4257
|
] }) });
|
|
4258
4258
|
};
|
|
4259
|
-
function Card({ className, ...props }) {
|
|
4260
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
4261
|
-
"div",
|
|
4262
|
-
{
|
|
4263
|
-
"data-slot": "card",
|
|
4264
|
-
className: cn(
|
|
4265
|
-
"bg-card text-card-foreground flex flex-col gap-6 rounded-xl border py-6 shadow-sm",
|
|
4266
|
-
className
|
|
4267
|
-
),
|
|
4268
|
-
...props
|
|
4269
|
-
}
|
|
4270
|
-
);
|
|
4271
|
-
}
|
|
4272
|
-
function CardContent({ className, ...props }) {
|
|
4273
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
4274
|
-
"div",
|
|
4275
|
-
{
|
|
4276
|
-
"data-slot": "card-content",
|
|
4277
|
-
className: cn("px-6", className),
|
|
4278
|
-
...props
|
|
4279
|
-
}
|
|
4280
|
-
);
|
|
4281
|
-
}
|
|
4282
|
-
function CardFooter({ className, ...props }) {
|
|
4283
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
4284
|
-
"div",
|
|
4285
|
-
{
|
|
4286
|
-
"data-slot": "card-footer",
|
|
4287
|
-
className: cn("flex items-center px-6 [.border-t]:pt-6", className),
|
|
4288
|
-
...props
|
|
4289
|
-
}
|
|
4290
|
-
);
|
|
4291
|
-
}
|
|
4292
4259
|
const TransactionProgressVector = (props) => {
|
|
4293
4260
|
return /* @__PURE__ */ jsxRuntime.jsxs("svg", { width: "200", height: "200", viewBox: "0 0 200 200", fill: "none", xmlns: "http://www.w3.org/2000/svg", ...props, children: [
|
|
4294
4261
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
@@ -6213,7 +6180,7 @@ const ConfirmStep = () => {
|
|
|
6213
6180
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "text-3xl font-black relative z-10", children: formatTime })
|
|
6214
6181
|
] }) });
|
|
6215
6182
|
};
|
|
6216
|
-
const TransactionManager = (
|
|
6183
|
+
const TransactionManager = () => {
|
|
6217
6184
|
const { current } = useTransactionStore();
|
|
6218
6185
|
const status = current?.status;
|
|
6219
6186
|
if (!status || status === "idle") return null;
|
|
@@ -6231,7 +6198,7 @@ const TransactionManager = ({ modalContainer }) => {
|
|
|
6231
6198
|
step = /* @__PURE__ */ jsxRuntime.jsx(SuccessStep, {});
|
|
6232
6199
|
}
|
|
6233
6200
|
return /* @__PURE__ */ jsxRuntime.jsx(Modal, { isOpen: true, onClose: () => {
|
|
6234
|
-
},
|
|
6201
|
+
}, children: step });
|
|
6235
6202
|
};
|
|
6236
6203
|
const useTokensRequest = () => {
|
|
6237
6204
|
const { setTokens, setSelectedToken, setSelectedAssetSymbol } = useTokensStore();
|
|
@@ -6352,6 +6319,49 @@ class ChainStrategyRegistry {
|
|
|
6352
6319
|
await strategy.disconnect();
|
|
6353
6320
|
}
|
|
6354
6321
|
}
|
|
6322
|
+
const EVM_CONFIG = {
|
|
6323
|
+
usdtAddress: "0xdAC17F958D2ee523a2206206994597C13D831ec7",
|
|
6324
|
+
gasEstimates: {
|
|
6325
|
+
approve: 65000n,
|
|
6326
|
+
bridge: 300000n
|
|
6327
|
+
},
|
|
6328
|
+
gasBuffer: 1.2,
|
|
6329
|
+
// 20% buffer
|
|
6330
|
+
timeout: 3e5,
|
|
6331
|
+
// 5 minutes (increased for slower networks)
|
|
6332
|
+
requiredConfirmations: 3
|
|
6333
|
+
// Wait for 3 confirmations for reorg protection
|
|
6334
|
+
};
|
|
6335
|
+
const TON_CONFIG = {
|
|
6336
|
+
apiUrl: "https://toncenter.com/api/v2",
|
|
6337
|
+
timeout: 36e4,
|
|
6338
|
+
// 6 minutes
|
|
6339
|
+
validUntil: 600
|
|
6340
|
+
// 10 minutes
|
|
6341
|
+
};
|
|
6342
|
+
const TRON_CONFIG = {
|
|
6343
|
+
timeout: 12e4,
|
|
6344
|
+
// 2 minutes (for 19 confirmations)
|
|
6345
|
+
feeLimit: 1e8,
|
|
6346
|
+
// 100 TRX in sun
|
|
6347
|
+
requiredConfirmations: 19,
|
|
6348
|
+
// TRON standard: 19 blocks for confirmation
|
|
6349
|
+
pollingInterval: 3e3
|
|
6350
|
+
// 3 seconds between checks
|
|
6351
|
+
};
|
|
6352
|
+
let tonClientInstance = null;
|
|
6353
|
+
function getTonClient(customClient, apiKey) {
|
|
6354
|
+
if (customClient) {
|
|
6355
|
+
return customClient;
|
|
6356
|
+
}
|
|
6357
|
+
if (!tonClientInstance) {
|
|
6358
|
+
tonClientInstance = new ton.TonClient({
|
|
6359
|
+
endpoint: `${TON_CONFIG.apiUrl}/jsonRPC`,
|
|
6360
|
+
apiKey
|
|
6361
|
+
});
|
|
6362
|
+
}
|
|
6363
|
+
return tonClientInstance;
|
|
6364
|
+
}
|
|
6355
6365
|
function isNativeAddress(addr) {
|
|
6356
6366
|
if (!addr) return false;
|
|
6357
6367
|
const a = addr.toLowerCase();
|
|
@@ -6377,44 +6387,72 @@ function formatUnitsFromBigIntStr(valueStr, decimals) {
|
|
|
6377
6387
|
const tail = s.slice(s.length - decimals).replace(/0+$/, "");
|
|
6378
6388
|
return Number(tail ? `${head}.${tail}` : head);
|
|
6379
6389
|
}
|
|
6380
|
-
|
|
6390
|
+
function isTonFriendlyAddress(address) {
|
|
6391
|
+
return !!address && /^[A-Za-z0-9_-]{48,}$/.test(address);
|
|
6392
|
+
}
|
|
6393
|
+
function normalizeTickerSymbol(symbol) {
|
|
6394
|
+
return symbol.toUpperCase().replace(/₮/g, "T").replace(/[^A-Z0-9]/g, "");
|
|
6395
|
+
}
|
|
6396
|
+
function parseTonAddress(address) {
|
|
6397
|
+
if (address.startsWith("0x")) {
|
|
6398
|
+
const hex = address.slice(2);
|
|
6399
|
+
return ton.Address.parseRaw(`0:${hex}`);
|
|
6400
|
+
}
|
|
6401
|
+
if (address.includes(":")) {
|
|
6402
|
+
return ton.Address.parseRaw(address);
|
|
6403
|
+
}
|
|
6404
|
+
return ton.Address.parse(address);
|
|
6405
|
+
}
|
|
6406
|
+
async function getEvmBalances(publicClient, address, tokens) {
|
|
6381
6407
|
const balances = {};
|
|
6382
6408
|
try {
|
|
6383
|
-
|
|
6409
|
+
console.log("start getEvmBalances");
|
|
6410
|
+
console.log("publicClient:", publicClient);
|
|
6411
|
+
console.log("isAddress:", viem.isAddress(address));
|
|
6412
|
+
console.log("tokens:", tokens);
|
|
6413
|
+
if (!address || !viem.isAddress(address)) {
|
|
6384
6414
|
console.warn(`Invalid EVM address provided: ${address}`);
|
|
6385
6415
|
return balances;
|
|
6386
6416
|
}
|
|
6387
|
-
if (
|
|
6388
|
-
throw new Error("No
|
|
6417
|
+
if (!publicClient) {
|
|
6418
|
+
throw new Error("No public client provided");
|
|
6389
6419
|
}
|
|
6390
|
-
const provider = new ethers.ethers.BrowserProvider(window.ethereum);
|
|
6391
6420
|
for (const token of tokens) {
|
|
6392
6421
|
try {
|
|
6393
6422
|
let balance = 0;
|
|
6394
6423
|
const isNative = isNativeAddress(token.address);
|
|
6395
6424
|
if (isNative) {
|
|
6396
|
-
const ethBalance = await
|
|
6397
|
-
|
|
6425
|
+
const ethBalance = await publicClient.getBalance({
|
|
6426
|
+
address
|
|
6427
|
+
});
|
|
6428
|
+
balance = parseFloat(viem.formatUnits(ethBalance, token.decimals));
|
|
6398
6429
|
} else {
|
|
6399
|
-
if (!
|
|
6430
|
+
if (!viem.isAddress(token.address)) {
|
|
6400
6431
|
continue;
|
|
6401
6432
|
}
|
|
6402
|
-
const
|
|
6403
|
-
|
|
6433
|
+
const bytecode = await publicClient.getBytecode({
|
|
6434
|
+
address: token.address
|
|
6435
|
+
});
|
|
6436
|
+
if (!bytecode || bytecode === "0x") {
|
|
6404
6437
|
continue;
|
|
6405
6438
|
}
|
|
6406
|
-
const contract = new ethers.ethers.Contract(
|
|
6407
|
-
token.address,
|
|
6408
|
-
[
|
|
6409
|
-
"function balanceOf(address owner) view returns (uint256)",
|
|
6410
|
-
"function decimals() view returns (uint8)"
|
|
6411
|
-
],
|
|
6412
|
-
provider
|
|
6413
|
-
);
|
|
6414
6439
|
try {
|
|
6415
|
-
const tokenBalance = await
|
|
6440
|
+
const tokenBalance = await publicClient.readContract({
|
|
6441
|
+
address: token.address,
|
|
6442
|
+
abi: [
|
|
6443
|
+
{
|
|
6444
|
+
name: "balanceOf",
|
|
6445
|
+
type: "function",
|
|
6446
|
+
stateMutability: "view",
|
|
6447
|
+
inputs: [{ name: "owner", type: "address" }],
|
|
6448
|
+
outputs: [{ name: "balance", type: "uint256" }]
|
|
6449
|
+
}
|
|
6450
|
+
],
|
|
6451
|
+
functionName: "balanceOf",
|
|
6452
|
+
args: [address]
|
|
6453
|
+
});
|
|
6416
6454
|
balance = parseFloat(
|
|
6417
|
-
|
|
6455
|
+
viem.formatUnits(tokenBalance, token.decimals)
|
|
6418
6456
|
);
|
|
6419
6457
|
} catch {
|
|
6420
6458
|
continue;
|
|
@@ -6437,6 +6475,68 @@ async function getEvmBalances(address, tokens) {
|
|
|
6437
6475
|
}
|
|
6438
6476
|
return balances;
|
|
6439
6477
|
}
|
|
6478
|
+
async function getTonBalances(address, tokens, customTonClient, tonApiKey) {
|
|
6479
|
+
const balances = {};
|
|
6480
|
+
try {
|
|
6481
|
+
if (!isTonFriendlyAddress(address)) {
|
|
6482
|
+
console.warn(`Invalid TON address provided: ${address}`);
|
|
6483
|
+
return balances;
|
|
6484
|
+
}
|
|
6485
|
+
const client = getTonClient(customTonClient, tonApiKey);
|
|
6486
|
+
const accountAddress = ton.Address.parse(address);
|
|
6487
|
+
console.log(address);
|
|
6488
|
+
console.log(tokens);
|
|
6489
|
+
try {
|
|
6490
|
+
const balance = await client.getBalance(accountAddress);
|
|
6491
|
+
const tonBalance = Number(balance) / 1e9;
|
|
6492
|
+
console.log("tonBalance", tonBalance);
|
|
6493
|
+
if (tonBalance > 0) {
|
|
6494
|
+
balances.TON = { balance: tonBalance, address: "ton-native" };
|
|
6495
|
+
}
|
|
6496
|
+
} catch (error) {
|
|
6497
|
+
console.warn("Failed to get native TON balance:", error);
|
|
6498
|
+
}
|
|
6499
|
+
for (const token of tokens) {
|
|
6500
|
+
try {
|
|
6501
|
+
if (isNativeAddress(token.address) || token.symbol.toUpperCase() === "TON") {
|
|
6502
|
+
continue;
|
|
6503
|
+
}
|
|
6504
|
+
const jettonMasterAddress = parseTonAddress(token.address);
|
|
6505
|
+
const jettonWalletAddress = await client.runMethod(
|
|
6506
|
+
jettonMasterAddress,
|
|
6507
|
+
"get_wallet_address",
|
|
6508
|
+
[
|
|
6509
|
+
{
|
|
6510
|
+
type: "slice",
|
|
6511
|
+
cell: ton.beginCell().storeAddress(accountAddress).endCell()
|
|
6512
|
+
}
|
|
6513
|
+
]
|
|
6514
|
+
);
|
|
6515
|
+
const jettonWalletAddr = jettonWalletAddress.stack.readAddress();
|
|
6516
|
+
const jettonData = await client.runMethod(
|
|
6517
|
+
jettonWalletAddr,
|
|
6518
|
+
"get_wallet_data"
|
|
6519
|
+
);
|
|
6520
|
+
const jettonBalance = jettonData.stack.readBigNumber();
|
|
6521
|
+
const humanBalance = Number(jettonBalance) / Math.pow(10, token.decimals);
|
|
6522
|
+
if (humanBalance > 0) {
|
|
6523
|
+
const symbolUpper = token.symbol.toUpperCase();
|
|
6524
|
+
const symbolNorm = normalizeTickerSymbol(symbolUpper);
|
|
6525
|
+
const entry = { balance: humanBalance, address: token.address };
|
|
6526
|
+
balances[symbolUpper] = entry;
|
|
6527
|
+
if (symbolNorm !== symbolUpper) {
|
|
6528
|
+
balances[symbolNorm] = entry;
|
|
6529
|
+
}
|
|
6530
|
+
}
|
|
6531
|
+
} catch (error) {
|
|
6532
|
+
console.debug(`Failed to get balance for ${token.symbol}:`, error);
|
|
6533
|
+
}
|
|
6534
|
+
}
|
|
6535
|
+
} catch (error) {
|
|
6536
|
+
console.error("Failed to get TON balances:", error);
|
|
6537
|
+
}
|
|
6538
|
+
return balances;
|
|
6539
|
+
}
|
|
6440
6540
|
async function getTronBalances(tronWeb, address, tokens) {
|
|
6441
6541
|
const balances = {};
|
|
6442
6542
|
try {
|
|
@@ -6480,30 +6580,6 @@ async function getTronBalances(tronWeb, address, tokens) {
|
|
|
6480
6580
|
}
|
|
6481
6581
|
return balances;
|
|
6482
6582
|
}
|
|
6483
|
-
const EVM_CONFIG = {
|
|
6484
|
-
usdtAddress: "0xdAC17F958D2ee523a2206206994597C13D831ec7",
|
|
6485
|
-
gasEstimates: {
|
|
6486
|
-
approve: 65000n,
|
|
6487
|
-
bridge: 300000n
|
|
6488
|
-
},
|
|
6489
|
-
gasBuffer: 1.2,
|
|
6490
|
-
// 20% buffer
|
|
6491
|
-
timeout: 12e4
|
|
6492
|
-
// 2 minutes
|
|
6493
|
-
};
|
|
6494
|
-
const TON_CONFIG = {
|
|
6495
|
-
apiUrl: "https://toncenter.com/api/v2",
|
|
6496
|
-
timeout: 36e4,
|
|
6497
|
-
// 6 minutes
|
|
6498
|
-
validUntil: 600
|
|
6499
|
-
// 10 minutes
|
|
6500
|
-
};
|
|
6501
|
-
const TRON_CONFIG = {
|
|
6502
|
-
timeout: 6e4,
|
|
6503
|
-
// 1 minute
|
|
6504
|
-
feeLimit: 1e8
|
|
6505
|
-
// 100 TRX in sun
|
|
6506
|
-
};
|
|
6507
6583
|
const ERC20_ABI = [
|
|
6508
6584
|
"function approve(address spender, uint256 amount) returns (bool)",
|
|
6509
6585
|
"function allowance(address owner, address spender) view returns (uint256)",
|
|
@@ -6514,7 +6590,9 @@ class EvmChainStrategy {
|
|
|
6514
6590
|
constructor(config) {
|
|
6515
6591
|
__publicField(this, "config");
|
|
6516
6592
|
__publicField(this, "provider");
|
|
6593
|
+
__publicField(this, "publicClient");
|
|
6517
6594
|
this.config = config;
|
|
6595
|
+
this.publicClient = config.publicClient;
|
|
6518
6596
|
if (config.walletClient) {
|
|
6519
6597
|
this.provider = new ethers.BrowserProvider(config.walletClient.transport);
|
|
6520
6598
|
}
|
|
@@ -6553,7 +6631,11 @@ class EvmChainStrategy {
|
|
|
6553
6631
|
return t("wallets.connectEvmWallet");
|
|
6554
6632
|
}
|
|
6555
6633
|
async getBalances(address, tokens) {
|
|
6556
|
-
|
|
6634
|
+
if (!this.publicClient) {
|
|
6635
|
+
console.warn("No publicClient available for balance query");
|
|
6636
|
+
return {};
|
|
6637
|
+
}
|
|
6638
|
+
return await getEvmBalances(this.publicClient, address, tokens);
|
|
6557
6639
|
}
|
|
6558
6640
|
isAddressValid(address) {
|
|
6559
6641
|
if (!address) return false;
|
|
@@ -6666,17 +6748,14 @@ class EvmChainStrategy {
|
|
|
6666
6748
|
if (!provider) {
|
|
6667
6749
|
throw new ProviderNotAvailableError("evm");
|
|
6668
6750
|
}
|
|
6669
|
-
|
|
6670
|
-
|
|
6671
|
-
|
|
6672
|
-
|
|
6673
|
-
|
|
6674
|
-
|
|
6675
|
-
|
|
6676
|
-
|
|
6677
|
-
}
|
|
6678
|
-
await new Promise((r) => setTimeout(r, 2500));
|
|
6679
|
-
}
|
|
6751
|
+
console.log(
|
|
6752
|
+
`Waiting for ${EVM_CONFIG.requiredConfirmations} confirmations for tx: ${txHash}`
|
|
6753
|
+
);
|
|
6754
|
+
const receipt = await provider.waitForTransaction(
|
|
6755
|
+
txHash,
|
|
6756
|
+
EVM_CONFIG.requiredConfirmations,
|
|
6757
|
+
EVM_CONFIG.timeout
|
|
6758
|
+
);
|
|
6680
6759
|
if (!receipt) {
|
|
6681
6760
|
const error = new TransactionTimeoutError("evm", txHash);
|
|
6682
6761
|
return {
|
|
@@ -6691,11 +6770,35 @@ class EvmChainStrategy {
|
|
|
6691
6770
|
error: error.message
|
|
6692
6771
|
};
|
|
6693
6772
|
}
|
|
6694
|
-
console.log(
|
|
6773
|
+
console.log(
|
|
6774
|
+
`EVM transaction confirmed in block ${receipt.blockNumber} with ${EVM_CONFIG.requiredConfirmations} confirmations`
|
|
6775
|
+
);
|
|
6695
6776
|
return {
|
|
6696
6777
|
completed: true
|
|
6697
6778
|
};
|
|
6698
6779
|
} catch (error) {
|
|
6780
|
+
if (error && typeof error === "object" && "code" in error && error.code === "TRANSACTION_REPLACED") {
|
|
6781
|
+
console.log(
|
|
6782
|
+
`Transaction was replaced: ${"reason" in error ? String(error.reason) : "unknown"}`
|
|
6783
|
+
);
|
|
6784
|
+
if ("receipt" in error && error.receipt) {
|
|
6785
|
+
const replacementReceipt = error.receipt;
|
|
6786
|
+
if (replacementReceipt.status === 1) {
|
|
6787
|
+
console.log(
|
|
6788
|
+
`Replacement transaction succeeded in block ${replacementReceipt.blockNumber}`
|
|
6789
|
+
);
|
|
6790
|
+
return {
|
|
6791
|
+
completed: true
|
|
6792
|
+
};
|
|
6793
|
+
} else {
|
|
6794
|
+
const chainError2 = new TransactionRevertedError("evm", txHash);
|
|
6795
|
+
return {
|
|
6796
|
+
completed: false,
|
|
6797
|
+
error: chainError2.message
|
|
6798
|
+
};
|
|
6799
|
+
}
|
|
6800
|
+
}
|
|
6801
|
+
}
|
|
6699
6802
|
const chainError = toChainStrategyError(
|
|
6700
6803
|
error,
|
|
6701
6804
|
"evm",
|
|
@@ -6809,13 +6912,52 @@ class EvmChainStrategy {
|
|
|
6809
6912
|
return false;
|
|
6810
6913
|
}
|
|
6811
6914
|
}
|
|
6915
|
+
/**
|
|
6916
|
+
* Check if a block has reached finality status (optional, for critical transactions)
|
|
6917
|
+
* This is more stringent than confirmations and protects against long-range reorgs
|
|
6918
|
+
*
|
|
6919
|
+
* Usage: Call this method after waitForCompletion if you need additional security
|
|
6920
|
+
* for high-value transactions. The method checks if the block has been marked as
|
|
6921
|
+
* "finalized" by the Ethereum consensus layer (2/3 of validators).
|
|
6922
|
+
*
|
|
6923
|
+
* @param blockNumber - The block number to check for finality
|
|
6924
|
+
* @returns true if the block is finalized, false otherwise
|
|
6925
|
+
*/
|
|
6926
|
+
async checkFinality(blockNumber) {
|
|
6927
|
+
try {
|
|
6928
|
+
const provider = this.provider;
|
|
6929
|
+
if (!provider) {
|
|
6930
|
+
return false;
|
|
6931
|
+
}
|
|
6932
|
+
const finalizedBlock = await provider.getBlock("finalized");
|
|
6933
|
+
if (!finalizedBlock) {
|
|
6934
|
+
console.debug(
|
|
6935
|
+
"Finalized block not available (pre-merge or unsupported)"
|
|
6936
|
+
);
|
|
6937
|
+
return false;
|
|
6938
|
+
}
|
|
6939
|
+
const isFinalized = blockNumber <= finalizedBlock.number;
|
|
6940
|
+
if (isFinalized) {
|
|
6941
|
+
console.log(
|
|
6942
|
+
`Block ${blockNumber} has reached finality (finalized block: ${finalizedBlock.number})`
|
|
6943
|
+
);
|
|
6944
|
+
} else {
|
|
6945
|
+
console.debug(
|
|
6946
|
+
`Block ${blockNumber} not yet finalized (finalized block: ${finalizedBlock.number})`
|
|
6947
|
+
);
|
|
6948
|
+
}
|
|
6949
|
+
return isFinalized;
|
|
6950
|
+
} catch (error) {
|
|
6951
|
+
console.debug("Error checking finality:", error);
|
|
6952
|
+
return false;
|
|
6953
|
+
}
|
|
6954
|
+
}
|
|
6812
6955
|
}
|
|
6813
6956
|
class TonChainStrategy {
|
|
6814
6957
|
constructor(config) {
|
|
6815
6958
|
__publicField(this, "config");
|
|
6816
6959
|
this.config = config;
|
|
6817
6960
|
}
|
|
6818
|
-
// ========== Identity ==========
|
|
6819
6961
|
canHandle(chainKey) {
|
|
6820
6962
|
return chainKey.toLowerCase() === "ton";
|
|
6821
6963
|
}
|
|
@@ -6825,7 +6967,6 @@ class TonChainStrategy {
|
|
|
6825
6967
|
getName() {
|
|
6826
6968
|
return "TON Chain Strategy";
|
|
6827
6969
|
}
|
|
6828
|
-
// ========== Wallet Management ==========
|
|
6829
6970
|
async connect() {
|
|
6830
6971
|
await this.config.tonConnectUI?.openModal();
|
|
6831
6972
|
}
|
|
@@ -6850,17 +6991,26 @@ class TonChainStrategy {
|
|
|
6850
6991
|
getConnectLabel(t) {
|
|
6851
6992
|
return t("wallets.connectTonWallet");
|
|
6852
6993
|
}
|
|
6853
|
-
|
|
6854
|
-
|
|
6855
|
-
|
|
6994
|
+
async getBalances(address, tokens) {
|
|
6995
|
+
return await getTonBalances(
|
|
6996
|
+
address,
|
|
6997
|
+
tokens,
|
|
6998
|
+
this.config.tonClient,
|
|
6999
|
+
this.config.tonApiKey
|
|
7000
|
+
);
|
|
6856
7001
|
}
|
|
6857
7002
|
isAddressValid(address) {
|
|
6858
7003
|
if (!address) return false;
|
|
6859
7004
|
return true;
|
|
6860
7005
|
}
|
|
6861
|
-
// ========== Gas Estimation ==========
|
|
6862
7006
|
async estimateGasRequirement(params) {
|
|
6863
|
-
const {
|
|
7007
|
+
const {
|
|
7008
|
+
selectedToken,
|
|
7009
|
+
nativeTokenSymbol,
|
|
7010
|
+
amount,
|
|
7011
|
+
balances,
|
|
7012
|
+
reserveFallback
|
|
7013
|
+
} = params;
|
|
6864
7014
|
const nativeSym = nativeTokenSymbol.toUpperCase();
|
|
6865
7015
|
const isNativeSelected = nativeSym === (selectedToken?.symbol ?? "").toUpperCase();
|
|
6866
7016
|
const nativeBalance = Number(balances[nativeSym]?.balance ?? 0);
|
|
@@ -6882,7 +7032,6 @@ class TonChainStrategy {
|
|
|
6882
7032
|
isNativeSelected
|
|
6883
7033
|
};
|
|
6884
7034
|
}
|
|
6885
|
-
// ========== Transaction Execution ==========
|
|
6886
7035
|
validateSteps(steps) {
|
|
6887
7036
|
if (!steps || steps.length === 0) {
|
|
6888
7037
|
throw new InvalidStepsError("ton", "No transaction steps provided");
|
|
@@ -6935,19 +7084,17 @@ class TonChainStrategy {
|
|
|
6935
7084
|
const result = await this.config.tonConnectUI.sendTransaction(
|
|
6936
7085
|
transaction
|
|
6937
7086
|
);
|
|
6938
|
-
const hash = this.getTxHash(result.boc);
|
|
6939
7087
|
return {
|
|
6940
7088
|
chainKey: "ton",
|
|
6941
|
-
hash
|
|
7089
|
+
hash: result.boc
|
|
6942
7090
|
};
|
|
6943
7091
|
} catch (error) {
|
|
6944
7092
|
throw toChainStrategyError(error, "ton", "transaction");
|
|
6945
7093
|
}
|
|
6946
7094
|
}
|
|
6947
|
-
async waitForCompletion(txHash
|
|
7095
|
+
async waitForCompletion(txHash) {
|
|
6948
7096
|
try {
|
|
6949
7097
|
const confirmed = await this.checkTonTransaction(
|
|
6950
|
-
context.srcAddress,
|
|
6951
7098
|
txHash,
|
|
6952
7099
|
TON_CONFIG.timeout
|
|
6953
7100
|
);
|
|
@@ -6977,39 +7124,78 @@ class TonChainStrategy {
|
|
|
6977
7124
|
};
|
|
6978
7125
|
}
|
|
6979
7126
|
}
|
|
6980
|
-
|
|
6981
|
-
|
|
6982
|
-
|
|
6983
|
-
|
|
6984
|
-
|
|
7127
|
+
getNormalizedExtMessageHash(message) {
|
|
7128
|
+
if (message.info.type !== "external-in") {
|
|
7129
|
+
throw new Error(`Expected external-in message, got ${message.info.type}`);
|
|
7130
|
+
}
|
|
7131
|
+
const normalizedInfo = {
|
|
7132
|
+
...message.info,
|
|
7133
|
+
src: void 0,
|
|
7134
|
+
importFee: 0n
|
|
7135
|
+
};
|
|
7136
|
+
const normalizedMessage = {
|
|
7137
|
+
...message,
|
|
7138
|
+
info: normalizedInfo,
|
|
7139
|
+
init: null
|
|
7140
|
+
};
|
|
7141
|
+
return core.beginCell().store(core.storeMessage(normalizedMessage, { forceRef: true })).endCell().hash();
|
|
6985
7142
|
}
|
|
6986
|
-
async checkTonTransaction(
|
|
7143
|
+
async checkTonTransaction(bocBase64, timeoutMs = 36e4) {
|
|
6987
7144
|
const deadline = Date.now() + timeoutMs;
|
|
6988
|
-
const
|
|
6989
|
-
|
|
6990
|
-
|
|
6991
|
-
|
|
6992
|
-
|
|
7145
|
+
const client = getTonClient(this.config.tonClient, this.config.tonApiKey);
|
|
7146
|
+
try {
|
|
7147
|
+
const inMessage = core.loadMessage(core.Cell.fromBase64(bocBase64).beginParse());
|
|
7148
|
+
if (inMessage.info.type !== "external-in") {
|
|
7149
|
+
console.debug(
|
|
7150
|
+
"Expected external-in message, got:",
|
|
7151
|
+
inMessage.info.type
|
|
6993
7152
|
);
|
|
6994
|
-
|
|
6995
|
-
|
|
6996
|
-
|
|
6997
|
-
|
|
6998
|
-
|
|
6999
|
-
|
|
7000
|
-
|
|
7001
|
-
|
|
7002
|
-
const
|
|
7003
|
-
|
|
7004
|
-
|
|
7153
|
+
return false;
|
|
7154
|
+
}
|
|
7155
|
+
const accountAddress = inMessage.info.dest;
|
|
7156
|
+
const targetMessageHash = this.getNormalizedExtMessageHash(inMessage);
|
|
7157
|
+
let lt = void 0;
|
|
7158
|
+
let hash = void 0;
|
|
7159
|
+
while (Date.now() < deadline) {
|
|
7160
|
+
try {
|
|
7161
|
+
const transactions = await client.getTransactions(accountAddress, {
|
|
7162
|
+
lt,
|
|
7163
|
+
hash,
|
|
7164
|
+
limit: 10,
|
|
7165
|
+
archival: true
|
|
7166
|
+
});
|
|
7167
|
+
if (transactions.length === 0) {
|
|
7168
|
+
await new Promise((r) => setTimeout(r, 3e3));
|
|
7169
|
+
lt = void 0;
|
|
7170
|
+
hash = void 0;
|
|
7171
|
+
continue;
|
|
7005
7172
|
}
|
|
7173
|
+
for (const tx of transactions) {
|
|
7174
|
+
if (tx.inMessage?.info.type === "external-in") {
|
|
7175
|
+
const txInMessageHash = this.getNormalizedExtMessageHash(
|
|
7176
|
+
tx.inMessage
|
|
7177
|
+
);
|
|
7178
|
+
if (txInMessageHash.equals(targetMessageHash)) {
|
|
7179
|
+
console.debug("Transaction found by in-message hash");
|
|
7180
|
+
return true;
|
|
7181
|
+
}
|
|
7182
|
+
}
|
|
7183
|
+
}
|
|
7184
|
+
const lastTx = transactions[transactions.length - 1];
|
|
7185
|
+
lt = lastTx.lt.toString();
|
|
7186
|
+
hash = lastTx.hash().toString("base64");
|
|
7187
|
+
} catch (error) {
|
|
7188
|
+
console.debug("Error fetching transactions:", error);
|
|
7189
|
+
await new Promise((r) => setTimeout(r, 3e3));
|
|
7190
|
+
lt = void 0;
|
|
7191
|
+
hash = void 0;
|
|
7006
7192
|
}
|
|
7007
|
-
} catch (e) {
|
|
7008
|
-
console.debug("TonCenter polling error:", e);
|
|
7009
7193
|
}
|
|
7010
|
-
|
|
7194
|
+
return false;
|
|
7195
|
+
} catch (error) {
|
|
7196
|
+
console.debug("Error parsing BOC or checking transaction:", error);
|
|
7197
|
+
return false;
|
|
7011
7198
|
}
|
|
7012
|
-
return false;
|
|
7013
7199
|
}
|
|
7014
7200
|
}
|
|
7015
7201
|
class TronChainStrategy {
|
|
@@ -7070,7 +7256,13 @@ class TronChainStrategy {
|
|
|
7070
7256
|
}
|
|
7071
7257
|
// ========== Gas Estimation ==========
|
|
7072
7258
|
async estimateGasRequirement(params) {
|
|
7073
|
-
const {
|
|
7259
|
+
const {
|
|
7260
|
+
selectedToken,
|
|
7261
|
+
nativeTokenSymbol,
|
|
7262
|
+
amount,
|
|
7263
|
+
balances,
|
|
7264
|
+
reserveFallback
|
|
7265
|
+
} = params;
|
|
7074
7266
|
const nativeSym = nativeTokenSymbol.toUpperCase();
|
|
7075
7267
|
const isNativeSelected = nativeSym === (selectedToken?.symbol ?? "").toUpperCase();
|
|
7076
7268
|
const nativeBalance = Number(balances[nativeSym]?.balance ?? 0);
|
|
@@ -7092,7 +7284,6 @@ class TronChainStrategy {
|
|
|
7092
7284
|
isNativeSelected
|
|
7093
7285
|
};
|
|
7094
7286
|
}
|
|
7095
|
-
// ========== Transaction Execution ==========
|
|
7096
7287
|
validateSteps(steps) {
|
|
7097
7288
|
console.log("validateSteps");
|
|
7098
7289
|
if (!steps?.length) {
|
|
@@ -7127,7 +7318,10 @@ class TronChainStrategy {
|
|
|
7127
7318
|
if (String(step.chainKey).toLowerCase() !== "tron") continue;
|
|
7128
7319
|
const tx = step.transaction;
|
|
7129
7320
|
if (!tx) {
|
|
7130
|
-
throw new InvalidTransactionDataError(
|
|
7321
|
+
throw new InvalidTransactionDataError(
|
|
7322
|
+
"tron",
|
|
7323
|
+
"Missing transaction data"
|
|
7324
|
+
);
|
|
7131
7325
|
}
|
|
7132
7326
|
const hexData = typeof tx?.data === "string" ? tx.data : "";
|
|
7133
7327
|
const parsed = this.parseTronStep(step, tx, hexData);
|
|
@@ -7178,13 +7372,19 @@ class TronChainStrategy {
|
|
|
7178
7372
|
break;
|
|
7179
7373
|
}
|
|
7180
7374
|
default:
|
|
7181
|
-
throw new InvalidStepsError(
|
|
7375
|
+
throw new InvalidStepsError(
|
|
7376
|
+
"tron",
|
|
7377
|
+
"Unsupported TRON parsed tx kind"
|
|
7378
|
+
);
|
|
7182
7379
|
}
|
|
7183
7380
|
const { txid } = await this.signAndBroadcast(tronWeb, unsigned);
|
|
7184
7381
|
lastTxId = txid;
|
|
7185
7382
|
}
|
|
7186
7383
|
if (!lastTxId) {
|
|
7187
|
-
throw new TransactionFailedError(
|
|
7384
|
+
throw new TransactionFailedError(
|
|
7385
|
+
"tron",
|
|
7386
|
+
"No TRON transaction was executed"
|
|
7387
|
+
);
|
|
7188
7388
|
}
|
|
7189
7389
|
return { hash: lastTxId, chainKey: "tron" };
|
|
7190
7390
|
}
|
|
@@ -7194,47 +7394,84 @@ class TronChainStrategy {
|
|
|
7194
7394
|
if (!tronWeb) {
|
|
7195
7395
|
throw new ProviderNotAvailableError("tron");
|
|
7196
7396
|
}
|
|
7397
|
+
console.log(
|
|
7398
|
+
`Waiting for ${TRON_CONFIG.requiredConfirmations} confirmations for TRON tx: ${txHash}`
|
|
7399
|
+
);
|
|
7197
7400
|
const deadline = Date.now() + TRON_CONFIG.timeout;
|
|
7198
|
-
|
|
7401
|
+
let txBlockNumber = null;
|
|
7402
|
+
while (Date.now() < deadline && !txBlockNumber) {
|
|
7199
7403
|
try {
|
|
7200
7404
|
const info = await tronWeb.trx.getTransactionInfo(txHash);
|
|
7201
|
-
|
|
7202
|
-
if (info) {
|
|
7405
|
+
if (info && info.blockNumber) {
|
|
7203
7406
|
const result = info.receipt?.result;
|
|
7204
|
-
if (result
|
|
7205
|
-
|
|
7407
|
+
if (result !== "SUCCESS") {
|
|
7408
|
+
const msg = this.hexToAscii(info.resMessage) || null;
|
|
7409
|
+
let reason = msg;
|
|
7410
|
+
const cr = info.contractResult?.[0];
|
|
7411
|
+
if (cr && /^0x?08c379a0/i.test(cr)) {
|
|
7412
|
+
try {
|
|
7413
|
+
const clean = cr.replace(/^0x/, "");
|
|
7414
|
+
const len = parseInt(clean.slice(8 + 64, 8 + 64 + 64), 16);
|
|
7415
|
+
const strHex = clean.slice(
|
|
7416
|
+
8 + 64 + 64,
|
|
7417
|
+
8 + 64 + 64 + len * 2
|
|
7418
|
+
);
|
|
7419
|
+
const str = this.hexToAscii("0x" + strHex);
|
|
7420
|
+
if (str) reason = str;
|
|
7421
|
+
} catch (e) {
|
|
7422
|
+
console.debug("TRON revert string decode error", e);
|
|
7423
|
+
}
|
|
7424
|
+
}
|
|
7425
|
+
const error2 = new TransactionRevertedError(
|
|
7426
|
+
"tron",
|
|
7427
|
+
txHash,
|
|
7428
|
+
reason || "Unknown error"
|
|
7429
|
+
);
|
|
7206
7430
|
return {
|
|
7207
|
-
completed:
|
|
7431
|
+
completed: false,
|
|
7432
|
+
error: error2.message
|
|
7208
7433
|
};
|
|
7209
7434
|
}
|
|
7210
|
-
|
|
7211
|
-
|
|
7212
|
-
|
|
7213
|
-
|
|
7214
|
-
|
|
7215
|
-
|
|
7216
|
-
|
|
7217
|
-
|
|
7218
|
-
|
|
7219
|
-
|
|
7220
|
-
|
|
7221
|
-
|
|
7222
|
-
|
|
7435
|
+
txBlockNumber = info.blockNumber;
|
|
7436
|
+
console.log(`TRON transaction found in block ${txBlockNumber}`);
|
|
7437
|
+
}
|
|
7438
|
+
} catch (e) {
|
|
7439
|
+
console.debug("TRON getTransactionInfo error:", e);
|
|
7440
|
+
}
|
|
7441
|
+
if (!txBlockNumber) {
|
|
7442
|
+
await new Promise((r) => setTimeout(r, TRON_CONFIG.pollingInterval));
|
|
7443
|
+
}
|
|
7444
|
+
}
|
|
7445
|
+
if (!txBlockNumber) {
|
|
7446
|
+
const error2 = new TransactionTimeoutError("tron", txHash);
|
|
7447
|
+
return {
|
|
7448
|
+
completed: false,
|
|
7449
|
+
error: error2.message
|
|
7450
|
+
};
|
|
7451
|
+
}
|
|
7452
|
+
let confirmations = 0;
|
|
7453
|
+
while (Date.now() < deadline) {
|
|
7454
|
+
try {
|
|
7455
|
+
const currentBlock = await tronWeb.trx.getCurrentBlock();
|
|
7456
|
+
const currentBlockNumber = currentBlock?.block_header?.raw_data?.number;
|
|
7457
|
+
if (currentBlockNumber) {
|
|
7458
|
+
confirmations = currentBlockNumber - txBlockNumber;
|
|
7459
|
+
if (confirmations >= TRON_CONFIG.requiredConfirmations) {
|
|
7460
|
+
console.log(
|
|
7461
|
+
`TRON transaction confirmed in block ${txBlockNumber} with ${confirmations} confirmations`
|
|
7462
|
+
);
|
|
7463
|
+
return {
|
|
7464
|
+
completed: true
|
|
7465
|
+
};
|
|
7223
7466
|
}
|
|
7224
|
-
|
|
7225
|
-
|
|
7226
|
-
txHash,
|
|
7227
|
-
reason || "Unknown error"
|
|
7467
|
+
console.log(
|
|
7468
|
+
`TRON transaction confirmations: ${confirmations}/${TRON_CONFIG.requiredConfirmations}`
|
|
7228
7469
|
);
|
|
7229
|
-
return {
|
|
7230
|
-
completed: false,
|
|
7231
|
-
error: error2.message
|
|
7232
|
-
};
|
|
7233
7470
|
}
|
|
7234
7471
|
} catch (e) {
|
|
7235
|
-
console.debug("TRON
|
|
7472
|
+
console.debug("TRON getCurrentBlock error:", e);
|
|
7236
7473
|
}
|
|
7237
|
-
await new Promise((r) => setTimeout(r,
|
|
7474
|
+
await new Promise((r) => setTimeout(r, TRON_CONFIG.pollingInterval));
|
|
7238
7475
|
}
|
|
7239
7476
|
const error = new TransactionTimeoutError("tron", txHash);
|
|
7240
7477
|
return {
|
|
@@ -7242,14 +7479,17 @@ class TronChainStrategy {
|
|
|
7242
7479
|
error: error.message
|
|
7243
7480
|
};
|
|
7244
7481
|
} catch (error) {
|
|
7245
|
-
const chainError = toChainStrategyError(
|
|
7482
|
+
const chainError = toChainStrategyError(
|
|
7483
|
+
error,
|
|
7484
|
+
"tron",
|
|
7485
|
+
"waitForCompletion"
|
|
7486
|
+
);
|
|
7246
7487
|
return {
|
|
7247
7488
|
completed: false,
|
|
7248
7489
|
error: chainError.message
|
|
7249
7490
|
};
|
|
7250
7491
|
}
|
|
7251
7492
|
}
|
|
7252
|
-
// ========== Private Helper Methods ==========
|
|
7253
7493
|
getTronWeb() {
|
|
7254
7494
|
return typeof window !== "undefined" ? window.tronWeb : void 0;
|
|
7255
7495
|
}
|
|
@@ -7302,7 +7542,10 @@ class TronChainStrategy {
|
|
|
7302
7542
|
amount: this.extractAmountFromTxData(tx.data)
|
|
7303
7543
|
};
|
|
7304
7544
|
}
|
|
7305
|
-
throw new InvalidTransactionDataError(
|
|
7545
|
+
throw new InvalidTransactionDataError(
|
|
7546
|
+
"tron",
|
|
7547
|
+
"Cannot parse approve transaction"
|
|
7548
|
+
);
|
|
7306
7549
|
}
|
|
7307
7550
|
if (step?.type === "transfer" || step?.type === "bridge") {
|
|
7308
7551
|
const s = step;
|
|
@@ -7332,7 +7575,10 @@ class TronChainStrategy {
|
|
|
7332
7575
|
feeLimit: raw2.feeLimit
|
|
7333
7576
|
};
|
|
7334
7577
|
}
|
|
7335
|
-
throw new InvalidTransactionDataError(
|
|
7578
|
+
throw new InvalidTransactionDataError(
|
|
7579
|
+
"tron",
|
|
7580
|
+
"Cannot parse transfer/bridge transaction"
|
|
7581
|
+
);
|
|
7336
7582
|
}
|
|
7337
7583
|
if (tx?.to && tx?.value && !tx?.data) {
|
|
7338
7584
|
const v = BigInt(tx.value.toString());
|
|
@@ -7352,19 +7598,28 @@ class TronChainStrategy {
|
|
|
7352
7598
|
feeLimit: raw.feeLimit
|
|
7353
7599
|
};
|
|
7354
7600
|
}
|
|
7355
|
-
throw new InvalidTransactionDataError(
|
|
7601
|
+
throw new InvalidTransactionDataError(
|
|
7602
|
+
"tron",
|
|
7603
|
+
`Unsupported TRON step type: ${step?.type ?? "unknown"}`
|
|
7604
|
+
);
|
|
7356
7605
|
}
|
|
7357
7606
|
extractSpenderFromTxData(data) {
|
|
7358
7607
|
const clean = data.replace(/^0x/, "");
|
|
7359
7608
|
if (clean.length < 74) {
|
|
7360
|
-
throw new InvalidTransactionDataError(
|
|
7609
|
+
throw new InvalidTransactionDataError(
|
|
7610
|
+
"tron",
|
|
7611
|
+
"Invalid transaction data length"
|
|
7612
|
+
);
|
|
7361
7613
|
}
|
|
7362
7614
|
return "41" + clean.slice(32, 72);
|
|
7363
7615
|
}
|
|
7364
7616
|
extractAmountFromTxData(data) {
|
|
7365
7617
|
const clean = data.replace(/^0x/, "");
|
|
7366
7618
|
if (clean.length < 138) {
|
|
7367
|
-
throw new InvalidTransactionDataError(
|
|
7619
|
+
throw new InvalidTransactionDataError(
|
|
7620
|
+
"tron",
|
|
7621
|
+
"Invalid transaction data length"
|
|
7622
|
+
);
|
|
7368
7623
|
}
|
|
7369
7624
|
const amountHex = clean.slice(72, 136);
|
|
7370
7625
|
return BigInt("0x" + amountHex).toString();
|
|
@@ -7372,7 +7627,10 @@ class TronChainStrategy {
|
|
|
7372
7627
|
extractRecipientFromTxData(data) {
|
|
7373
7628
|
const clean = data.replace(/^0x/, "");
|
|
7374
7629
|
if (clean.length < 74) {
|
|
7375
|
-
throw new InvalidTransactionDataError(
|
|
7630
|
+
throw new InvalidTransactionDataError(
|
|
7631
|
+
"tron",
|
|
7632
|
+
"Invalid transaction data length"
|
|
7633
|
+
);
|
|
7376
7634
|
}
|
|
7377
7635
|
return "41" + clean.slice(32, 72);
|
|
7378
7636
|
}
|
|
@@ -7447,7 +7705,6 @@ class TronChainStrategy {
|
|
|
7447
7705
|
return null;
|
|
7448
7706
|
}
|
|
7449
7707
|
}
|
|
7450
|
-
// ========== Transaction Builders ==========
|
|
7451
7708
|
async buildApprove(tronWeb, p) {
|
|
7452
7709
|
const res = await tronWeb.transactionBuilder.triggerSmartContract(
|
|
7453
7710
|
p.token,
|
|
@@ -7460,7 +7717,10 @@ class TronChainStrategy {
|
|
|
7460
7717
|
p.from
|
|
7461
7718
|
);
|
|
7462
7719
|
if (!res?.transaction) {
|
|
7463
|
-
throw new TransactionFailedError(
|
|
7720
|
+
throw new TransactionFailedError(
|
|
7721
|
+
"tron",
|
|
7722
|
+
"Failed to build approve transaction"
|
|
7723
|
+
);
|
|
7464
7724
|
}
|
|
7465
7725
|
return res.transaction;
|
|
7466
7726
|
}
|
|
@@ -7476,7 +7736,10 @@ class TronChainStrategy {
|
|
|
7476
7736
|
p.from
|
|
7477
7737
|
);
|
|
7478
7738
|
if (!res?.transaction) {
|
|
7479
|
-
throw new TransactionFailedError(
|
|
7739
|
+
throw new TransactionFailedError(
|
|
7740
|
+
"tron",
|
|
7741
|
+
"Failed to build transfer transaction"
|
|
7742
|
+
);
|
|
7480
7743
|
}
|
|
7481
7744
|
return res.transaction;
|
|
7482
7745
|
}
|
|
@@ -7496,12 +7759,13 @@ class TronChainStrategy {
|
|
|
7496
7759
|
p.from
|
|
7497
7760
|
);
|
|
7498
7761
|
if (!res?.transaction) {
|
|
7499
|
-
throw new TransactionFailedError(
|
|
7762
|
+
throw new TransactionFailedError(
|
|
7763
|
+
"tron",
|
|
7764
|
+
"Failed to build raw call transaction"
|
|
7765
|
+
);
|
|
7500
7766
|
}
|
|
7501
7767
|
return res.transaction;
|
|
7502
7768
|
}
|
|
7503
|
-
// ========== Transaction Sender ==========
|
|
7504
|
-
/* eslint-disable @typescript-eslint/no-explicit-any */
|
|
7505
7769
|
async signAndBroadcast(tronWeb, unsignedTx) {
|
|
7506
7770
|
const signed = await tronWeb.trx.sign(unsignedTx);
|
|
7507
7771
|
const sent = await tronWeb.trx.sendRawTransaction(signed);
|
|
@@ -7513,33 +7777,77 @@ class TronChainStrategy {
|
|
|
7513
7777
|
}
|
|
7514
7778
|
return { txid: sent.txid };
|
|
7515
7779
|
}
|
|
7780
|
+
/**
|
|
7781
|
+
* Check if a transaction has been solidified (confirmed by solidityNode)
|
|
7782
|
+
* This is an additional check for critical transactions to ensure they are
|
|
7783
|
+
* truly confirmed and available through the solidityNode API.
|
|
7784
|
+
*
|
|
7785
|
+
* Usage: Call this method after waitForCompletion for high-value transactions
|
|
7786
|
+
* to get additional assurance that the transaction is solidified.
|
|
7787
|
+
*
|
|
7788
|
+
* @param txHash - Transaction hash to check
|
|
7789
|
+
* @returns true if the transaction is solidified, false otherwise
|
|
7790
|
+
*/
|
|
7791
|
+
async checkSolidified(txHash) {
|
|
7792
|
+
try {
|
|
7793
|
+
const tronWeb = this.getTronWeb();
|
|
7794
|
+
if (!tronWeb) {
|
|
7795
|
+
return false;
|
|
7796
|
+
}
|
|
7797
|
+
const info = await tronWeb.trx.getTransactionInfo(txHash);
|
|
7798
|
+
if (!info || !info.blockNumber) {
|
|
7799
|
+
console.debug(
|
|
7800
|
+
"Transaction not yet solidified (no blockNumber in info)"
|
|
7801
|
+
);
|
|
7802
|
+
return false;
|
|
7803
|
+
}
|
|
7804
|
+
const result = info.receipt?.result;
|
|
7805
|
+
if (result === "SUCCESS") {
|
|
7806
|
+
console.log(
|
|
7807
|
+
`Transaction ${txHash} is solidified in block ${info.blockNumber}`
|
|
7808
|
+
);
|
|
7809
|
+
return true;
|
|
7810
|
+
}
|
|
7811
|
+
console.debug(`Transaction solidified but result is: ${result}`);
|
|
7812
|
+
return false;
|
|
7813
|
+
} catch (error) {
|
|
7814
|
+
console.debug("Error checking solidified status:", error);
|
|
7815
|
+
return false;
|
|
7816
|
+
}
|
|
7817
|
+
}
|
|
7516
7818
|
}
|
|
7517
7819
|
function ChainStrategyProvider({
|
|
7518
7820
|
children,
|
|
7519
7821
|
evmWallet,
|
|
7520
7822
|
tonWallet,
|
|
7521
|
-
tronWallet
|
|
7823
|
+
tronWallet,
|
|
7824
|
+
tonClient,
|
|
7825
|
+
tonApiKey
|
|
7522
7826
|
}) {
|
|
7523
7827
|
const evmStrategy = require$$0.useMemo(
|
|
7524
7828
|
() => new EvmChainStrategy({
|
|
7525
7829
|
evmAddress: evmWallet.address,
|
|
7526
7830
|
evmIsConnected: evmWallet.isConnected,
|
|
7527
7831
|
evmDisconnect: evmWallet.disconnect,
|
|
7528
|
-
walletClient: evmWallet.walletClient
|
|
7832
|
+
walletClient: evmWallet.walletClient,
|
|
7833
|
+
publicClient: evmWallet.publicClient
|
|
7529
7834
|
}),
|
|
7530
7835
|
[
|
|
7531
7836
|
evmWallet.address,
|
|
7532
7837
|
evmWallet.isConnected,
|
|
7533
7838
|
evmWallet.disconnect,
|
|
7534
|
-
evmWallet.walletClient
|
|
7839
|
+
evmWallet.walletClient,
|
|
7840
|
+
evmWallet.publicClient
|
|
7535
7841
|
]
|
|
7536
7842
|
);
|
|
7537
7843
|
const tonStrategy = require$$0.useMemo(
|
|
7538
7844
|
() => new TonChainStrategy({
|
|
7539
7845
|
tonConnectUI: tonWallet.tonConnectUI,
|
|
7540
|
-
tonAddress: tonWallet.address
|
|
7846
|
+
tonAddress: tonWallet.address,
|
|
7847
|
+
tonClient,
|
|
7848
|
+
tonApiKey
|
|
7541
7849
|
}),
|
|
7542
|
-
[tonWallet.tonConnectUI, tonWallet.address]
|
|
7850
|
+
[tonWallet.tonConnectUI, tonWallet.address, tonClient, tonApiKey]
|
|
7543
7851
|
);
|
|
7544
7852
|
const tronStrategy = require$$0.useMemo(
|
|
7545
7853
|
() => new TronChainStrategy({
|
|
@@ -7575,6 +7883,7 @@ const EvaaBridgeWithProviders = (props) => {
|
|
|
7575
7883
|
const { address: evmAddress, isConnected: evmIsConnected } = wagmi.useAccount();
|
|
7576
7884
|
const { disconnect: evmDisconnect } = wagmi.useDisconnect();
|
|
7577
7885
|
const { data: walletClient } = wagmi.useWalletClient();
|
|
7886
|
+
const publicClient = wagmi.usePublicClient();
|
|
7578
7887
|
const {
|
|
7579
7888
|
address: tronAddress,
|
|
7580
7889
|
connected: tronConnected,
|
|
@@ -7592,14 +7901,15 @@ const EvaaBridgeWithProviders = (props) => {
|
|
|
7592
7901
|
require$$0.useEffect(() => {
|
|
7593
7902
|
setTronConnected(!!tronConnected);
|
|
7594
7903
|
}, [tronConnected, setTronConnected]);
|
|
7595
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
7904
|
+
return /* @__PURE__ */ jsxRuntime.jsx(ModalContainerProvider, { containerId: props.modalContainerId, children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
7596
7905
|
ChainStrategyProvider,
|
|
7597
7906
|
{
|
|
7598
7907
|
evmWallet: {
|
|
7599
7908
|
address: evmAddress,
|
|
7600
7909
|
isConnected: evmIsConnected,
|
|
7601
7910
|
disconnect: evmDisconnect,
|
|
7602
|
-
walletClient
|
|
7911
|
+
walletClient,
|
|
7912
|
+
publicClient
|
|
7603
7913
|
},
|
|
7604
7914
|
tonWallet: {
|
|
7605
7915
|
tonConnectUI,
|
|
@@ -7612,9 +7922,11 @@ const EvaaBridgeWithProviders = (props) => {
|
|
|
7612
7922
|
connect: tronConnect,
|
|
7613
7923
|
disconnect: tronDisconnect
|
|
7614
7924
|
},
|
|
7925
|
+
tonClient: props.tonClient,
|
|
7926
|
+
tonApiKey: props.tonApiKey,
|
|
7615
7927
|
children: /* @__PURE__ */ jsxRuntime.jsx(EvaaBridgeContent, { ...props })
|
|
7616
7928
|
}
|
|
7617
|
-
);
|
|
7929
|
+
) });
|
|
7618
7930
|
};
|
|
7619
7931
|
const EvaaBridgeContent = ({
|
|
7620
7932
|
className,
|
|
@@ -7623,7 +7935,6 @@ const EvaaBridgeContent = ({
|
|
|
7623
7935
|
onChainChange
|
|
7624
7936
|
} = {}) => {
|
|
7625
7937
|
const { t } = reactI18next.useTranslation();
|
|
7626
|
-
const modalContainerRef = require$$0.useRef(null);
|
|
7627
7938
|
useTokensRequest();
|
|
7628
7939
|
useChainsRequest();
|
|
7629
7940
|
const [sendToAnother, setSendToAnother] = require$$0.useState(false);
|
|
@@ -7716,16 +8027,15 @@ const EvaaBridgeContent = ({
|
|
|
7716
8027
|
}, [chains, assetMatrix, allowedFromChains]);
|
|
7717
8028
|
return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
7718
8029
|
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
7719
|
-
|
|
8030
|
+
Card,
|
|
7720
8031
|
{
|
|
7721
8032
|
className: cn(
|
|
7722
|
-
"
|
|
8033
|
+
"max-w-md w-full mx-auto flex flex-col relative",
|
|
7723
8034
|
className
|
|
7724
8035
|
),
|
|
7725
|
-
ref: modalContainerRef,
|
|
7726
8036
|
children: [
|
|
7727
|
-
/* @__PURE__ */ jsxRuntime.jsx(FormHeader, {
|
|
7728
|
-
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
8037
|
+
/* @__PURE__ */ jsxRuntime.jsx(FormHeader, {}),
|
|
8038
|
+
/* @__PURE__ */ jsxRuntime.jsxs(CardContent, { className: "space-y-[1px]", children: [
|
|
7729
8039
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7730
8040
|
SwapSection,
|
|
7731
8041
|
{
|
|
@@ -7738,8 +8048,7 @@ const EvaaBridgeContent = ({
|
|
|
7738
8048
|
amount,
|
|
7739
8049
|
isSource: true,
|
|
7740
8050
|
onAmountChange: handleAmountChange,
|
|
7741
|
-
onSelect: handleFromChainChange
|
|
7742
|
-
modalContainer: modalContainerRef.current || void 0
|
|
8051
|
+
onSelect: handleFromChainChange
|
|
7743
8052
|
}
|
|
7744
8053
|
),
|
|
7745
8054
|
/* @__PURE__ */ jsxRuntime.jsx(SwapButton, {}),
|
|
@@ -7753,8 +8062,7 @@ const EvaaBridgeContent = ({
|
|
|
7753
8062
|
allowedChains: allowedToChains,
|
|
7754
8063
|
amount: outputAmount,
|
|
7755
8064
|
readOnlyAmount: true,
|
|
7756
|
-
onSelect: handleToChainChange
|
|
7757
|
-
modalContainer: modalContainerRef.current || void 0
|
|
8065
|
+
onSelect: handleToChainChange
|
|
7758
8066
|
}
|
|
7759
8067
|
),
|
|
7760
8068
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
@@ -7763,15 +8071,15 @@ const EvaaBridgeContent = ({
|
|
|
7763
8071
|
enabled: sendToAnother,
|
|
7764
8072
|
onToggle: () => setSendToAnother((v) => !v)
|
|
7765
8073
|
}
|
|
7766
|
-
)
|
|
8074
|
+
),
|
|
8075
|
+
/* @__PURE__ */ jsxRuntime.jsx(SubmitButton, {})
|
|
7767
8076
|
] }),
|
|
7768
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7769
|
-
/* @__PURE__ */ jsxRuntime.jsx(ReceiveRow, {})
|
|
8077
|
+
/* @__PURE__ */ jsxRuntime.jsx(CardFooter, { children: /* @__PURE__ */ jsxRuntime.jsx(ReceiveRow, {}) })
|
|
7770
8078
|
]
|
|
7771
8079
|
}
|
|
7772
8080
|
),
|
|
7773
|
-
/* @__PURE__ */ jsxRuntime.jsx(WalletSelectModal, {
|
|
7774
|
-
/* @__PURE__ */ jsxRuntime.jsx(TransactionManager, {
|
|
8081
|
+
/* @__PURE__ */ jsxRuntime.jsx(WalletSelectModal, {}),
|
|
8082
|
+
/* @__PURE__ */ jsxRuntime.jsx(TransactionManager, {}),
|
|
7775
8083
|
/* @__PURE__ */ jsxRuntime.jsx(sonner.Toaster, { position: "top-right", richColors: true })
|
|
7776
8084
|
] });
|
|
7777
8085
|
};
|
|
@@ -7854,8 +8162,8 @@ exports.getQuoteAmounts = getQuoteAmounts;
|
|
|
7854
8162
|
exports.getQuoteDetails = getQuoteDetails;
|
|
7855
8163
|
exports.getQuoteFees = getQuoteFees;
|
|
7856
8164
|
exports.getQuotesByPriority = getQuotesByPriority;
|
|
7857
|
-
exports.getSwapBalances = getSwapBalances;
|
|
7858
8165
|
exports.getTokens = getTokens;
|
|
8166
|
+
exports.getTonBalances = getTonBalances;
|
|
7859
8167
|
exports.getTronBalances = getTronBalances;
|
|
7860
8168
|
exports.isAddressValidForChain = isAddressValidForChain;
|
|
7861
8169
|
exports.isEvmAddress = isEvmAddress;
|
|
@@ -7864,7 +8172,7 @@ exports.isTronAddress = isTronAddress;
|
|
|
7864
8172
|
exports.isZeroAddr = isZeroAddr;
|
|
7865
8173
|
exports.listAssetsForSelect = listAssetsForSelect;
|
|
7866
8174
|
exports.lookupTokenMeta = lookupTokenMeta;
|
|
7867
|
-
exports.normalizeTickerSymbol = normalizeTickerSymbol;
|
|
8175
|
+
exports.normalizeTickerSymbol = normalizeTickerSymbol$1;
|
|
7868
8176
|
exports.pollUntilDelivered = pollUntilDelivered;
|
|
7869
8177
|
exports.resolveTokenOnChain = resolveTokenOnChain;
|
|
7870
8178
|
exports.resolveTokenOnChainFromMatrix = resolveTokenOnChainFromMatrix$2;
|