@zubari/sdk 0.5.1 → 0.5.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/dist/index.js +800 -230
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +798 -228
- package/dist/index.mjs.map +1 -1
- package/dist/protocols/index.js.map +1 -1
- package/dist/protocols/index.mjs.map +1 -1
- package/dist/react/index.js +744 -174
- package/dist/react/index.js.map +1 -1
- package/dist/react/index.mjs +742 -172
- package/dist/react/index.mjs.map +1 -1
- package/dist/services/index.js +708 -114
- package/dist/services/index.js.map +1 -1
- package/dist/services/index.mjs +706 -112
- package/dist/services/index.mjs.map +1 -1
- package/dist/wallet/index.js +745 -175
- package/dist/wallet/index.js.map +1 -1
- package/dist/wallet/index.mjs +743 -173
- package/dist/wallet/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -3,8 +3,11 @@
|
|
|
3
3
|
var ethers = require('ethers');
|
|
4
4
|
var bip39 = require('@scure/bip39');
|
|
5
5
|
var english = require('@scure/bip39/wordlists/english');
|
|
6
|
-
var
|
|
7
|
-
var
|
|
6
|
+
var secp256k1_js = require('@noble/curves/secp256k1.js');
|
|
7
|
+
var hmac_js = require('@noble/hashes/hmac.js');
|
|
8
|
+
var legacy_js = require('@noble/hashes/legacy.js');
|
|
9
|
+
var sha2_js = require('@noble/hashes/sha2.js');
|
|
10
|
+
var utils_js = require('@noble/hashes/utils.js');
|
|
8
11
|
var sha256 = require('@noble/hashes/sha256');
|
|
9
12
|
var ripemd160 = require('@noble/hashes/ripemd160');
|
|
10
13
|
var viem = require('viem');
|
|
@@ -137,8 +140,8 @@ var TESTNET_NETWORKS = {
|
|
|
137
140
|
var USDT_ADDRESSES = {
|
|
138
141
|
ethereum: {
|
|
139
142
|
mainnet: "0xdAC17F958D2ee523a2206206994597C13D831ec7",
|
|
140
|
-
testnet: "
|
|
141
|
-
// Sepolia
|
|
143
|
+
testnet: "0xaA8E23Fb1079EA71e0a56F48a2aA51851D8433D0"
|
|
144
|
+
// Sepolia
|
|
142
145
|
},
|
|
143
146
|
tron: {
|
|
144
147
|
mainnet: "TR7NHqjeKQxGTCi8q8ZY4pL8otSzgjLj6t",
|
|
@@ -388,15 +391,15 @@ var TESTNET_FEE_WALLETS = {
|
|
|
388
391
|
name: "Zubari TON Testnet Treasury",
|
|
389
392
|
network: "ton-testnet"
|
|
390
393
|
},
|
|
391
|
-
// Tron
|
|
394
|
+
// Tron Nile Testnet
|
|
392
395
|
TRON: {
|
|
393
396
|
address: "",
|
|
394
397
|
name: "Zubari Tron Testnet Treasury",
|
|
395
|
-
network: "tron-
|
|
398
|
+
network: "tron-nile"
|
|
396
399
|
}
|
|
397
400
|
};
|
|
398
|
-
function getFeeWallet(
|
|
399
|
-
return isMainnet2 ? MAINNET_FEE_WALLETS[
|
|
401
|
+
function getFeeWallet(chain2, isMainnet2 = true) {
|
|
402
|
+
return isMainnet2 ? MAINNET_FEE_WALLETS[chain2] : TESTNET_FEE_WALLETS[chain2];
|
|
400
403
|
}
|
|
401
404
|
function getAllFeeWallets(useMainnet = false) {
|
|
402
405
|
return useMainnet ? MAINNET_FEE_WALLETS : TESTNET_FEE_WALLETS;
|
|
@@ -413,8 +416,8 @@ function getDefaultSubscriptionAddress() {
|
|
|
413
416
|
function getCurrentFeeWallets() {
|
|
414
417
|
return isMainnet() ? MAINNET_FEE_WALLETS : TESTNET_FEE_WALLETS;
|
|
415
418
|
}
|
|
416
|
-
function getCurrentFeeWallet(
|
|
417
|
-
return getCurrentFeeWallets()[
|
|
419
|
+
function getCurrentFeeWallet(chain2) {
|
|
420
|
+
return getCurrentFeeWallets()[chain2];
|
|
418
421
|
}
|
|
419
422
|
function getCurrentCurrencyAddresses() {
|
|
420
423
|
return CURRENCY_ADDRESSES[getZubariNetwork()];
|
|
@@ -471,14 +474,14 @@ var WdkApiClient = class {
|
|
|
471
474
|
/**
|
|
472
475
|
* Derive address for a specific chain using Tether WDK
|
|
473
476
|
*/
|
|
474
|
-
async deriveAddress(seed,
|
|
477
|
+
async deriveAddress(seed, chain2, network = "mainnet") {
|
|
475
478
|
try {
|
|
476
479
|
const response = await fetch(`${this.config.baseUrl}/api/wallets/wdk/derive-address`, {
|
|
477
480
|
method: "POST",
|
|
478
481
|
headers: {
|
|
479
482
|
"Content-Type": "application/json"
|
|
480
483
|
},
|
|
481
|
-
body: JSON.stringify({ seed, chain, network })
|
|
484
|
+
body: JSON.stringify({ seed, chain: chain2, network })
|
|
482
485
|
});
|
|
483
486
|
return await response.json();
|
|
484
487
|
} catch (error) {
|
|
@@ -511,14 +514,14 @@ var WdkApiClient = class {
|
|
|
511
514
|
/**
|
|
512
515
|
* Send a transaction on a specific chain using Tether WDK
|
|
513
516
|
*/
|
|
514
|
-
async sendTransaction(seed,
|
|
517
|
+
async sendTransaction(seed, chain2, to, amount, network = "mainnet") {
|
|
515
518
|
try {
|
|
516
519
|
const response = await fetch(`${this.config.baseUrl}/api/wallets/wdk/send`, {
|
|
517
520
|
method: "POST",
|
|
518
521
|
headers: {
|
|
519
522
|
"Content-Type": "application/json"
|
|
520
523
|
},
|
|
521
|
-
body: JSON.stringify({ seed, chain, to, amount, network })
|
|
524
|
+
body: JSON.stringify({ seed, chain: chain2, to, amount, network })
|
|
522
525
|
});
|
|
523
526
|
return await response.json();
|
|
524
527
|
} catch (error) {
|
|
@@ -532,14 +535,14 @@ var WdkApiClient = class {
|
|
|
532
535
|
* Get transaction history for an address on a specific chain
|
|
533
536
|
* Fetches from blockchain explorers (Etherscan, mempool.space, etc.)
|
|
534
537
|
*/
|
|
535
|
-
async getTransactionHistory(seed,
|
|
538
|
+
async getTransactionHistory(seed, chain2, network = "mainnet", limit = 10) {
|
|
536
539
|
try {
|
|
537
540
|
const response = await fetch(`${this.config.baseUrl}/api/wallets/wdk/history`, {
|
|
538
541
|
method: "POST",
|
|
539
542
|
headers: {
|
|
540
543
|
"Content-Type": "application/json"
|
|
541
544
|
},
|
|
542
|
-
body: JSON.stringify({ seed, chain, network, limit })
|
|
545
|
+
body: JSON.stringify({ seed, chain: chain2, network, limit })
|
|
543
546
|
});
|
|
544
547
|
return await response.json();
|
|
545
548
|
} catch (error) {
|
|
@@ -553,14 +556,14 @@ var WdkApiClient = class {
|
|
|
553
556
|
* Get transaction status by hash
|
|
554
557
|
* Fetches from blockchain explorers to check confirmation status
|
|
555
558
|
*/
|
|
556
|
-
async getTransactionStatus(txHash,
|
|
559
|
+
async getTransactionStatus(txHash, chain2, network = "mainnet") {
|
|
557
560
|
try {
|
|
558
561
|
const response = await fetch(`${this.config.baseUrl}/api/wallets/wdk/tx-status`, {
|
|
559
562
|
method: "POST",
|
|
560
563
|
headers: {
|
|
561
564
|
"Content-Type": "application/json"
|
|
562
565
|
},
|
|
563
|
-
body: JSON.stringify({ txHash, chain, network })
|
|
566
|
+
body: JSON.stringify({ txHash, chain: chain2, network })
|
|
564
567
|
});
|
|
565
568
|
return await response.json();
|
|
566
569
|
} catch (error) {
|
|
@@ -595,6 +598,589 @@ __export(BrowserAddressDerivation_exports, {
|
|
|
595
598
|
generateSeedPhrase: () => generateSeedPhrase,
|
|
596
599
|
isValidSeed: () => isValidSeed
|
|
597
600
|
});
|
|
601
|
+
|
|
602
|
+
// node_modules/@scure/base/index.js
|
|
603
|
+
function isBytes(a) {
|
|
604
|
+
return a instanceof Uint8Array || ArrayBuffer.isView(a) && a.constructor.name === "Uint8Array";
|
|
605
|
+
}
|
|
606
|
+
function isArrayOf(isString, arr) {
|
|
607
|
+
if (!Array.isArray(arr))
|
|
608
|
+
return false;
|
|
609
|
+
if (arr.length === 0)
|
|
610
|
+
return true;
|
|
611
|
+
if (isString) {
|
|
612
|
+
return arr.every((item) => typeof item === "string");
|
|
613
|
+
} else {
|
|
614
|
+
return arr.every((item) => Number.isSafeInteger(item));
|
|
615
|
+
}
|
|
616
|
+
}
|
|
617
|
+
function afn(input) {
|
|
618
|
+
if (typeof input !== "function")
|
|
619
|
+
throw new Error("function expected");
|
|
620
|
+
return true;
|
|
621
|
+
}
|
|
622
|
+
function astr(label, input) {
|
|
623
|
+
if (typeof input !== "string")
|
|
624
|
+
throw new Error(`${label}: string expected`);
|
|
625
|
+
return true;
|
|
626
|
+
}
|
|
627
|
+
function anumber(n) {
|
|
628
|
+
if (!Number.isSafeInteger(n))
|
|
629
|
+
throw new Error(`invalid integer: ${n}`);
|
|
630
|
+
}
|
|
631
|
+
function aArr(input) {
|
|
632
|
+
if (!Array.isArray(input))
|
|
633
|
+
throw new Error("array expected");
|
|
634
|
+
}
|
|
635
|
+
function astrArr(label, input) {
|
|
636
|
+
if (!isArrayOf(true, input))
|
|
637
|
+
throw new Error(`${label}: array of strings expected`);
|
|
638
|
+
}
|
|
639
|
+
function anumArr(label, input) {
|
|
640
|
+
if (!isArrayOf(false, input))
|
|
641
|
+
throw new Error(`${label}: array of numbers expected`);
|
|
642
|
+
}
|
|
643
|
+
// @__NO_SIDE_EFFECTS__
|
|
644
|
+
function chain(...args) {
|
|
645
|
+
const id = (a) => a;
|
|
646
|
+
const wrap = (a, b) => (c) => a(b(c));
|
|
647
|
+
const encode = args.map((x) => x.encode).reduceRight(wrap, id);
|
|
648
|
+
const decode = args.map((x) => x.decode).reduce(wrap, id);
|
|
649
|
+
return { encode, decode };
|
|
650
|
+
}
|
|
651
|
+
// @__NO_SIDE_EFFECTS__
|
|
652
|
+
function alphabet(letters) {
|
|
653
|
+
const lettersA = typeof letters === "string" ? letters.split("") : letters;
|
|
654
|
+
const len = lettersA.length;
|
|
655
|
+
astrArr("alphabet", lettersA);
|
|
656
|
+
const indexes = new Map(lettersA.map((l, i) => [l, i]));
|
|
657
|
+
return {
|
|
658
|
+
encode: (digits) => {
|
|
659
|
+
aArr(digits);
|
|
660
|
+
return digits.map((i) => {
|
|
661
|
+
if (!Number.isSafeInteger(i) || i < 0 || i >= len)
|
|
662
|
+
throw new Error(`alphabet.encode: digit index outside alphabet "${i}". Allowed: ${letters}`);
|
|
663
|
+
return lettersA[i];
|
|
664
|
+
});
|
|
665
|
+
},
|
|
666
|
+
decode: (input) => {
|
|
667
|
+
aArr(input);
|
|
668
|
+
return input.map((letter) => {
|
|
669
|
+
astr("alphabet.decode", letter);
|
|
670
|
+
const i = indexes.get(letter);
|
|
671
|
+
if (i === void 0)
|
|
672
|
+
throw new Error(`Unknown letter: "${letter}". Allowed: ${letters}`);
|
|
673
|
+
return i;
|
|
674
|
+
});
|
|
675
|
+
}
|
|
676
|
+
};
|
|
677
|
+
}
|
|
678
|
+
// @__NO_SIDE_EFFECTS__
|
|
679
|
+
function join(separator = "") {
|
|
680
|
+
astr("join", separator);
|
|
681
|
+
return {
|
|
682
|
+
encode: (from) => {
|
|
683
|
+
astrArr("join.decode", from);
|
|
684
|
+
return from.join(separator);
|
|
685
|
+
},
|
|
686
|
+
decode: (to) => {
|
|
687
|
+
astr("join.decode", to);
|
|
688
|
+
return to.split(separator);
|
|
689
|
+
}
|
|
690
|
+
};
|
|
691
|
+
}
|
|
692
|
+
function convertRadix(data, from, to) {
|
|
693
|
+
if (from < 2)
|
|
694
|
+
throw new Error(`convertRadix: invalid from=${from}, base cannot be less than 2`);
|
|
695
|
+
if (to < 2)
|
|
696
|
+
throw new Error(`convertRadix: invalid to=${to}, base cannot be less than 2`);
|
|
697
|
+
aArr(data);
|
|
698
|
+
if (!data.length)
|
|
699
|
+
return [];
|
|
700
|
+
let pos = 0;
|
|
701
|
+
const res = [];
|
|
702
|
+
const digits = Array.from(data, (d) => {
|
|
703
|
+
anumber(d);
|
|
704
|
+
if (d < 0 || d >= from)
|
|
705
|
+
throw new Error(`invalid integer: ${d}`);
|
|
706
|
+
return d;
|
|
707
|
+
});
|
|
708
|
+
const dlen = digits.length;
|
|
709
|
+
while (true) {
|
|
710
|
+
let carry = 0;
|
|
711
|
+
let done = true;
|
|
712
|
+
for (let i = pos; i < dlen; i++) {
|
|
713
|
+
const digit = digits[i];
|
|
714
|
+
const fromCarry = from * carry;
|
|
715
|
+
const digitBase = fromCarry + digit;
|
|
716
|
+
if (!Number.isSafeInteger(digitBase) || fromCarry / from !== carry || digitBase - digit !== fromCarry) {
|
|
717
|
+
throw new Error("convertRadix: carry overflow");
|
|
718
|
+
}
|
|
719
|
+
const div = digitBase / to;
|
|
720
|
+
carry = digitBase % to;
|
|
721
|
+
const rounded = Math.floor(div);
|
|
722
|
+
digits[i] = rounded;
|
|
723
|
+
if (!Number.isSafeInteger(rounded) || rounded * to + carry !== digitBase)
|
|
724
|
+
throw new Error("convertRadix: carry overflow");
|
|
725
|
+
if (!done)
|
|
726
|
+
continue;
|
|
727
|
+
else if (!rounded)
|
|
728
|
+
pos = i;
|
|
729
|
+
else
|
|
730
|
+
done = false;
|
|
731
|
+
}
|
|
732
|
+
res.push(carry);
|
|
733
|
+
if (done)
|
|
734
|
+
break;
|
|
735
|
+
}
|
|
736
|
+
for (let i = 0; i < data.length - 1 && data[i] === 0; i++)
|
|
737
|
+
res.push(0);
|
|
738
|
+
return res.reverse();
|
|
739
|
+
}
|
|
740
|
+
var gcd = (a, b) => b === 0 ? a : gcd(b, a % b);
|
|
741
|
+
var radix2carry = /* @__NO_SIDE_EFFECTS__ */ (from, to) => from + (to - gcd(from, to));
|
|
742
|
+
var powers = /* @__PURE__ */ (() => {
|
|
743
|
+
let res = [];
|
|
744
|
+
for (let i = 0; i < 40; i++)
|
|
745
|
+
res.push(2 ** i);
|
|
746
|
+
return res;
|
|
747
|
+
})();
|
|
748
|
+
function convertRadix2(data, from, to, padding) {
|
|
749
|
+
aArr(data);
|
|
750
|
+
if (from <= 0 || from > 32)
|
|
751
|
+
throw new Error(`convertRadix2: wrong from=${from}`);
|
|
752
|
+
if (to <= 0 || to > 32)
|
|
753
|
+
throw new Error(`convertRadix2: wrong to=${to}`);
|
|
754
|
+
if (/* @__PURE__ */ radix2carry(from, to) > 32) {
|
|
755
|
+
throw new Error(`convertRadix2: carry overflow from=${from} to=${to} carryBits=${/* @__PURE__ */ radix2carry(from, to)}`);
|
|
756
|
+
}
|
|
757
|
+
let carry = 0;
|
|
758
|
+
let pos = 0;
|
|
759
|
+
const max = powers[from];
|
|
760
|
+
const mask = powers[to] - 1;
|
|
761
|
+
const res = [];
|
|
762
|
+
for (const n of data) {
|
|
763
|
+
anumber(n);
|
|
764
|
+
if (n >= max)
|
|
765
|
+
throw new Error(`convertRadix2: invalid data word=${n} from=${from}`);
|
|
766
|
+
carry = carry << from | n;
|
|
767
|
+
if (pos + from > 32)
|
|
768
|
+
throw new Error(`convertRadix2: carry overflow pos=${pos} from=${from}`);
|
|
769
|
+
pos += from;
|
|
770
|
+
for (; pos >= to; pos -= to)
|
|
771
|
+
res.push((carry >> pos - to & mask) >>> 0);
|
|
772
|
+
const pow = powers[pos];
|
|
773
|
+
if (pow === void 0)
|
|
774
|
+
throw new Error("invalid carry");
|
|
775
|
+
carry &= pow - 1;
|
|
776
|
+
}
|
|
777
|
+
carry = carry << to - pos & mask;
|
|
778
|
+
if (!padding && pos >= from)
|
|
779
|
+
throw new Error("Excess padding");
|
|
780
|
+
if (!padding && carry > 0)
|
|
781
|
+
throw new Error(`Non-zero padding: ${carry}`);
|
|
782
|
+
if (padding && pos > 0)
|
|
783
|
+
res.push(carry >>> 0);
|
|
784
|
+
return res;
|
|
785
|
+
}
|
|
786
|
+
// @__NO_SIDE_EFFECTS__
|
|
787
|
+
function radix(num) {
|
|
788
|
+
anumber(num);
|
|
789
|
+
const _256 = 2 ** 8;
|
|
790
|
+
return {
|
|
791
|
+
encode: (bytes) => {
|
|
792
|
+
if (!isBytes(bytes))
|
|
793
|
+
throw new Error("radix.encode input should be Uint8Array");
|
|
794
|
+
return convertRadix(Array.from(bytes), _256, num);
|
|
795
|
+
},
|
|
796
|
+
decode: (digits) => {
|
|
797
|
+
anumArr("radix.decode", digits);
|
|
798
|
+
return Uint8Array.from(convertRadix(digits, num, _256));
|
|
799
|
+
}
|
|
800
|
+
};
|
|
801
|
+
}
|
|
802
|
+
// @__NO_SIDE_EFFECTS__
|
|
803
|
+
function radix2(bits, revPadding = false) {
|
|
804
|
+
anumber(bits);
|
|
805
|
+
if (/* @__PURE__ */ radix2carry(8, bits) > 32 || /* @__PURE__ */ radix2carry(bits, 8) > 32)
|
|
806
|
+
throw new Error("radix2: carry overflow");
|
|
807
|
+
return {
|
|
808
|
+
encode: (bytes) => {
|
|
809
|
+
if (!isBytes(bytes))
|
|
810
|
+
throw new Error("radix2.encode input should be Uint8Array");
|
|
811
|
+
return convertRadix2(Array.from(bytes), 8, bits, !revPadding);
|
|
812
|
+
},
|
|
813
|
+
decode: (digits) => {
|
|
814
|
+
anumArr("radix2.decode", digits);
|
|
815
|
+
return Uint8Array.from(convertRadix2(digits, bits, 8, revPadding));
|
|
816
|
+
}
|
|
817
|
+
};
|
|
818
|
+
}
|
|
819
|
+
function unsafeWrapper(fn) {
|
|
820
|
+
afn(fn);
|
|
821
|
+
return function(...args) {
|
|
822
|
+
try {
|
|
823
|
+
return fn.apply(null, args);
|
|
824
|
+
} catch (e) {
|
|
825
|
+
}
|
|
826
|
+
};
|
|
827
|
+
}
|
|
828
|
+
function checksum(len, fn) {
|
|
829
|
+
anumber(len);
|
|
830
|
+
afn(fn);
|
|
831
|
+
return {
|
|
832
|
+
encode(data) {
|
|
833
|
+
if (!isBytes(data))
|
|
834
|
+
throw new Error("checksum.encode: input should be Uint8Array");
|
|
835
|
+
const sum = fn(data).slice(0, len);
|
|
836
|
+
const res = new Uint8Array(data.length + len);
|
|
837
|
+
res.set(data);
|
|
838
|
+
res.set(sum, data.length);
|
|
839
|
+
return res;
|
|
840
|
+
},
|
|
841
|
+
decode(data) {
|
|
842
|
+
if (!isBytes(data))
|
|
843
|
+
throw new Error("checksum.decode: input should be Uint8Array");
|
|
844
|
+
const payload = data.slice(0, -len);
|
|
845
|
+
const oldChecksum = data.slice(-len);
|
|
846
|
+
const newChecksum = fn(payload).slice(0, len);
|
|
847
|
+
for (let i = 0; i < len; i++)
|
|
848
|
+
if (newChecksum[i] !== oldChecksum[i])
|
|
849
|
+
throw new Error("Invalid checksum");
|
|
850
|
+
return payload;
|
|
851
|
+
}
|
|
852
|
+
};
|
|
853
|
+
}
|
|
854
|
+
var genBase58 = /* @__NO_SIDE_EFFECTS__ */ (abc) => /* @__PURE__ */ chain(/* @__PURE__ */ radix(58), /* @__PURE__ */ alphabet(abc), /* @__PURE__ */ join(""));
|
|
855
|
+
var base58 = /* @__PURE__ */ genBase58("123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz");
|
|
856
|
+
var createBase58check = (sha2563) => /* @__PURE__ */ chain(checksum(4, (data) => sha2563(sha2563(data))), base58);
|
|
857
|
+
var base58check = createBase58check;
|
|
858
|
+
var BECH_ALPHABET = /* @__PURE__ */ chain(/* @__PURE__ */ alphabet("qpzry9x8gf2tvdw0s3jn54khce6mua7l"), /* @__PURE__ */ join(""));
|
|
859
|
+
var POLYMOD_GENERATORS = [996825010, 642813549, 513874426, 1027748829, 705979059];
|
|
860
|
+
function bech32Polymod(pre) {
|
|
861
|
+
const b = pre >> 25;
|
|
862
|
+
let chk = (pre & 33554431) << 5;
|
|
863
|
+
for (let i = 0; i < POLYMOD_GENERATORS.length; i++) {
|
|
864
|
+
if ((b >> i & 1) === 1)
|
|
865
|
+
chk ^= POLYMOD_GENERATORS[i];
|
|
866
|
+
}
|
|
867
|
+
return chk;
|
|
868
|
+
}
|
|
869
|
+
function bechChecksum(prefix, words, encodingConst = 1) {
|
|
870
|
+
const len = prefix.length;
|
|
871
|
+
let chk = 1;
|
|
872
|
+
for (let i = 0; i < len; i++) {
|
|
873
|
+
const c = prefix.charCodeAt(i);
|
|
874
|
+
if (c < 33 || c > 126)
|
|
875
|
+
throw new Error(`Invalid prefix (${prefix})`);
|
|
876
|
+
chk = bech32Polymod(chk) ^ c >> 5;
|
|
877
|
+
}
|
|
878
|
+
chk = bech32Polymod(chk);
|
|
879
|
+
for (let i = 0; i < len; i++)
|
|
880
|
+
chk = bech32Polymod(chk) ^ prefix.charCodeAt(i) & 31;
|
|
881
|
+
for (let v of words)
|
|
882
|
+
chk = bech32Polymod(chk) ^ v;
|
|
883
|
+
for (let i = 0; i < 6; i++)
|
|
884
|
+
chk = bech32Polymod(chk);
|
|
885
|
+
chk ^= encodingConst;
|
|
886
|
+
return BECH_ALPHABET.encode(convertRadix2([chk % powers[30]], 30, 5, false));
|
|
887
|
+
}
|
|
888
|
+
// @__NO_SIDE_EFFECTS__
|
|
889
|
+
function genBech32(encoding) {
|
|
890
|
+
const ENCODING_CONST = 1 ;
|
|
891
|
+
const _words = /* @__PURE__ */ radix2(5);
|
|
892
|
+
const fromWords = _words.decode;
|
|
893
|
+
const toWords = _words.encode;
|
|
894
|
+
const fromWordsUnsafe = unsafeWrapper(fromWords);
|
|
895
|
+
function encode(prefix, words, limit = 90) {
|
|
896
|
+
astr("bech32.encode prefix", prefix);
|
|
897
|
+
if (isBytes(words))
|
|
898
|
+
words = Array.from(words);
|
|
899
|
+
anumArr("bech32.encode", words);
|
|
900
|
+
const plen = prefix.length;
|
|
901
|
+
if (plen === 0)
|
|
902
|
+
throw new TypeError(`Invalid prefix length ${plen}`);
|
|
903
|
+
const actualLength = plen + 7 + words.length;
|
|
904
|
+
if (limit !== false && actualLength > limit)
|
|
905
|
+
throw new TypeError(`Length ${actualLength} exceeds limit ${limit}`);
|
|
906
|
+
const lowered = prefix.toLowerCase();
|
|
907
|
+
const sum = bechChecksum(lowered, words, ENCODING_CONST);
|
|
908
|
+
return `${lowered}1${BECH_ALPHABET.encode(words)}${sum}`;
|
|
909
|
+
}
|
|
910
|
+
function decode(str, limit = 90) {
|
|
911
|
+
astr("bech32.decode input", str);
|
|
912
|
+
const slen = str.length;
|
|
913
|
+
if (slen < 8 || limit !== false && slen > limit)
|
|
914
|
+
throw new TypeError(`invalid string length: ${slen} (${str}). Expected (8..${limit})`);
|
|
915
|
+
const lowered = str.toLowerCase();
|
|
916
|
+
if (str !== lowered && str !== str.toUpperCase())
|
|
917
|
+
throw new Error(`String must be lowercase or uppercase`);
|
|
918
|
+
const sepIndex = lowered.lastIndexOf("1");
|
|
919
|
+
if (sepIndex === 0 || sepIndex === -1)
|
|
920
|
+
throw new Error(`Letter "1" must be present between prefix and data only`);
|
|
921
|
+
const prefix = lowered.slice(0, sepIndex);
|
|
922
|
+
const data = lowered.slice(sepIndex + 1);
|
|
923
|
+
if (data.length < 6)
|
|
924
|
+
throw new Error("Data must be at least 6 characters long");
|
|
925
|
+
const words = BECH_ALPHABET.decode(data).slice(0, -6);
|
|
926
|
+
const sum = bechChecksum(prefix, words, ENCODING_CONST);
|
|
927
|
+
if (!data.endsWith(sum))
|
|
928
|
+
throw new Error(`Invalid checksum in ${str}: expected "${sum}"`);
|
|
929
|
+
return { prefix, words };
|
|
930
|
+
}
|
|
931
|
+
const decodeUnsafe = unsafeWrapper(decode);
|
|
932
|
+
function decodeToBytes(str) {
|
|
933
|
+
const { prefix, words } = decode(str, false);
|
|
934
|
+
return { prefix, words, bytes: fromWords(words) };
|
|
935
|
+
}
|
|
936
|
+
function encodeFromBytes(prefix, bytes) {
|
|
937
|
+
return encode(prefix, toWords(bytes));
|
|
938
|
+
}
|
|
939
|
+
return {
|
|
940
|
+
encode,
|
|
941
|
+
decode,
|
|
942
|
+
encodeFromBytes,
|
|
943
|
+
decodeToBytes,
|
|
944
|
+
decodeUnsafe,
|
|
945
|
+
fromWords,
|
|
946
|
+
fromWordsUnsafe,
|
|
947
|
+
toWords
|
|
948
|
+
};
|
|
949
|
+
}
|
|
950
|
+
var bech32 = /* @__PURE__ */ genBech32();
|
|
951
|
+
|
|
952
|
+
// node_modules/@scure/bip32/index.js
|
|
953
|
+
var Point = secp256k1_js.secp256k1.Point;
|
|
954
|
+
var { Fn } = Point;
|
|
955
|
+
var base58check2 = createBase58check(sha2_js.sha256);
|
|
956
|
+
var MASTER_SECRET = Uint8Array.from("Bitcoin seed".split(""), (char) => char.charCodeAt(0));
|
|
957
|
+
var BITCOIN_VERSIONS = { private: 76066276, public: 76067358 };
|
|
958
|
+
var HARDENED_OFFSET = 2147483648;
|
|
959
|
+
var hash160 = (data) => legacy_js.ripemd160(sha2_js.sha256(data));
|
|
960
|
+
var fromU32 = (data) => utils_js.createView(data).getUint32(0, false);
|
|
961
|
+
var toU32 = (n) => {
|
|
962
|
+
if (!Number.isSafeInteger(n) || n < 0 || n > 2 ** 32 - 1) {
|
|
963
|
+
throw new Error("invalid number, should be from 0 to 2**32-1, got " + n);
|
|
964
|
+
}
|
|
965
|
+
const buf = new Uint8Array(4);
|
|
966
|
+
utils_js.createView(buf).setUint32(0, n, false);
|
|
967
|
+
return buf;
|
|
968
|
+
};
|
|
969
|
+
var HDKey = class _HDKey {
|
|
970
|
+
get fingerprint() {
|
|
971
|
+
if (!this.pubHash) {
|
|
972
|
+
throw new Error("No publicKey set!");
|
|
973
|
+
}
|
|
974
|
+
return fromU32(this.pubHash);
|
|
975
|
+
}
|
|
976
|
+
get identifier() {
|
|
977
|
+
return this.pubHash;
|
|
978
|
+
}
|
|
979
|
+
get pubKeyHash() {
|
|
980
|
+
return this.pubHash;
|
|
981
|
+
}
|
|
982
|
+
get privateKey() {
|
|
983
|
+
return this._privateKey || null;
|
|
984
|
+
}
|
|
985
|
+
get publicKey() {
|
|
986
|
+
return this._publicKey || null;
|
|
987
|
+
}
|
|
988
|
+
get privateExtendedKey() {
|
|
989
|
+
const priv = this._privateKey;
|
|
990
|
+
if (!priv) {
|
|
991
|
+
throw new Error("No private key");
|
|
992
|
+
}
|
|
993
|
+
return base58check2.encode(this.serialize(this.versions.private, utils_js.concatBytes(Uint8Array.of(0), priv)));
|
|
994
|
+
}
|
|
995
|
+
get publicExtendedKey() {
|
|
996
|
+
if (!this._publicKey) {
|
|
997
|
+
throw new Error("No public key");
|
|
998
|
+
}
|
|
999
|
+
return base58check2.encode(this.serialize(this.versions.public, this._publicKey));
|
|
1000
|
+
}
|
|
1001
|
+
static fromMasterSeed(seed, versions = BITCOIN_VERSIONS) {
|
|
1002
|
+
utils_js.abytes(seed);
|
|
1003
|
+
if (8 * seed.length < 128 || 8 * seed.length > 512) {
|
|
1004
|
+
throw new Error("HDKey: seed length must be between 128 and 512 bits; 256 bits is advised, got " + seed.length);
|
|
1005
|
+
}
|
|
1006
|
+
const I = hmac_js.hmac(sha2_js.sha512, MASTER_SECRET, seed);
|
|
1007
|
+
const privateKey = I.slice(0, 32);
|
|
1008
|
+
const chainCode = I.slice(32);
|
|
1009
|
+
return new _HDKey({ versions, chainCode, privateKey });
|
|
1010
|
+
}
|
|
1011
|
+
static fromExtendedKey(base58key, versions = BITCOIN_VERSIONS) {
|
|
1012
|
+
const keyBuffer = base58check2.decode(base58key);
|
|
1013
|
+
const keyView = utils_js.createView(keyBuffer);
|
|
1014
|
+
const version = keyView.getUint32(0, false);
|
|
1015
|
+
const opt = {
|
|
1016
|
+
versions,
|
|
1017
|
+
depth: keyBuffer[4],
|
|
1018
|
+
parentFingerprint: keyView.getUint32(5, false),
|
|
1019
|
+
index: keyView.getUint32(9, false),
|
|
1020
|
+
chainCode: keyBuffer.slice(13, 45)
|
|
1021
|
+
};
|
|
1022
|
+
const key = keyBuffer.slice(45);
|
|
1023
|
+
const isPriv = key[0] === 0;
|
|
1024
|
+
if (version !== versions[isPriv ? "private" : "public"]) {
|
|
1025
|
+
throw new Error("Version mismatch");
|
|
1026
|
+
}
|
|
1027
|
+
if (isPriv) {
|
|
1028
|
+
return new _HDKey({ ...opt, privateKey: key.slice(1) });
|
|
1029
|
+
} else {
|
|
1030
|
+
return new _HDKey({ ...opt, publicKey: key });
|
|
1031
|
+
}
|
|
1032
|
+
}
|
|
1033
|
+
static fromJSON(json) {
|
|
1034
|
+
return _HDKey.fromExtendedKey(json.xpriv);
|
|
1035
|
+
}
|
|
1036
|
+
versions;
|
|
1037
|
+
depth = 0;
|
|
1038
|
+
index = 0;
|
|
1039
|
+
chainCode = null;
|
|
1040
|
+
parentFingerprint = 0;
|
|
1041
|
+
_privateKey;
|
|
1042
|
+
_publicKey;
|
|
1043
|
+
pubHash;
|
|
1044
|
+
constructor(opt) {
|
|
1045
|
+
if (!opt || typeof opt !== "object") {
|
|
1046
|
+
throw new Error("HDKey.constructor must not be called directly");
|
|
1047
|
+
}
|
|
1048
|
+
this.versions = opt.versions || BITCOIN_VERSIONS;
|
|
1049
|
+
this.depth = opt.depth || 0;
|
|
1050
|
+
this.chainCode = opt.chainCode || null;
|
|
1051
|
+
this.index = opt.index || 0;
|
|
1052
|
+
this.parentFingerprint = opt.parentFingerprint || 0;
|
|
1053
|
+
if (!this.depth) {
|
|
1054
|
+
if (this.parentFingerprint || this.index) {
|
|
1055
|
+
throw new Error("HDKey: zero depth with non-zero index/parent fingerprint");
|
|
1056
|
+
}
|
|
1057
|
+
}
|
|
1058
|
+
if (this.depth > 255) {
|
|
1059
|
+
throw new Error("HDKey: depth exceeds the serializable value 255");
|
|
1060
|
+
}
|
|
1061
|
+
if (opt.publicKey && opt.privateKey) {
|
|
1062
|
+
throw new Error("HDKey: publicKey and privateKey at same time.");
|
|
1063
|
+
}
|
|
1064
|
+
if (opt.privateKey) {
|
|
1065
|
+
if (!secp256k1_js.secp256k1.utils.isValidSecretKey(opt.privateKey))
|
|
1066
|
+
throw new Error("Invalid private key");
|
|
1067
|
+
this._privateKey = opt.privateKey;
|
|
1068
|
+
this._publicKey = secp256k1_js.secp256k1.getPublicKey(opt.privateKey, true);
|
|
1069
|
+
} else if (opt.publicKey) {
|
|
1070
|
+
this._publicKey = Point.fromBytes(opt.publicKey).toBytes(true);
|
|
1071
|
+
} else {
|
|
1072
|
+
throw new Error("HDKey: no public or private key provided");
|
|
1073
|
+
}
|
|
1074
|
+
this.pubHash = hash160(this._publicKey);
|
|
1075
|
+
}
|
|
1076
|
+
derive(path) {
|
|
1077
|
+
if (!/^[mM]'?/.test(path)) {
|
|
1078
|
+
throw new Error('Path must start with "m" or "M"');
|
|
1079
|
+
}
|
|
1080
|
+
if (/^[mM]'?$/.test(path)) {
|
|
1081
|
+
return this;
|
|
1082
|
+
}
|
|
1083
|
+
const parts = path.replace(/^[mM]'?\//, "").split("/");
|
|
1084
|
+
let child = this;
|
|
1085
|
+
for (const c of parts) {
|
|
1086
|
+
const m = /^(\d+)('?)$/.exec(c);
|
|
1087
|
+
const m1 = m && m[1];
|
|
1088
|
+
if (!m || m.length !== 3 || typeof m1 !== "string")
|
|
1089
|
+
throw new Error("invalid child index: " + c);
|
|
1090
|
+
let idx = +m1;
|
|
1091
|
+
if (!Number.isSafeInteger(idx) || idx >= HARDENED_OFFSET) {
|
|
1092
|
+
throw new Error("Invalid index");
|
|
1093
|
+
}
|
|
1094
|
+
if (m[2] === "'") {
|
|
1095
|
+
idx += HARDENED_OFFSET;
|
|
1096
|
+
}
|
|
1097
|
+
child = child.deriveChild(idx);
|
|
1098
|
+
}
|
|
1099
|
+
return child;
|
|
1100
|
+
}
|
|
1101
|
+
deriveChild(index) {
|
|
1102
|
+
if (!this._publicKey || !this.chainCode) {
|
|
1103
|
+
throw new Error("No publicKey or chainCode set");
|
|
1104
|
+
}
|
|
1105
|
+
let data = toU32(index);
|
|
1106
|
+
if (index >= HARDENED_OFFSET) {
|
|
1107
|
+
const priv = this._privateKey;
|
|
1108
|
+
if (!priv) {
|
|
1109
|
+
throw new Error("Could not derive hardened child key");
|
|
1110
|
+
}
|
|
1111
|
+
data = utils_js.concatBytes(Uint8Array.of(0), priv, data);
|
|
1112
|
+
} else {
|
|
1113
|
+
data = utils_js.concatBytes(this._publicKey, data);
|
|
1114
|
+
}
|
|
1115
|
+
const I = hmac_js.hmac(sha2_js.sha512, this.chainCode, data);
|
|
1116
|
+
const childTweak = I.slice(0, 32);
|
|
1117
|
+
const chainCode = I.slice(32);
|
|
1118
|
+
if (!secp256k1_js.secp256k1.utils.isValidSecretKey(childTweak)) {
|
|
1119
|
+
throw new Error("Tweak bigger than curve order");
|
|
1120
|
+
}
|
|
1121
|
+
const opt = {
|
|
1122
|
+
versions: this.versions,
|
|
1123
|
+
chainCode,
|
|
1124
|
+
depth: this.depth + 1,
|
|
1125
|
+
parentFingerprint: this.fingerprint,
|
|
1126
|
+
index
|
|
1127
|
+
};
|
|
1128
|
+
const ctweak = Fn.fromBytes(childTweak);
|
|
1129
|
+
try {
|
|
1130
|
+
if (this._privateKey) {
|
|
1131
|
+
const added = Fn.create(Fn.fromBytes(this._privateKey) + ctweak);
|
|
1132
|
+
if (!Fn.isValidNot0(added)) {
|
|
1133
|
+
throw new Error("The tweak was out of range or the resulted private key is invalid");
|
|
1134
|
+
}
|
|
1135
|
+
opt.privateKey = Fn.toBytes(added);
|
|
1136
|
+
} else {
|
|
1137
|
+
const added = Point.fromBytes(this._publicKey).add(Point.BASE.multiply(ctweak));
|
|
1138
|
+
if (added.equals(Point.ZERO)) {
|
|
1139
|
+
throw new Error("The tweak was equal to negative P, which made the result key invalid");
|
|
1140
|
+
}
|
|
1141
|
+
opt.publicKey = added.toBytes(true);
|
|
1142
|
+
}
|
|
1143
|
+
return new _HDKey(opt);
|
|
1144
|
+
} catch (err) {
|
|
1145
|
+
return this.deriveChild(index + 1);
|
|
1146
|
+
}
|
|
1147
|
+
}
|
|
1148
|
+
sign(hash) {
|
|
1149
|
+
if (!this._privateKey) {
|
|
1150
|
+
throw new Error("No privateKey set!");
|
|
1151
|
+
}
|
|
1152
|
+
utils_js.abytes(hash, 32);
|
|
1153
|
+
return secp256k1_js.secp256k1.sign(hash, this._privateKey, { prehash: false });
|
|
1154
|
+
}
|
|
1155
|
+
verify(hash, signature) {
|
|
1156
|
+
utils_js.abytes(hash, 32);
|
|
1157
|
+
utils_js.abytes(signature, 64);
|
|
1158
|
+
if (!this._publicKey) {
|
|
1159
|
+
throw new Error("No publicKey set!");
|
|
1160
|
+
}
|
|
1161
|
+
return secp256k1_js.secp256k1.verify(signature, hash, this._publicKey, { prehash: false });
|
|
1162
|
+
}
|
|
1163
|
+
wipePrivateData() {
|
|
1164
|
+
if (this._privateKey) {
|
|
1165
|
+
this._privateKey.fill(0);
|
|
1166
|
+
this._privateKey = void 0;
|
|
1167
|
+
}
|
|
1168
|
+
return this;
|
|
1169
|
+
}
|
|
1170
|
+
toJSON() {
|
|
1171
|
+
return {
|
|
1172
|
+
xpriv: this.privateExtendedKey,
|
|
1173
|
+
xpub: this.publicExtendedKey
|
|
1174
|
+
};
|
|
1175
|
+
}
|
|
1176
|
+
serialize(version, key) {
|
|
1177
|
+
if (!this.chainCode) {
|
|
1178
|
+
throw new Error("No chainCode set");
|
|
1179
|
+
}
|
|
1180
|
+
utils_js.abytes(key, 33);
|
|
1181
|
+
return utils_js.concatBytes(toU32(version), new Uint8Array([this.depth]), toU32(this.parentFingerprint), toU32(this.index), this.chainCode, key);
|
|
1182
|
+
}
|
|
1183
|
+
};
|
|
598
1184
|
var DERIVATION_PATHS2 = {
|
|
599
1185
|
ethereum: "m/44'/60'/0'/0/0",
|
|
600
1186
|
bitcoin_mainnet: "m/84'/0'/0'/0/0",
|
|
@@ -611,7 +1197,7 @@ function deriveEthereumAddress(seed) {
|
|
|
611
1197
|
function deriveBitcoinAddress(seed, network = "mainnet") {
|
|
612
1198
|
try {
|
|
613
1199
|
const seedBytes = bip39.mnemonicToSeedSync(seed);
|
|
614
|
-
const hdKey =
|
|
1200
|
+
const hdKey = HDKey.fromMasterSeed(seedBytes);
|
|
615
1201
|
const path = network === "testnet" ? DERIVATION_PATHS2.bitcoin_testnet : DERIVATION_PATHS2.bitcoin_mainnet;
|
|
616
1202
|
const child = hdKey.derive(path);
|
|
617
1203
|
if (!child.publicKey) {
|
|
@@ -619,10 +1205,10 @@ function deriveBitcoinAddress(seed, network = "mainnet") {
|
|
|
619
1205
|
}
|
|
620
1206
|
const pubKeyHash = ripemd160.ripemd160(sha256.sha256(child.publicKey));
|
|
621
1207
|
const witnessVersion = 0;
|
|
622
|
-
const words =
|
|
1208
|
+
const words = bech32.toWords(pubKeyHash);
|
|
623
1209
|
words.unshift(witnessVersion);
|
|
624
1210
|
const hrp = network === "testnet" ? "tb" : "bc";
|
|
625
|
-
const address =
|
|
1211
|
+
const address = bech32.encode(hrp, words);
|
|
626
1212
|
return address;
|
|
627
1213
|
} catch (error) {
|
|
628
1214
|
console.error("Bitcoin address derivation failed:", error);
|
|
@@ -695,7 +1281,7 @@ function deriveTronAddress(seed) {
|
|
|
695
1281
|
for (let i = 0; i < 20; i++) {
|
|
696
1282
|
addressBytes[i + 1] = parseInt(ethAddressHex.slice(i * 2, i * 2 + 2), 16);
|
|
697
1283
|
}
|
|
698
|
-
const tronBase58check =
|
|
1284
|
+
const tronBase58check = base58check(sha256.sha256);
|
|
699
1285
|
return tronBase58check.encode(addressBytes);
|
|
700
1286
|
} catch (error) {
|
|
701
1287
|
console.error("TRON address derivation failed:", error);
|
|
@@ -705,17 +1291,17 @@ function deriveTronAddress(seed) {
|
|
|
705
1291
|
function deriveSparkAddress(seed, network = "mainnet") {
|
|
706
1292
|
try {
|
|
707
1293
|
const seedBytes = bip39.mnemonicToSeedSync(seed);
|
|
708
|
-
const hdKey =
|
|
1294
|
+
const hdKey = HDKey.fromMasterSeed(seedBytes);
|
|
709
1295
|
const child = hdKey.derive(DERIVATION_PATHS2.spark);
|
|
710
1296
|
if (!child.publicKey) {
|
|
711
1297
|
throw new Error("Failed to derive public key");
|
|
712
1298
|
}
|
|
713
1299
|
const pubKeyHash = ripemd160.ripemd160(sha256.sha256(child.publicKey));
|
|
714
1300
|
const witnessVersion = 0;
|
|
715
|
-
const words =
|
|
1301
|
+
const words = bech32.toWords(pubKeyHash);
|
|
716
1302
|
words.unshift(witnessVersion);
|
|
717
1303
|
const hrp = network === "testnet" ? "tsp" : "sp";
|
|
718
|
-
const address =
|
|
1304
|
+
const address = bech32.encode(hrp, words);
|
|
719
1305
|
return address;
|
|
720
1306
|
} catch (error) {
|
|
721
1307
|
console.error("Spark address derivation failed:", error);
|
|
@@ -811,9 +1397,9 @@ var CHAIN_ERROR_MESSAGES = {
|
|
|
811
1397
|
"no route": "NETWORK_ERROR"
|
|
812
1398
|
}
|
|
813
1399
|
};
|
|
814
|
-
function parseChainError(
|
|
1400
|
+
function parseChainError(chain2, errorMessage) {
|
|
815
1401
|
const errorLower = errorMessage.toLowerCase();
|
|
816
|
-
const chainErrors = CHAIN_ERROR_MESSAGES[
|
|
1402
|
+
const chainErrors = CHAIN_ERROR_MESSAGES[chain2];
|
|
817
1403
|
for (const [pattern, code] of Object.entries(chainErrors)) {
|
|
818
1404
|
if (errorLower.includes(pattern)) {
|
|
819
1405
|
return code;
|
|
@@ -951,38 +1537,38 @@ var ZubariWdkService = class {
|
|
|
951
1537
|
* For Ethereum, falls back to local derivation if API fails.
|
|
952
1538
|
* For other chains, WDK API is required - no placeholder fallback.
|
|
953
1539
|
*/
|
|
954
|
-
async deriveAddress(seed,
|
|
1540
|
+
async deriveAddress(seed, chain2) {
|
|
955
1541
|
await this.initialize();
|
|
956
|
-
const path = this.getDerivationPath(
|
|
1542
|
+
const path = this.getDerivationPath(chain2);
|
|
957
1543
|
try {
|
|
958
|
-
const response = await this.apiClient.deriveAddress(seed,
|
|
1544
|
+
const response = await this.apiClient.deriveAddress(seed, chain2, this.config.network);
|
|
959
1545
|
if (response.success && response.address) {
|
|
960
1546
|
return {
|
|
961
|
-
chain,
|
|
1547
|
+
chain: chain2,
|
|
962
1548
|
address: response.address,
|
|
963
1549
|
path: response.path || path
|
|
964
1550
|
};
|
|
965
1551
|
}
|
|
966
1552
|
} catch (error) {
|
|
967
|
-
console.warn(`API address derivation failed for ${
|
|
968
|
-
if (
|
|
969
|
-
return this.deriveBrowserAddress(seed,
|
|
1553
|
+
console.warn(`API address derivation failed for ${chain2}:`, error);
|
|
1554
|
+
if (chain2 === "ethereum") {
|
|
1555
|
+
return this.deriveBrowserAddress(seed, chain2);
|
|
970
1556
|
}
|
|
971
1557
|
}
|
|
972
1558
|
if (this.useNativeWdk && this.nativeWdkService) {
|
|
973
1559
|
try {
|
|
974
1560
|
const wdk = this.nativeWdkService;
|
|
975
1561
|
await wdk.initialize(seed);
|
|
976
|
-
return await wdk.deriveAddress(
|
|
1562
|
+
return await wdk.deriveAddress(chain2);
|
|
977
1563
|
} catch (error) {
|
|
978
|
-
console.warn(`Native WDK address derivation failed for ${
|
|
1564
|
+
console.warn(`Native WDK address derivation failed for ${chain2}:`, error);
|
|
979
1565
|
}
|
|
980
1566
|
}
|
|
981
|
-
if (
|
|
982
|
-
return this.deriveBrowserAddress(seed,
|
|
1567
|
+
if (chain2 === "ethereum") {
|
|
1568
|
+
return this.deriveBrowserAddress(seed, chain2);
|
|
983
1569
|
}
|
|
984
1570
|
throw new Error(
|
|
985
|
-
`WDK API required for ${
|
|
1571
|
+
`WDK API required for ${chain2} address derivation. Ensure the backend is running.`
|
|
986
1572
|
);
|
|
987
1573
|
}
|
|
988
1574
|
/**
|
|
@@ -1062,13 +1648,13 @@ var ZubariWdkService = class {
|
|
|
1062
1648
|
/**
|
|
1063
1649
|
* Get fee rates for a chain
|
|
1064
1650
|
*/
|
|
1065
|
-
async getFeeRates(seed,
|
|
1651
|
+
async getFeeRates(seed, chain2) {
|
|
1066
1652
|
await this.initialize();
|
|
1067
1653
|
try {
|
|
1068
1654
|
const response = await fetch(`${this.config.apiUrl}/api/wallets/wdk/fee-rates`, {
|
|
1069
1655
|
method: "POST",
|
|
1070
1656
|
headers: { "Content-Type": "application/json" },
|
|
1071
|
-
body: JSON.stringify({ seed, chain, network: this.config.network })
|
|
1657
|
+
body: JSON.stringify({ seed, chain: chain2, network: this.config.network })
|
|
1072
1658
|
});
|
|
1073
1659
|
if (response.ok) {
|
|
1074
1660
|
const data = await response.json();
|
|
@@ -1077,20 +1663,20 @@ var ZubariWdkService = class {
|
|
|
1077
1663
|
}
|
|
1078
1664
|
}
|
|
1079
1665
|
} catch (error) {
|
|
1080
|
-
console.warn(`Failed to fetch fee rates for ${
|
|
1666
|
+
console.warn(`Failed to fetch fee rates for ${chain2}:`, error);
|
|
1081
1667
|
}
|
|
1082
1668
|
return { slow: "0", normal: "0", fast: "0" };
|
|
1083
1669
|
}
|
|
1084
1670
|
/**
|
|
1085
1671
|
* Estimate transaction fee
|
|
1086
1672
|
*/
|
|
1087
|
-
async estimateFee(seed,
|
|
1673
|
+
async estimateFee(seed, chain2, to, amount) {
|
|
1088
1674
|
await this.initialize();
|
|
1089
1675
|
try {
|
|
1090
1676
|
const response = await fetch(`${this.config.apiUrl}/api/wallets/wdk/estimate-fee`, {
|
|
1091
1677
|
method: "POST",
|
|
1092
1678
|
headers: { "Content-Type": "application/json" },
|
|
1093
|
-
body: JSON.stringify({ seed, chain, to, amount, network: this.config.network })
|
|
1679
|
+
body: JSON.stringify({ seed, chain: chain2, to, amount, network: this.config.network })
|
|
1094
1680
|
});
|
|
1095
1681
|
if (response.ok) {
|
|
1096
1682
|
const data = await response.json();
|
|
@@ -1099,9 +1685,9 @@ var ZubariWdkService = class {
|
|
|
1099
1685
|
}
|
|
1100
1686
|
}
|
|
1101
1687
|
} catch (error) {
|
|
1102
|
-
console.warn(`Failed to estimate fee for ${
|
|
1688
|
+
console.warn(`Failed to estimate fee for ${chain2}:`, error);
|
|
1103
1689
|
}
|
|
1104
|
-
return { fee: "0", symbol: this.getChainSymbol(
|
|
1690
|
+
return { fee: "0", symbol: this.getChainSymbol(chain2) };
|
|
1105
1691
|
}
|
|
1106
1692
|
/**
|
|
1107
1693
|
* Send a transaction on any supported chain
|
|
@@ -1112,10 +1698,10 @@ var ZubariWdkService = class {
|
|
|
1112
1698
|
* @param amount - Amount to send (in native units: ETH, BTC, SOL, etc.)
|
|
1113
1699
|
* @returns Transaction result with hash on success, or error details on failure
|
|
1114
1700
|
*/
|
|
1115
|
-
async sendTransaction(seed,
|
|
1701
|
+
async sendTransaction(seed, chain2, to, amount) {
|
|
1116
1702
|
await this.initialize();
|
|
1117
1703
|
const startTime = Date.now();
|
|
1118
|
-
console.log(`[ZubariWdkService] Sending ${
|
|
1704
|
+
console.log(`[ZubariWdkService] Sending ${chain2} transaction`, {
|
|
1119
1705
|
to: `${to.slice(0, 10)}...${to.slice(-6)}`,
|
|
1120
1706
|
amount,
|
|
1121
1707
|
network: this.config.network
|
|
@@ -1124,7 +1710,7 @@ var ZubariWdkService = class {
|
|
|
1124
1710
|
const response = await fetch(`${this.config.apiUrl}/api/wallets/wdk/send`, {
|
|
1125
1711
|
method: "POST",
|
|
1126
1712
|
headers: { "Content-Type": "application/json" },
|
|
1127
|
-
body: JSON.stringify({ seed, chain, to, amount, network: this.config.network })
|
|
1713
|
+
body: JSON.stringify({ seed, chain: chain2, to, amount, network: this.config.network })
|
|
1128
1714
|
});
|
|
1129
1715
|
const elapsed = Date.now() - startTime;
|
|
1130
1716
|
if (response.ok) {
|
|
@@ -1134,22 +1720,22 @@ var ZubariWdkService = class {
|
|
|
1134
1720
|
txHash = txHash.hash;
|
|
1135
1721
|
}
|
|
1136
1722
|
if (txHash) {
|
|
1137
|
-
const isValid = this.validateTxHash(
|
|
1723
|
+
const isValid = this.validateTxHash(chain2, txHash);
|
|
1138
1724
|
if (!isValid) {
|
|
1139
|
-
console.warn(`[ZubariWdkService] Invalid ${
|
|
1725
|
+
console.warn(`[ZubariWdkService] Invalid ${chain2} tx hash format:`, txHash);
|
|
1140
1726
|
}
|
|
1141
1727
|
}
|
|
1142
|
-
console.log(`[ZubariWdkService] ${
|
|
1728
|
+
console.log(`[ZubariWdkService] ${chain2} transaction ${data.success ? "SUCCESS" : "FAILED"}`, {
|
|
1143
1729
|
txHash: txHash ? `${txHash.slice(0, 16)}...` : "N/A",
|
|
1144
1730
|
elapsed: `${elapsed}ms`
|
|
1145
1731
|
});
|
|
1146
1732
|
if (!data.success) {
|
|
1147
|
-
const errorCode2 = parseChainError(
|
|
1733
|
+
const errorCode2 = parseChainError(chain2, data.error || "");
|
|
1148
1734
|
return {
|
|
1149
1735
|
success: false,
|
|
1150
1736
|
error: data.error,
|
|
1151
1737
|
errorCode: errorCode2,
|
|
1152
|
-
chain
|
|
1738
|
+
chain: chain2
|
|
1153
1739
|
};
|
|
1154
1740
|
}
|
|
1155
1741
|
return {
|
|
@@ -1158,14 +1744,14 @@ var ZubariWdkService = class {
|
|
|
1158
1744
|
from: data.from,
|
|
1159
1745
|
to: data.to,
|
|
1160
1746
|
amount: data.amount,
|
|
1161
|
-
chain: data.chain ||
|
|
1747
|
+
chain: data.chain || chain2,
|
|
1162
1748
|
network: data.network || this.config.network
|
|
1163
1749
|
};
|
|
1164
1750
|
}
|
|
1165
1751
|
const errorData = await response.json().catch(() => ({}));
|
|
1166
1752
|
const errorMessage = errorData.error || `HTTP ${response.status}`;
|
|
1167
|
-
const errorCode = parseChainError(
|
|
1168
|
-
console.error(`[ZubariWdkService] ${
|
|
1753
|
+
const errorCode = parseChainError(chain2, errorMessage);
|
|
1754
|
+
console.error(`[ZubariWdkService] ${chain2} transaction FAILED`, {
|
|
1169
1755
|
status: response.status,
|
|
1170
1756
|
error: errorMessage,
|
|
1171
1757
|
errorCode,
|
|
@@ -1175,13 +1761,13 @@ var ZubariWdkService = class {
|
|
|
1175
1761
|
success: false,
|
|
1176
1762
|
error: errorMessage,
|
|
1177
1763
|
errorCode,
|
|
1178
|
-
chain
|
|
1764
|
+
chain: chain2
|
|
1179
1765
|
};
|
|
1180
1766
|
} catch (error) {
|
|
1181
1767
|
const elapsed = Date.now() - startTime;
|
|
1182
1768
|
const errorMessage = error instanceof Error ? error.message : "Transaction failed";
|
|
1183
|
-
const errorCode = parseChainError(
|
|
1184
|
-
console.error(`[ZubariWdkService] ${
|
|
1769
|
+
const errorCode = parseChainError(chain2, errorMessage);
|
|
1770
|
+
console.error(`[ZubariWdkService] ${chain2} transaction ERROR`, {
|
|
1185
1771
|
error: errorMessage,
|
|
1186
1772
|
errorCode,
|
|
1187
1773
|
elapsed: `${elapsed}ms`
|
|
@@ -1190,15 +1776,15 @@ var ZubariWdkService = class {
|
|
|
1190
1776
|
success: false,
|
|
1191
1777
|
error: errorMessage,
|
|
1192
1778
|
errorCode,
|
|
1193
|
-
chain
|
|
1779
|
+
chain: chain2
|
|
1194
1780
|
};
|
|
1195
1781
|
}
|
|
1196
1782
|
}
|
|
1197
1783
|
/**
|
|
1198
1784
|
* Validate transaction hash format for a specific chain
|
|
1199
1785
|
*/
|
|
1200
|
-
validateTxHash(
|
|
1201
|
-
switch (
|
|
1786
|
+
validateTxHash(chain2, txHash) {
|
|
1787
|
+
switch (chain2) {
|
|
1202
1788
|
case "ethereum":
|
|
1203
1789
|
return /^0x[a-fA-F0-9]{64}$/.test(txHash);
|
|
1204
1790
|
case "bitcoin":
|
|
@@ -1230,7 +1816,7 @@ var ZubariWdkService = class {
|
|
|
1230
1816
|
// ==========================================
|
|
1231
1817
|
// Private Helper Methods
|
|
1232
1818
|
// ==========================================
|
|
1233
|
-
getDerivationPath(
|
|
1819
|
+
getDerivationPath(chain2) {
|
|
1234
1820
|
const paths = {
|
|
1235
1821
|
bitcoin: this.config.network === "testnet" ? "m/84'/1'/0'/0/0" : "m/84'/0'/0'/0/0",
|
|
1236
1822
|
ethereum: "m/44'/60'/0'/0/0",
|
|
@@ -1239,9 +1825,9 @@ var ZubariWdkService = class {
|
|
|
1239
1825
|
solana: "m/44'/501'/0'/0'",
|
|
1240
1826
|
spark: "m/44'/998'/0'/0/0"
|
|
1241
1827
|
};
|
|
1242
|
-
return paths[
|
|
1828
|
+
return paths[chain2];
|
|
1243
1829
|
}
|
|
1244
|
-
getChainSymbol(
|
|
1830
|
+
getChainSymbol(chain2) {
|
|
1245
1831
|
const symbols = {
|
|
1246
1832
|
ethereum: "ETH",
|
|
1247
1833
|
bitcoin: "BTC",
|
|
@@ -1250,16 +1836,16 @@ var ZubariWdkService = class {
|
|
|
1250
1836
|
solana: "SOL",
|
|
1251
1837
|
spark: "SAT"
|
|
1252
1838
|
};
|
|
1253
|
-
return symbols[
|
|
1839
|
+
return symbols[chain2];
|
|
1254
1840
|
}
|
|
1255
1841
|
/**
|
|
1256
1842
|
* Derive address using browser-compatible libraries
|
|
1257
1843
|
*/
|
|
1258
|
-
async deriveBrowserAddress(seed,
|
|
1259
|
-
const path = this.getDerivationPath(
|
|
1844
|
+
async deriveBrowserAddress(seed, chain2) {
|
|
1845
|
+
const path = this.getDerivationPath(chain2);
|
|
1260
1846
|
try {
|
|
1261
1847
|
let address;
|
|
1262
|
-
switch (
|
|
1848
|
+
switch (chain2) {
|
|
1263
1849
|
case "ethereum":
|
|
1264
1850
|
address = deriveEthereumAddress(seed);
|
|
1265
1851
|
break;
|
|
@@ -1279,11 +1865,11 @@ var ZubariWdkService = class {
|
|
|
1279
1865
|
address = await deriveTonAddress(seed);
|
|
1280
1866
|
break;
|
|
1281
1867
|
default:
|
|
1282
|
-
throw new Error(`Unsupported chain: ${
|
|
1868
|
+
throw new Error(`Unsupported chain: ${chain2}`);
|
|
1283
1869
|
}
|
|
1284
|
-
return { chain, address, path };
|
|
1870
|
+
return { chain: chain2, address, path };
|
|
1285
1871
|
} catch (error) {
|
|
1286
|
-
console.error(`Browser derivation failed for ${
|
|
1872
|
+
console.error(`Browser derivation failed for ${chain2}:`, error);
|
|
1287
1873
|
throw error;
|
|
1288
1874
|
}
|
|
1289
1875
|
}
|
|
@@ -1352,12 +1938,12 @@ var ZubariWallet = class {
|
|
|
1352
1938
|
solana: "solana",
|
|
1353
1939
|
spark: "spark"
|
|
1354
1940
|
};
|
|
1355
|
-
const
|
|
1356
|
-
if (!
|
|
1941
|
+
const chain2 = chainMap[network];
|
|
1942
|
+
if (!chain2) {
|
|
1357
1943
|
throw new Error(`Unsupported network: ${network}`);
|
|
1358
1944
|
}
|
|
1359
1945
|
try {
|
|
1360
|
-
const result = await this.wdkService.deriveAddress(this.seed,
|
|
1946
|
+
const result = await this.wdkService.deriveAddress(this.seed, chain2);
|
|
1361
1947
|
const account = {
|
|
1362
1948
|
network,
|
|
1363
1949
|
address: result.address,
|
|
@@ -1412,13 +1998,13 @@ var ZubariWallet = class {
|
|
|
1412
1998
|
solana: "solana",
|
|
1413
1999
|
spark: "spark"
|
|
1414
2000
|
};
|
|
1415
|
-
const
|
|
1416
|
-
if (!
|
|
2001
|
+
const chain2 = chainMap[network];
|
|
2002
|
+
if (!chain2) {
|
|
1417
2003
|
throw new Error(`Unsupported network: ${network}`);
|
|
1418
2004
|
}
|
|
1419
2005
|
try {
|
|
1420
2006
|
const balances = await this.wdkService.getAllBalances(this.seed);
|
|
1421
|
-
const chainBalance = balances[
|
|
2007
|
+
const chainBalance = balances[chain2];
|
|
1422
2008
|
if (chainBalance) {
|
|
1423
2009
|
const balanceValue = BigInt(chainBalance.balance || "0");
|
|
1424
2010
|
const decimals = networkConfig.nativeCurrency.decimals;
|
|
@@ -1507,14 +2093,14 @@ var ZubariWallet = class {
|
|
|
1507
2093
|
solana: "solana",
|
|
1508
2094
|
spark: "spark"
|
|
1509
2095
|
};
|
|
1510
|
-
const
|
|
1511
|
-
if (!
|
|
2096
|
+
const chain2 = chainMap[network];
|
|
2097
|
+
if (!chain2) {
|
|
1512
2098
|
throw new Error(`Unsupported network: ${network}`);
|
|
1513
2099
|
}
|
|
1514
2100
|
try {
|
|
1515
2101
|
const result = await this.wdkService.sendTransaction(
|
|
1516
2102
|
this.seed,
|
|
1517
|
-
|
|
2103
|
+
chain2,
|
|
1518
2104
|
to,
|
|
1519
2105
|
amount.toString()
|
|
1520
2106
|
);
|
|
@@ -2189,8 +2775,8 @@ async function fetchPrices() {
|
|
|
2189
2775
|
if (response.ok) {
|
|
2190
2776
|
const data = await response.json();
|
|
2191
2777
|
const prices = {};
|
|
2192
|
-
for (const [
|
|
2193
|
-
prices[
|
|
2778
|
+
for (const [chain2, geckoId] of Object.entries(COINGECKO_IDS)) {
|
|
2779
|
+
prices[chain2] = data[geckoId]?.usd || 0;
|
|
2194
2780
|
}
|
|
2195
2781
|
priceCache = { prices, timestamp: Date.now() };
|
|
2196
2782
|
return prices;
|
|
@@ -2200,22 +2786,9 @@ async function fetchPrices() {
|
|
|
2200
2786
|
}
|
|
2201
2787
|
return priceCache?.prices || {};
|
|
2202
2788
|
}
|
|
2203
|
-
async function getPriceForChain(
|
|
2789
|
+
async function getPriceForChain(chain2) {
|
|
2204
2790
|
const prices = await fetchPrices();
|
|
2205
|
-
return prices[
|
|
2206
|
-
}
|
|
2207
|
-
function tonFriendlyToRaw(addr) {
|
|
2208
|
-
if (addr.includes(":")) return addr;
|
|
2209
|
-
try {
|
|
2210
|
-
const b64 = addr.replace(/-/g, "+").replace(/_/g, "/");
|
|
2211
|
-
const bytes = Uint8Array.from(atob(b64), (c) => c.charCodeAt(0));
|
|
2212
|
-
if (bytes.length !== 36) return addr;
|
|
2213
|
-
const workchain = bytes[1] === 255 ? -1 : bytes[1];
|
|
2214
|
-
const hash = Array.from(bytes.slice(2, 34)).map((b) => b.toString(16).padStart(2, "0")).join("");
|
|
2215
|
-
return `${workchain}:${hash}`;
|
|
2216
|
-
} catch {
|
|
2217
|
-
return addr;
|
|
2218
|
-
}
|
|
2791
|
+
return prices[chain2] || 0;
|
|
2219
2792
|
}
|
|
2220
2793
|
var STORAGE_KEYS = {
|
|
2221
2794
|
ENCRYPTED_SEED: "encrypted_seed",
|
|
@@ -2421,9 +2994,9 @@ var WalletManager = class _WalletManager {
|
|
|
2421
2994
|
if (!this.derivedAddress) {
|
|
2422
2995
|
throw new Error("Wallet not initialized");
|
|
2423
2996
|
}
|
|
2424
|
-
const
|
|
2997
|
+
const chain2 = this.config.network === "mainnet" ? chains.mainnet : chains.sepolia;
|
|
2425
2998
|
const client = viem.createPublicClient({
|
|
2426
|
-
chain,
|
|
2999
|
+
chain: chain2,
|
|
2427
3000
|
transport: viem.http(this.config.rpcUrl, {
|
|
2428
3001
|
timeout: 15e3,
|
|
2429
3002
|
// 15 second timeout
|
|
@@ -2445,9 +3018,9 @@ var WalletManager = class _WalletManager {
|
|
|
2445
3018
|
* Create viem public client for the current network
|
|
2446
3019
|
*/
|
|
2447
3020
|
getPublicClient() {
|
|
2448
|
-
const
|
|
3021
|
+
const chain2 = this.config.network === "mainnet" ? chains.mainnet : chains.sepolia;
|
|
2449
3022
|
return viem.createPublicClient({
|
|
2450
|
-
chain,
|
|
3023
|
+
chain: chain2,
|
|
2451
3024
|
transport: viem.http(this.config.rpcUrl, {
|
|
2452
3025
|
timeout: 15e3,
|
|
2453
3026
|
// 15 second timeout
|
|
@@ -2501,11 +3074,11 @@ var WalletManager = class _WalletManager {
|
|
|
2501
3074
|
*
|
|
2502
3075
|
* No fallback to placeholder addresses - WDK API is required for real addresses.
|
|
2503
3076
|
*/
|
|
2504
|
-
static async deriveAddressForChainAsync(seed,
|
|
2505
|
-
if (
|
|
3077
|
+
static async deriveAddressForChainAsync(seed, chain2, network = "mainnet", apiUrl) {
|
|
3078
|
+
if (chain2 === "ethereum") {
|
|
2506
3079
|
try {
|
|
2507
3080
|
const wdkService2 = getZubariWdkService({ network, apiUrl });
|
|
2508
|
-
const result2 = await wdkService2.deriveAddress(seed,
|
|
3081
|
+
const result2 = await wdkService2.deriveAddress(seed, chain2);
|
|
2509
3082
|
return result2.address;
|
|
2510
3083
|
} catch (error) {
|
|
2511
3084
|
console.warn("WDK service failed for Ethereum, using local derivation:", error);
|
|
@@ -2513,7 +3086,7 @@ var WalletManager = class _WalletManager {
|
|
|
2513
3086
|
}
|
|
2514
3087
|
}
|
|
2515
3088
|
const wdkService = getZubariWdkService({ network, apiUrl });
|
|
2516
|
-
const result = await wdkService.deriveAddress(seed,
|
|
3089
|
+
const result = await wdkService.deriveAddress(seed, chain2);
|
|
2517
3090
|
return result.address;
|
|
2518
3091
|
}
|
|
2519
3092
|
/**
|
|
@@ -2522,14 +3095,14 @@ var WalletManager = class _WalletManager {
|
|
|
2522
3095
|
*
|
|
2523
3096
|
* @throws Error for non-Ethereum chains - use WDK API instead
|
|
2524
3097
|
*/
|
|
2525
|
-
static deriveAddressForChain(seed,
|
|
2526
|
-
if (
|
|
3098
|
+
static deriveAddressForChain(seed, chain2) {
|
|
3099
|
+
if (chain2 === "ethereum") {
|
|
2527
3100
|
const ethPath = DERIVATION_PATHS["ethereum"];
|
|
2528
3101
|
const ethNode = ethers.HDNodeWallet.fromPhrase(seed, void 0, `${ethPath}/0`);
|
|
2529
3102
|
return ethNode.address;
|
|
2530
3103
|
}
|
|
2531
3104
|
throw new Error(
|
|
2532
|
-
`Sync derivation not supported for ${
|
|
3105
|
+
`Sync derivation not supported for ${chain2}. Use deriveAddressForChainAsync() with WDK API.`
|
|
2533
3106
|
);
|
|
2534
3107
|
}
|
|
2535
3108
|
/**
|
|
@@ -2561,9 +3134,9 @@ var WalletManager = class _WalletManager {
|
|
|
2561
3134
|
const wdkAddresses = await this.wdkService.deriveAllAddresses(this.currentSeed);
|
|
2562
3135
|
const enabledChainsSet = new Set(this.config.enabledChains);
|
|
2563
3136
|
const addresses = {};
|
|
2564
|
-
for (const [
|
|
2565
|
-
if (enabledChainsSet.has(
|
|
2566
|
-
addresses[
|
|
3137
|
+
for (const [chain2, address] of Object.entries(wdkAddresses)) {
|
|
3138
|
+
if (enabledChainsSet.has(chain2) && address) {
|
|
3139
|
+
addresses[chain2] = address;
|
|
2567
3140
|
}
|
|
2568
3141
|
}
|
|
2569
3142
|
this.derivedAddresses = addresses;
|
|
@@ -2604,10 +3177,10 @@ var WalletManager = class _WalletManager {
|
|
|
2604
3177
|
*/
|
|
2605
3178
|
normalizeAddresses(addresses) {
|
|
2606
3179
|
const normalized = {};
|
|
2607
|
-
for (const [
|
|
3180
|
+
for (const [chain2, value] of Object.entries(addresses)) {
|
|
2608
3181
|
const addr = this.normalizeAddress(value);
|
|
2609
3182
|
if (addr) {
|
|
2610
|
-
normalized[
|
|
3183
|
+
normalized[chain2] = addr;
|
|
2611
3184
|
}
|
|
2612
3185
|
}
|
|
2613
3186
|
return normalized;
|
|
@@ -2660,20 +3233,20 @@ var WalletManager = class _WalletManager {
|
|
|
2660
3233
|
* Get address for a specific chain
|
|
2661
3234
|
* Returns cached address or null - use deriveAllAddressesAsync to derive addresses
|
|
2662
3235
|
*/
|
|
2663
|
-
getAddressForChain(
|
|
2664
|
-
const cachedValue = this.derivedAddresses[
|
|
3236
|
+
getAddressForChain(chain2) {
|
|
3237
|
+
const cachedValue = this.derivedAddresses[chain2];
|
|
2665
3238
|
if (cachedValue) {
|
|
2666
|
-
console.log(`[WalletManager] getAddressForChain(${
|
|
3239
|
+
console.log(`[WalletManager] getAddressForChain(${chain2}) cached value:`, cachedValue, "type:", typeof cachedValue);
|
|
2667
3240
|
const addr = this.normalizeAddress(cachedValue);
|
|
2668
|
-
console.log(`[WalletManager] getAddressForChain(${
|
|
3241
|
+
console.log(`[WalletManager] getAddressForChain(${chain2}) normalized:`, addr);
|
|
2669
3242
|
if (addr) {
|
|
2670
|
-
this.derivedAddresses[
|
|
3243
|
+
this.derivedAddresses[chain2] = addr;
|
|
2671
3244
|
return addr;
|
|
2672
3245
|
}
|
|
2673
3246
|
}
|
|
2674
|
-
if (
|
|
2675
|
-
this.derivedAddresses[
|
|
2676
|
-
return this.derivedAddresses[
|
|
3247
|
+
if (chain2 === "ethereum" && this.currentSeed) {
|
|
3248
|
+
this.derivedAddresses[chain2] = _WalletManager.deriveAddressForChain(this.currentSeed, chain2);
|
|
3249
|
+
return this.derivedAddresses[chain2];
|
|
2677
3250
|
}
|
|
2678
3251
|
return null;
|
|
2679
3252
|
}
|
|
@@ -2686,11 +3259,11 @@ var WalletManager = class _WalletManager {
|
|
|
2686
3259
|
/**
|
|
2687
3260
|
* Set the selected chain
|
|
2688
3261
|
*/
|
|
2689
|
-
setSelectedChain(
|
|
2690
|
-
if (!this.config.enabledChains.includes(
|
|
2691
|
-
throw new Error(`Chain ${
|
|
3262
|
+
setSelectedChain(chain2) {
|
|
3263
|
+
if (!this.config.enabledChains.includes(chain2)) {
|
|
3264
|
+
throw new Error(`Chain ${chain2} is not enabled`);
|
|
2692
3265
|
}
|
|
2693
|
-
this.selectedChain =
|
|
3266
|
+
this.selectedChain = chain2;
|
|
2694
3267
|
}
|
|
2695
3268
|
/**
|
|
2696
3269
|
* Get the currently selected chain
|
|
@@ -2707,22 +3280,22 @@ var WalletManager = class _WalletManager {
|
|
|
2707
3280
|
/**
|
|
2708
3281
|
* Get chain configuration
|
|
2709
3282
|
*/
|
|
2710
|
-
getChainConfig(
|
|
2711
|
-
return getNetworkConfig(
|
|
3283
|
+
getChainConfig(chain2) {
|
|
3284
|
+
return getNetworkConfig(chain2, this.config.network === "testnet");
|
|
2712
3285
|
}
|
|
2713
3286
|
/**
|
|
2714
3287
|
* Fetch balance for a specific chain
|
|
2715
3288
|
* Note: Currently only Ethereum is implemented
|
|
2716
3289
|
*/
|
|
2717
|
-
async fetchBalanceForChain(
|
|
2718
|
-
const address = this.getAddressForChain(
|
|
3290
|
+
async fetchBalanceForChain(chain2) {
|
|
3291
|
+
const address = this.getAddressForChain(chain2);
|
|
2719
3292
|
if (!address) {
|
|
2720
|
-
throw new Error(`No address for chain ${
|
|
3293
|
+
throw new Error(`No address for chain ${chain2}`);
|
|
2721
3294
|
}
|
|
2722
|
-
const networkConfig = this.getChainConfig(
|
|
3295
|
+
const networkConfig = this.getChainConfig(chain2);
|
|
2723
3296
|
let balance = "0";
|
|
2724
3297
|
const tokenBalances = {};
|
|
2725
|
-
if (
|
|
3298
|
+
if (chain2 === "ethereum") {
|
|
2726
3299
|
const viemChain = this.config.network === "mainnet" ? chains.mainnet : chains.sepolia;
|
|
2727
3300
|
const isTestnet2 = this.config.network !== "mainnet";
|
|
2728
3301
|
const client = viem.createPublicClient({
|
|
@@ -2769,7 +3342,7 @@ var WalletManager = class _WalletManager {
|
|
|
2769
3342
|
} else if (usdtResult.status === "rejected") {
|
|
2770
3343
|
console.warn("[WalletManager] Failed to fetch ETH USDT balance:", usdtResult.reason);
|
|
2771
3344
|
}
|
|
2772
|
-
} else if (
|
|
3345
|
+
} else if (chain2 === "bitcoin") {
|
|
2773
3346
|
const isMainnet2 = this.config.network === "mainnet" || address.startsWith("bc1") || address.startsWith("1") || address.startsWith("3");
|
|
2774
3347
|
const apisToTry = isMainnet2 ? ["https://mempool.space/api"] : [
|
|
2775
3348
|
"https://mempool.space/testnet/api",
|
|
@@ -2801,7 +3374,7 @@ var WalletManager = class _WalletManager {
|
|
|
2801
3374
|
console.warn(`Failed to fetch from ${apiUrl}:`, error);
|
|
2802
3375
|
}
|
|
2803
3376
|
}
|
|
2804
|
-
} else if (
|
|
3377
|
+
} else if (chain2 === "solana") {
|
|
2805
3378
|
const rpcUrl = this.config.network === "mainnet" ? "https://api.mainnet-beta.solana.com" : "https://api.devnet.solana.com";
|
|
2806
3379
|
try {
|
|
2807
3380
|
const response = await fetch(rpcUrl, {
|
|
@@ -2821,7 +3394,7 @@ var WalletManager = class _WalletManager {
|
|
|
2821
3394
|
}
|
|
2822
3395
|
}
|
|
2823
3396
|
} catch (error) {
|
|
2824
|
-
console.warn(`Failed to fetch ${
|
|
3397
|
+
console.warn(`Failed to fetch ${chain2} balance:`, error);
|
|
2825
3398
|
}
|
|
2826
3399
|
const isTestnet2 = this.config.network !== "mainnet";
|
|
2827
3400
|
const usdtMint = USDT_ADDRESSES.solana?.[isTestnet2 ? "testnet" : "mainnet"];
|
|
@@ -2855,7 +3428,7 @@ var WalletManager = class _WalletManager {
|
|
|
2855
3428
|
console.warn("Failed to fetch Solana USDT balance:", error);
|
|
2856
3429
|
}
|
|
2857
3430
|
}
|
|
2858
|
-
} else if (
|
|
3431
|
+
} else if (chain2 === "tron") {
|
|
2859
3432
|
const tronConfig = getNetworkConfig("tron", this.config.network !== "mainnet");
|
|
2860
3433
|
const baseUrl = tronConfig.rpcUrl;
|
|
2861
3434
|
try {
|
|
@@ -2884,9 +3457,9 @@ var WalletManager = class _WalletManager {
|
|
|
2884
3457
|
}
|
|
2885
3458
|
}
|
|
2886
3459
|
} catch (error) {
|
|
2887
|
-
console.warn(`Failed to fetch ${
|
|
3460
|
+
console.warn(`Failed to fetch ${chain2} balance:`, error);
|
|
2888
3461
|
}
|
|
2889
|
-
} else if (
|
|
3462
|
+
} else if (chain2 === "ton") {
|
|
2890
3463
|
const isTestnet2 = this.config.network !== "mainnet";
|
|
2891
3464
|
const baseUrl = isTestnet2 ? "https://testnet.toncenter.com/api/v2" : "https://toncenter.com/api/v2";
|
|
2892
3465
|
try {
|
|
@@ -2902,36 +3475,25 @@ var WalletManager = class _WalletManager {
|
|
|
2902
3475
|
}
|
|
2903
3476
|
}
|
|
2904
3477
|
} catch (error) {
|
|
2905
|
-
console.warn(`Failed to fetch ${
|
|
3478
|
+
console.warn(`Failed to fetch ${chain2} balance:`, error);
|
|
2906
3479
|
}
|
|
2907
3480
|
const usdtJetton = USDT_ADDRESSES.ton?.[isTestnet2 ? "testnet" : "mainnet"];
|
|
2908
3481
|
if (usdtJetton) {
|
|
2909
|
-
const
|
|
3482
|
+
const v3BaseUrl = isTestnet2 ? "https://testnet.toncenter.com/api/v3" : "https://toncenter.com/api/v3";
|
|
2910
3483
|
try {
|
|
2911
|
-
const rawAddr = tonFriendlyToRaw(address);
|
|
2912
3484
|
const jettonResponse = await fetch(
|
|
2913
|
-
`${
|
|
3485
|
+
`${v3BaseUrl}/jetton/wallets?owner_address=${address}&jetton_address=${usdtJetton}&limit=1`,
|
|
2914
3486
|
{ headers: { "Accept": "application/json" } }
|
|
2915
3487
|
);
|
|
2916
3488
|
if (jettonResponse.ok) {
|
|
2917
3489
|
const jettonData = await jettonResponse.json();
|
|
2918
|
-
const
|
|
2919
|
-
if (
|
|
2920
|
-
|
|
2921
|
-
|
|
2922
|
-
|
|
2923
|
-
|
|
2924
|
-
|
|
2925
|
-
const rawBalance = jb.balance;
|
|
2926
|
-
if (rawBalance) {
|
|
2927
|
-
const decimals = jb.jetton?.decimals || 6;
|
|
2928
|
-
const usdtAmount = Number(BigInt(rawBalance)) / Math.pow(10, decimals);
|
|
2929
|
-
if (usdtAmount > 0) {
|
|
2930
|
-
tokenBalances.USDT = { balance: usdtAmount.toFixed(6), balanceUsd: usdtAmount };
|
|
2931
|
-
}
|
|
2932
|
-
}
|
|
2933
|
-
break;
|
|
2934
|
-
}
|
|
3490
|
+
const wallets = jettonData.jetton_wallets;
|
|
3491
|
+
if (wallets && wallets.length > 0) {
|
|
3492
|
+
const rawBalance = wallets[0].balance;
|
|
3493
|
+
if (rawBalance) {
|
|
3494
|
+
const usdtAmount = Number(BigInt(rawBalance)) / 1e6;
|
|
3495
|
+
if (usdtAmount > 0) {
|
|
3496
|
+
tokenBalances.USDT = { balance: usdtAmount.toFixed(6), balanceUsd: usdtAmount };
|
|
2935
3497
|
}
|
|
2936
3498
|
}
|
|
2937
3499
|
}
|
|
@@ -2940,7 +3502,7 @@ var WalletManager = class _WalletManager {
|
|
|
2940
3502
|
console.warn("Failed to fetch TON USDT jetton balance:", error);
|
|
2941
3503
|
}
|
|
2942
3504
|
}
|
|
2943
|
-
} else if (
|
|
3505
|
+
} else if (chain2 === "spark") {
|
|
2944
3506
|
try {
|
|
2945
3507
|
const response = await fetch(`${this.config.apiUrl}/api/wallets/wdk/balance`, {
|
|
2946
3508
|
method: "POST",
|
|
@@ -2959,14 +3521,14 @@ var WalletManager = class _WalletManager {
|
|
|
2959
3521
|
}
|
|
2960
3522
|
}
|
|
2961
3523
|
} catch (error) {
|
|
2962
|
-
console.warn(`Failed to fetch ${
|
|
3524
|
+
console.warn(`Failed to fetch ${chain2} balance:`, error);
|
|
2963
3525
|
}
|
|
2964
3526
|
}
|
|
2965
|
-
const priceUsd = await getPriceForChain(
|
|
3527
|
+
const priceUsd = await getPriceForChain(chain2);
|
|
2966
3528
|
const balanceNum = parseFloat(balance) || 0;
|
|
2967
3529
|
const balanceUsd = balanceNum * priceUsd;
|
|
2968
3530
|
return {
|
|
2969
|
-
chain,
|
|
3531
|
+
chain: chain2,
|
|
2970
3532
|
symbol: networkConfig.nativeCurrency.symbol,
|
|
2971
3533
|
balance,
|
|
2972
3534
|
balanceUsd,
|
|
@@ -2980,19 +3542,19 @@ var WalletManager = class _WalletManager {
|
|
|
2980
3542
|
*/
|
|
2981
3543
|
async fetchAllBalances() {
|
|
2982
3544
|
const balances = [];
|
|
2983
|
-
for (const
|
|
3545
|
+
for (const chain2 of this.config.enabledChains) {
|
|
2984
3546
|
try {
|
|
2985
|
-
const balance = await this.fetchBalanceForChain(
|
|
3547
|
+
const balance = await this.fetchBalanceForChain(chain2);
|
|
2986
3548
|
balances.push(balance);
|
|
2987
3549
|
} catch (error) {
|
|
2988
|
-
console.error(`Failed to fetch balance for ${
|
|
2989
|
-
const networkConfig = this.getChainConfig(
|
|
3550
|
+
console.error(`Failed to fetch balance for ${chain2}:`, error);
|
|
3551
|
+
const networkConfig = this.getChainConfig(chain2);
|
|
2990
3552
|
balances.push({
|
|
2991
|
-
chain,
|
|
3553
|
+
chain: chain2,
|
|
2992
3554
|
symbol: networkConfig.nativeCurrency.symbol,
|
|
2993
3555
|
balance: "0",
|
|
2994
3556
|
balanceUsd: 0,
|
|
2995
|
-
address: this.getAddressForChain(
|
|
3557
|
+
address: this.getAddressForChain(chain2) || "",
|
|
2996
3558
|
decimals: networkConfig.nativeCurrency.decimals
|
|
2997
3559
|
});
|
|
2998
3560
|
}
|
|
@@ -3022,13 +3584,13 @@ var WalletManager = class _WalletManager {
|
|
|
3022
3584
|
* @param token - Optional token symbol (e.g., 'USDT' for stablecoins)
|
|
3023
3585
|
* @returns Transaction result with hash and status
|
|
3024
3586
|
*/
|
|
3025
|
-
async sendTransaction(
|
|
3587
|
+
async sendTransaction(chain2, to, amount, token) {
|
|
3026
3588
|
if (!this.currentSeed) {
|
|
3027
3589
|
return { success: false, error: "Wallet is locked" };
|
|
3028
3590
|
}
|
|
3029
|
-
const fromAddress = this.getAddressForChain(
|
|
3591
|
+
const fromAddress = this.getAddressForChain(chain2);
|
|
3030
3592
|
if (!fromAddress) {
|
|
3031
|
-
return { success: false, error: `No address for chain ${
|
|
3593
|
+
return { success: false, error: `No address for chain ${chain2}` };
|
|
3032
3594
|
}
|
|
3033
3595
|
try {
|
|
3034
3596
|
const headers = {
|
|
@@ -3042,7 +3604,7 @@ var WalletManager = class _WalletManager {
|
|
|
3042
3604
|
headers,
|
|
3043
3605
|
body: JSON.stringify({
|
|
3044
3606
|
seed: this.currentSeed,
|
|
3045
|
-
chain,
|
|
3607
|
+
chain: chain2,
|
|
3046
3608
|
to,
|
|
3047
3609
|
amount,
|
|
3048
3610
|
token,
|
|
@@ -3051,12 +3613,12 @@ var WalletManager = class _WalletManager {
|
|
|
3051
3613
|
});
|
|
3052
3614
|
if (response.ok) {
|
|
3053
3615
|
const data = await response.json();
|
|
3054
|
-
console.log(`Transaction sent on ${
|
|
3616
|
+
console.log(`Transaction sent on ${chain2}:`, data);
|
|
3055
3617
|
let txHash = data.txHash || data.transactionHash || data.hash;
|
|
3056
3618
|
if (txHash && typeof txHash === "object" && "hash" in txHash) {
|
|
3057
3619
|
txHash = txHash.hash;
|
|
3058
3620
|
}
|
|
3059
|
-
if (
|
|
3621
|
+
if (chain2 === "ethereum" && txHash && (typeof txHash !== "string" || !txHash.startsWith("0x") || txHash.length !== 66)) {
|
|
3060
3622
|
console.warn(`Invalid Ethereum tx hash format: ${txHash} (length: ${txHash?.length}, expected: 66)`);
|
|
3061
3623
|
}
|
|
3062
3624
|
return {
|
|
@@ -3065,7 +3627,7 @@ var WalletManager = class _WalletManager {
|
|
|
3065
3627
|
from: fromAddress,
|
|
3066
3628
|
to,
|
|
3067
3629
|
amount,
|
|
3068
|
-
chain
|
|
3630
|
+
chain: chain2
|
|
3069
3631
|
};
|
|
3070
3632
|
}
|
|
3071
3633
|
const errorData = await response.json().catch(() => ({}));
|
|
@@ -3074,7 +3636,7 @@ var WalletManager = class _WalletManager {
|
|
|
3074
3636
|
error: errorData.error || `HTTP ${response.status}`
|
|
3075
3637
|
};
|
|
3076
3638
|
} catch (error) {
|
|
3077
|
-
console.error(`Transaction failed on ${
|
|
3639
|
+
console.error(`Transaction failed on ${chain2}:`, error);
|
|
3078
3640
|
return {
|
|
3079
3641
|
success: false,
|
|
3080
3642
|
error: error instanceof Error ? error.message : "Transaction failed"
|
|
@@ -3084,7 +3646,7 @@ var WalletManager = class _WalletManager {
|
|
|
3084
3646
|
/**
|
|
3085
3647
|
* Estimate transaction fee using Tether WDK
|
|
3086
3648
|
*/
|
|
3087
|
-
async estimateFee(
|
|
3649
|
+
async estimateFee(chain2, to, amount, token) {
|
|
3088
3650
|
try {
|
|
3089
3651
|
const headers = {
|
|
3090
3652
|
"Content-Type": "application/json"
|
|
@@ -3096,7 +3658,7 @@ var WalletManager = class _WalletManager {
|
|
|
3096
3658
|
method: "POST",
|
|
3097
3659
|
headers,
|
|
3098
3660
|
body: JSON.stringify({
|
|
3099
|
-
chain,
|
|
3661
|
+
chain: chain2,
|
|
3100
3662
|
to,
|
|
3101
3663
|
amount,
|
|
3102
3664
|
token,
|
|
@@ -7580,8 +8142,8 @@ async function fetchPrices2() {
|
|
|
7580
8142
|
if (response.ok) {
|
|
7581
8143
|
const data = await response.json();
|
|
7582
8144
|
const prices = {};
|
|
7583
|
-
for (const [
|
|
7584
|
-
prices[
|
|
8145
|
+
for (const [chain2, geckoId] of Object.entries(COINGECKO_IDS2)) {
|
|
8146
|
+
prices[chain2] = data[geckoId]?.usd || 0;
|
|
7585
8147
|
}
|
|
7586
8148
|
priceCache2 = { prices, timestamp: Date.now() };
|
|
7587
8149
|
return prices;
|
|
@@ -7591,9 +8153,9 @@ async function fetchPrices2() {
|
|
|
7591
8153
|
}
|
|
7592
8154
|
return priceCache2?.prices || {};
|
|
7593
8155
|
}
|
|
7594
|
-
async function getPriceForChain2(
|
|
8156
|
+
async function getPriceForChain2(chain2) {
|
|
7595
8157
|
const prices = await fetchPrices2();
|
|
7596
|
-
return prices[
|
|
8158
|
+
return prices[chain2] || 0;
|
|
7597
8159
|
}
|
|
7598
8160
|
var dynamicImport2 = new Function("specifier", "return import(specifier)");
|
|
7599
8161
|
async function loadWdkModules() {
|
|
@@ -7640,7 +8202,7 @@ var DEFAULT_RPC_URLS = {
|
|
|
7640
8202
|
// Uses Electrum testnet
|
|
7641
8203
|
solana: "https://api.devnet.solana.com",
|
|
7642
8204
|
ton: "https://testnet.toncenter.com/api/v2/jsonRPC",
|
|
7643
|
-
tron: "https://
|
|
8205
|
+
tron: "https://nile.trongrid.io",
|
|
7644
8206
|
spark: ""
|
|
7645
8207
|
// Uses Spark testnet
|
|
7646
8208
|
}
|
|
@@ -7659,7 +8221,7 @@ var EXPLORER_URLS = {
|
|
|
7659
8221
|
bitcoin: "https://mempool.space/testnet/tx/",
|
|
7660
8222
|
solana: "https://solscan.io/tx/?cluster=devnet&tx=",
|
|
7661
8223
|
ton: "https://testnet.tonscan.org/tx/",
|
|
7662
|
-
tron: "https://
|
|
8224
|
+
tron: "https://nile.tronscan.org/#/transaction/",
|
|
7663
8225
|
spark: "https://testnet.spark.info/tx/"
|
|
7664
8226
|
}
|
|
7665
8227
|
};
|
|
@@ -7683,19 +8245,19 @@ var TransactionService = class {
|
|
|
7683
8245
|
/**
|
|
7684
8246
|
* Get RPC URL for a chain
|
|
7685
8247
|
*/
|
|
7686
|
-
getRpcUrl(
|
|
8248
|
+
getRpcUrl(chain2) {
|
|
7687
8249
|
const networkUrls = DEFAULT_RPC_URLS[this.config.network];
|
|
7688
|
-
if (this.config.rpcUrls?.[
|
|
7689
|
-
return this.config.rpcUrls[
|
|
8250
|
+
if (this.config.rpcUrls?.[chain2]) {
|
|
8251
|
+
return this.config.rpcUrls[chain2];
|
|
7690
8252
|
}
|
|
7691
|
-
return networkUrls[
|
|
8253
|
+
return networkUrls[chain2] || "";
|
|
7692
8254
|
}
|
|
7693
8255
|
/**
|
|
7694
8256
|
* Get explorer URL for a transaction
|
|
7695
8257
|
*/
|
|
7696
|
-
getExplorerUrl(
|
|
8258
|
+
getExplorerUrl(chain2, txHash) {
|
|
7697
8259
|
const explorers = EXPLORER_URLS[this.config.network];
|
|
7698
|
-
const baseUrl = explorers[
|
|
8260
|
+
const baseUrl = explorers[chain2] || "";
|
|
7699
8261
|
return `${baseUrl}${txHash}`;
|
|
7700
8262
|
}
|
|
7701
8263
|
/**
|
|
@@ -7719,27 +8281,27 @@ var TransactionService = class {
|
|
|
7719
8281
|
* Get or create wallet instance for a specific chain
|
|
7720
8282
|
*/
|
|
7721
8283
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
7722
|
-
async getWallet(
|
|
8284
|
+
async getWallet(chain2) {
|
|
7723
8285
|
if (!this.seed) {
|
|
7724
8286
|
throw new Error("TransactionService not initialized. Call initialize() first.");
|
|
7725
8287
|
}
|
|
7726
|
-
if (this.wallets[
|
|
7727
|
-
return this.wallets[
|
|
8288
|
+
if (this.wallets[chain2]) {
|
|
8289
|
+
return this.wallets[chain2];
|
|
7728
8290
|
}
|
|
7729
8291
|
const isTestnet2 = this.config.network === "testnet";
|
|
7730
8292
|
try {
|
|
7731
|
-
switch (
|
|
8293
|
+
switch (chain2) {
|
|
7732
8294
|
case "ethereum": {
|
|
7733
8295
|
const rpcUrl = this.getRpcUrl("ethereum");
|
|
7734
8296
|
const wallet = new WalletManagerEvm(this.seed, { provider: rpcUrl });
|
|
7735
|
-
this.wallets[
|
|
8297
|
+
this.wallets[chain2] = wallet;
|
|
7736
8298
|
return wallet;
|
|
7737
8299
|
}
|
|
7738
8300
|
case "bitcoin": {
|
|
7739
8301
|
const wallet = new WalletManagerBtc(this.seed, {
|
|
7740
8302
|
network: isTestnet2 ? "testnet" : "bitcoin"
|
|
7741
8303
|
});
|
|
7742
|
-
this.wallets[
|
|
8304
|
+
this.wallets[chain2] = wallet;
|
|
7743
8305
|
return wallet;
|
|
7744
8306
|
}
|
|
7745
8307
|
case "solana": {
|
|
@@ -7747,7 +8309,7 @@ var TransactionService = class {
|
|
|
7747
8309
|
const wallet = new WalletManagerSolana(this.seed, {
|
|
7748
8310
|
rpcUrl
|
|
7749
8311
|
});
|
|
7750
|
-
this.wallets[
|
|
8312
|
+
this.wallets[chain2] = wallet;
|
|
7751
8313
|
return wallet;
|
|
7752
8314
|
}
|
|
7753
8315
|
case "ton": {
|
|
@@ -7755,7 +8317,7 @@ var TransactionService = class {
|
|
|
7755
8317
|
const wallet = new WalletManagerTon(this.seed, {
|
|
7756
8318
|
tonClient: { url }
|
|
7757
8319
|
});
|
|
7758
|
-
this.wallets[
|
|
8320
|
+
this.wallets[chain2] = wallet;
|
|
7759
8321
|
return wallet;
|
|
7760
8322
|
}
|
|
7761
8323
|
case "tron": {
|
|
@@ -7763,32 +8325,32 @@ var TransactionService = class {
|
|
|
7763
8325
|
const wallet = new WalletManagerTron(this.seed, {
|
|
7764
8326
|
provider: fullHost
|
|
7765
8327
|
});
|
|
7766
|
-
this.wallets[
|
|
8328
|
+
this.wallets[chain2] = wallet;
|
|
7767
8329
|
return wallet;
|
|
7768
8330
|
}
|
|
7769
8331
|
case "spark": {
|
|
7770
8332
|
const wallet = new WalletManagerSpark(this.seed, {
|
|
7771
8333
|
network: isTestnet2 ? "TESTNET" : "MAINNET"
|
|
7772
8334
|
});
|
|
7773
|
-
this.wallets[
|
|
8335
|
+
this.wallets[chain2] = wallet;
|
|
7774
8336
|
return wallet;
|
|
7775
8337
|
}
|
|
7776
8338
|
default:
|
|
7777
|
-
throw new Error(`Unsupported chain: ${
|
|
8339
|
+
throw new Error(`Unsupported chain: ${chain2}`);
|
|
7778
8340
|
}
|
|
7779
8341
|
} catch (error) {
|
|
7780
|
-
console.error(`Failed to initialize ${
|
|
8342
|
+
console.error(`Failed to initialize ${chain2} wallet:`, error);
|
|
7781
8343
|
throw error;
|
|
7782
8344
|
}
|
|
7783
8345
|
}
|
|
7784
8346
|
/**
|
|
7785
8347
|
* Estimate transaction fee
|
|
7786
8348
|
*/
|
|
7787
|
-
async estimateFee(
|
|
7788
|
-
const wallet = await this.getWallet(
|
|
8349
|
+
async estimateFee(chain2, params) {
|
|
8350
|
+
const wallet = await this.getWallet(chain2);
|
|
7789
8351
|
try {
|
|
7790
8352
|
const feeRates = await wallet.getFeeRates();
|
|
7791
|
-
if (
|
|
8353
|
+
if (chain2 === "ethereum") {
|
|
7792
8354
|
return {
|
|
7793
8355
|
slow: {
|
|
7794
8356
|
fee: `${feeRates.slow || "0"} Gwei`,
|
|
@@ -7803,7 +8365,7 @@ var TransactionService = class {
|
|
|
7803
8365
|
estimatedTime: "~30 sec"
|
|
7804
8366
|
}
|
|
7805
8367
|
};
|
|
7806
|
-
} else if (
|
|
8368
|
+
} else if (chain2 === "bitcoin") {
|
|
7807
8369
|
return {
|
|
7808
8370
|
slow: {
|
|
7809
8371
|
fee: `${feeRates.slow || feeRates.low || "0"} sat/vB`,
|
|
@@ -7835,7 +8397,7 @@ var TransactionService = class {
|
|
|
7835
8397
|
};
|
|
7836
8398
|
}
|
|
7837
8399
|
} catch (error) {
|
|
7838
|
-
console.error(`Error estimating fee for ${
|
|
8400
|
+
console.error(`Error estimating fee for ${chain2}:`, error);
|
|
7839
8401
|
return {
|
|
7840
8402
|
slow: { fee: "0", estimatedTime: "Unknown" },
|
|
7841
8403
|
medium: { fee: "0", estimatedTime: "Unknown" },
|
|
@@ -7846,8 +8408,8 @@ var TransactionService = class {
|
|
|
7846
8408
|
/**
|
|
7847
8409
|
* Send a transaction
|
|
7848
8410
|
*/
|
|
7849
|
-
async send(
|
|
7850
|
-
const wallet = await this.getWallet(
|
|
8411
|
+
async send(chain2, params) {
|
|
8412
|
+
const wallet = await this.getWallet(chain2);
|
|
7851
8413
|
const account = await wallet.getAccount(0);
|
|
7852
8414
|
const timestamp = Date.now();
|
|
7853
8415
|
try {
|
|
@@ -7867,17 +8429,17 @@ var TransactionService = class {
|
|
|
7867
8429
|
}
|
|
7868
8430
|
return {
|
|
7869
8431
|
hash: txHash,
|
|
7870
|
-
network:
|
|
8432
|
+
network: chain2,
|
|
7871
8433
|
status: "pending",
|
|
7872
|
-
explorerUrl: this.getExplorerUrl(
|
|
8434
|
+
explorerUrl: this.getExplorerUrl(chain2, txHash),
|
|
7873
8435
|
timestamp
|
|
7874
8436
|
};
|
|
7875
8437
|
} catch (error) {
|
|
7876
8438
|
const errorMessage = error instanceof Error ? error.message : "Transaction failed";
|
|
7877
|
-
console.error(`Transaction failed on ${
|
|
8439
|
+
console.error(`Transaction failed on ${chain2}:`, error);
|
|
7878
8440
|
return {
|
|
7879
8441
|
hash: "",
|
|
7880
|
-
network:
|
|
8442
|
+
network: chain2,
|
|
7881
8443
|
status: "failed",
|
|
7882
8444
|
error: errorMessage,
|
|
7883
8445
|
timestamp
|
|
@@ -7887,27 +8449,27 @@ var TransactionService = class {
|
|
|
7887
8449
|
/**
|
|
7888
8450
|
* Get transaction status
|
|
7889
8451
|
*/
|
|
7890
|
-
async getTransactionStatus(
|
|
7891
|
-
const wallet = await this.getWallet(
|
|
8452
|
+
async getTransactionStatus(chain2, txHash) {
|
|
8453
|
+
const wallet = await this.getWallet(chain2);
|
|
7892
8454
|
try {
|
|
7893
8455
|
const tx = await wallet.getTransaction(txHash);
|
|
7894
8456
|
return {
|
|
7895
8457
|
hash: txHash,
|
|
7896
|
-
network:
|
|
8458
|
+
network: chain2,
|
|
7897
8459
|
status: tx.confirmed ? "confirmed" : "pending",
|
|
7898
8460
|
blockNumber: tx.blockNumber,
|
|
7899
8461
|
gasUsed: tx.gasUsed?.toString(),
|
|
7900
8462
|
fee: tx.fee?.toString(),
|
|
7901
|
-
explorerUrl: this.getExplorerUrl(
|
|
8463
|
+
explorerUrl: this.getExplorerUrl(chain2, txHash),
|
|
7902
8464
|
timestamp: tx.timestamp || Date.now()
|
|
7903
8465
|
};
|
|
7904
8466
|
} catch (error) {
|
|
7905
8467
|
console.error(`Error getting transaction status for ${txHash}:`, error);
|
|
7906
8468
|
return {
|
|
7907
8469
|
hash: txHash,
|
|
7908
|
-
network:
|
|
8470
|
+
network: chain2,
|
|
7909
8471
|
status: "pending",
|
|
7910
|
-
explorerUrl: this.getExplorerUrl(
|
|
8472
|
+
explorerUrl: this.getExplorerUrl(chain2, txHash),
|
|
7911
8473
|
timestamp: Date.now()
|
|
7912
8474
|
};
|
|
7913
8475
|
}
|
|
@@ -7915,14 +8477,14 @@ var TransactionService = class {
|
|
|
7915
8477
|
/**
|
|
7916
8478
|
* Get transaction history for an address
|
|
7917
8479
|
*/
|
|
7918
|
-
async getTransactionHistory(
|
|
7919
|
-
const wallet = await this.getWallet(
|
|
8480
|
+
async getTransactionHistory(chain2, limit = 10) {
|
|
8481
|
+
const wallet = await this.getWallet(chain2);
|
|
7920
8482
|
const account = await wallet.getAccount(0);
|
|
7921
8483
|
try {
|
|
7922
8484
|
const history = await account.getTransactions({ limit });
|
|
7923
8485
|
return history.map((tx) => ({
|
|
7924
8486
|
hash: tx.hash || tx.txHash,
|
|
7925
|
-
network:
|
|
8487
|
+
network: chain2,
|
|
7926
8488
|
type: tx.type || (tx.from === account.address ? "send" : "receive"),
|
|
7927
8489
|
from: tx.from,
|
|
7928
8490
|
to: tx.to,
|
|
@@ -7934,20 +8496,20 @@ var TransactionService = class {
|
|
|
7934
8496
|
blockNumber: tx.blockNumber
|
|
7935
8497
|
}));
|
|
7936
8498
|
} catch (error) {
|
|
7937
|
-
console.error(`Error getting transaction history for ${
|
|
8499
|
+
console.error(`Error getting transaction history for ${chain2}:`, error);
|
|
7938
8500
|
return [];
|
|
7939
8501
|
}
|
|
7940
8502
|
}
|
|
7941
8503
|
/**
|
|
7942
8504
|
* Get balance for a specific chain
|
|
7943
8505
|
*/
|
|
7944
|
-
async getBalance(
|
|
7945
|
-
const wallet = await this.getWallet(
|
|
8506
|
+
async getBalance(chain2) {
|
|
8507
|
+
const wallet = await this.getWallet(chain2);
|
|
7946
8508
|
const account = await wallet.getAccount(0);
|
|
7947
8509
|
try {
|
|
7948
8510
|
const balance = await account.getBalance();
|
|
7949
8511
|
const balanceStr = balance.toString();
|
|
7950
|
-
const priceUsd = await getPriceForChain2(
|
|
8512
|
+
const priceUsd = await getPriceForChain2(chain2);
|
|
7951
8513
|
const balanceNum = parseFloat(balanceStr) || 0;
|
|
7952
8514
|
const balanceUsd = balanceNum * priceUsd;
|
|
7953
8515
|
return {
|
|
@@ -7955,7 +8517,7 @@ var TransactionService = class {
|
|
|
7955
8517
|
balanceUsd
|
|
7956
8518
|
};
|
|
7957
8519
|
} catch (error) {
|
|
7958
|
-
console.error(`Error getting balance for ${
|
|
8520
|
+
console.error(`Error getting balance for ${chain2}:`, error);
|
|
7959
8521
|
return { balance: "0", balanceUsd: 0 };
|
|
7960
8522
|
}
|
|
7961
8523
|
}
|
|
@@ -8023,6 +8585,14 @@ function normalizeAddress(address) {
|
|
|
8023
8585
|
}
|
|
8024
8586
|
return address.toLowerCase();
|
|
8025
8587
|
}
|
|
8588
|
+
/*! Bundled license information:
|
|
8589
|
+
|
|
8590
|
+
@scure/base/index.js:
|
|
8591
|
+
(*! scure-base - MIT License (c) 2022 Paul Miller (paulmillr.com) *)
|
|
8592
|
+
|
|
8593
|
+
@scure/bip32/index.js:
|
|
8594
|
+
(*! scure-bip32 - MIT License (c) 2022 Patricio Palladino, Paul Miller (paulmillr.com) *)
|
|
8595
|
+
*/
|
|
8026
8596
|
|
|
8027
8597
|
exports.BrowserAddressDerivation = BrowserAddressDerivation_exports;
|
|
8028
8598
|
exports.CURRENCY_ADDRESSES = CURRENCY_ADDRESSES;
|