@zubari/sdk 0.1.6 → 0.1.8

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.mjs CHANGED
@@ -1415,6 +1415,47 @@ function createZubariWdkService(config) {
1415
1415
  }
1416
1416
 
1417
1417
  // src/wallet/WalletManager.ts
1418
+ var COINGECKO_IDS = {
1419
+ ethereum: "ethereum",
1420
+ bitcoin: "bitcoin",
1421
+ ton: "the-open-network",
1422
+ tron: "tron",
1423
+ solana: "solana",
1424
+ spark: "bitcoin"
1425
+ // Spark uses BTC
1426
+ };
1427
+ var priceCache = null;
1428
+ var PRICE_CACHE_TTL = 6e4;
1429
+ async function fetchPrices() {
1430
+ if (priceCache && Date.now() - priceCache.timestamp < PRICE_CACHE_TTL) {
1431
+ return priceCache.prices;
1432
+ }
1433
+ const ids = Object.values(COINGECKO_IDS).filter((v, i, a) => a.indexOf(v) === i).join(",");
1434
+ try {
1435
+ const response = await fetch(
1436
+ `https://api.coingecko.com/api/v3/simple/price?ids=${ids}&vs_currencies=usd`,
1437
+ {
1438
+ headers: { "Accept": "application/json" }
1439
+ }
1440
+ );
1441
+ if (response.ok) {
1442
+ const data = await response.json();
1443
+ const prices = {};
1444
+ for (const [chain, geckoId] of Object.entries(COINGECKO_IDS)) {
1445
+ prices[chain] = data[geckoId]?.usd || 0;
1446
+ }
1447
+ priceCache = { prices, timestamp: Date.now() };
1448
+ return prices;
1449
+ }
1450
+ } catch (error) {
1451
+ console.warn("Failed to fetch prices from CoinGecko:", error);
1452
+ }
1453
+ return priceCache?.prices || {};
1454
+ }
1455
+ async function getPriceForChain(chain) {
1456
+ const prices = await fetchPrices();
1457
+ return prices[chain] || 0;
1458
+ }
1418
1459
  var STORAGE_KEYS = {
1419
1460
  ENCRYPTED_SEED: "encrypted_seed",
1420
1461
  ACTIVE_WALLET: "active_wallet"
@@ -1887,22 +1928,36 @@ var WalletManager = class _WalletManager {
1887
1928
  console.warn(`Failed to fetch ${chain} balance:`, error);
1888
1929
  }
1889
1930
  } else if (chain === "bitcoin") {
1890
- const baseUrl = this.config.network === "mainnet" ? "https://blockstream.info/api" : "https://blockstream.info/testnet/api";
1891
- try {
1892
- const response = await fetch(`${baseUrl}/address/${address}`, {
1893
- headers: { "Accept": "application/json" }
1894
- });
1895
- if (response.ok) {
1896
- const data = await response.json();
1897
- const chainFunded = data.chain_stats?.funded_txo_sum || 0;
1898
- const chainSpent = data.chain_stats?.spent_txo_sum || 0;
1899
- const mempoolFunded = data.mempool_stats?.funded_txo_sum || 0;
1900
- const mempoolSpent = data.mempool_stats?.spent_txo_sum || 0;
1901
- const satoshis = chainFunded - chainSpent + (mempoolFunded - mempoolSpent);
1902
- balance = (satoshis / 1e8).toFixed(8);
1931
+ const isMainnet = this.config.network === "mainnet" || address.startsWith("bc1") || address.startsWith("1") || address.startsWith("3");
1932
+ const apisToTry = isMainnet ? ["https://mempool.space/api"] : [
1933
+ "https://mempool.space/testnet/api",
1934
+ // testnet3 first (more common)
1935
+ "https://mempool.space/testnet4/api"
1936
+ // then testnet4
1937
+ ];
1938
+ for (const apiUrl of apisToTry) {
1939
+ try {
1940
+ const response = await fetch(`${apiUrl}/address/${address}`, {
1941
+ headers: { "Accept": "application/json" }
1942
+ });
1943
+ if (response.ok) {
1944
+ const data = await response.json();
1945
+ const txCount = (data.chain_stats?.tx_count || 0) + (data.mempool_stats?.tx_count || 0);
1946
+ if (txCount > 0 || isMainnet) {
1947
+ const chainFunded = data.chain_stats?.funded_txo_sum || 0;
1948
+ const chainSpent = data.chain_stats?.spent_txo_sum || 0;
1949
+ const mempoolFunded = data.mempool_stats?.funded_txo_sum || 0;
1950
+ const mempoolSpent = data.mempool_stats?.spent_txo_sum || 0;
1951
+ const satoshis = chainFunded - chainSpent + (mempoolFunded - mempoolSpent);
1952
+ balance = (satoshis / 1e8).toFixed(8);
1953
+ console.log(`Bitcoin balance for ${address}: ${balance} BTC (${satoshis} sats) via ${apiUrl}`);
1954
+ break;
1955
+ }
1956
+ console.log(`No transactions found on ${apiUrl}, trying next...`);
1957
+ }
1958
+ } catch (error) {
1959
+ console.warn(`Failed to fetch from ${apiUrl}:`, error);
1903
1960
  }
1904
- } catch (error) {
1905
- console.warn(`Failed to fetch ${chain} balance:`, error);
1906
1961
  }
1907
1962
  } else if (chain === "solana") {
1908
1963
  const rpcUrl = this.config.network === "mainnet" ? "https://api.mainnet-beta.solana.com" : "https://api.devnet.solana.com";
@@ -1941,13 +1996,53 @@ var WalletManager = class _WalletManager {
1941
1996
  } catch (error) {
1942
1997
  console.warn(`Failed to fetch ${chain} balance:`, error);
1943
1998
  }
1999
+ } else if (chain === "ton") {
2000
+ const baseUrl = this.config.network === "mainnet" ? "https://toncenter.com/api/v2" : "https://testnet.toncenter.com/api/v2";
2001
+ try {
2002
+ const response = await fetch(`${baseUrl}/getAddressBalance?address=${address}`, {
2003
+ headers: { "Accept": "application/json" }
2004
+ });
2005
+ if (response.ok) {
2006
+ const data = await response.json();
2007
+ if (data.ok && data.result !== void 0) {
2008
+ const nanotons = BigInt(data.result);
2009
+ balance = (Number(nanotons) / 1e9).toFixed(9);
2010
+ console.log(`TON balance for ${address}: ${balance} TON`);
2011
+ }
2012
+ }
2013
+ } catch (error) {
2014
+ console.warn(`Failed to fetch ${chain} balance:`, error);
2015
+ }
2016
+ } else if (chain === "spark") {
2017
+ try {
2018
+ const response = await fetch(`${this.config.apiUrl}/api/wallets/wdk/balance`, {
2019
+ method: "POST",
2020
+ headers: { "Content-Type": "application/json" },
2021
+ body: JSON.stringify({
2022
+ chain: "spark",
2023
+ address,
2024
+ network: this.config.network
2025
+ })
2026
+ });
2027
+ if (response.ok) {
2028
+ const data = await response.json();
2029
+ if (data.success && data.balance !== void 0) {
2030
+ balance = (parseFloat(data.balance) / 1e8).toFixed(8);
2031
+ console.log(`Spark balance for ${address}: ${balance} BTC`);
2032
+ }
2033
+ }
2034
+ } catch (error) {
2035
+ console.warn(`Failed to fetch ${chain} balance:`, error);
2036
+ }
1944
2037
  }
2038
+ const priceUsd = await getPriceForChain(chain);
2039
+ const balanceNum = parseFloat(balance) || 0;
2040
+ const balanceUsd = balanceNum * priceUsd;
1945
2041
  return {
1946
2042
  chain,
1947
2043
  symbol: networkConfig.nativeCurrency.symbol,
1948
2044
  balance,
1949
- balanceUsd: 0,
1950
- // TODO: Implement price fetching
2045
+ balanceUsd,
1951
2046
  address,
1952
2047
  decimals: networkConfig.nativeCurrency.decimals
1953
2048
  };
@@ -2463,6 +2558,47 @@ var WalletManagerTron;
2463
2558
  var WalletManagerSpark;
2464
2559
  var wdkLoaded = false;
2465
2560
  var wdkLoadError = null;
2561
+ var COINGECKO_IDS2 = {
2562
+ ethereum: "ethereum",
2563
+ bitcoin: "bitcoin",
2564
+ ton: "the-open-network",
2565
+ tron: "tron",
2566
+ solana: "solana",
2567
+ spark: "bitcoin"
2568
+ // Spark uses BTC
2569
+ };
2570
+ var priceCache2 = null;
2571
+ var PRICE_CACHE_TTL2 = 6e4;
2572
+ async function fetchPrices2() {
2573
+ if (priceCache2 && Date.now() - priceCache2.timestamp < PRICE_CACHE_TTL2) {
2574
+ return priceCache2.prices;
2575
+ }
2576
+ const ids = Object.values(COINGECKO_IDS2).filter((v, i, a) => a.indexOf(v) === i).join(",");
2577
+ try {
2578
+ const response = await fetch(
2579
+ `https://api.coingecko.com/api/v3/simple/price?ids=${ids}&vs_currencies=usd`,
2580
+ {
2581
+ headers: { "Accept": "application/json" }
2582
+ }
2583
+ );
2584
+ if (response.ok) {
2585
+ const data = await response.json();
2586
+ const prices = {};
2587
+ for (const [chain, geckoId] of Object.entries(COINGECKO_IDS2)) {
2588
+ prices[chain] = data[geckoId]?.usd || 0;
2589
+ }
2590
+ priceCache2 = { prices, timestamp: Date.now() };
2591
+ return prices;
2592
+ }
2593
+ } catch (error) {
2594
+ console.warn("Failed to fetch prices from CoinGecko:", error);
2595
+ }
2596
+ return priceCache2?.prices || {};
2597
+ }
2598
+ async function getPriceForChain2(chain) {
2599
+ const prices = await fetchPrices2();
2600
+ return prices[chain] || 0;
2601
+ }
2466
2602
  var dynamicImport2 = new Function("specifier", "return import(specifier)");
2467
2603
  async function loadWdkModules() {
2468
2604
  if (wdkLoaded) return;
@@ -2814,10 +2950,13 @@ var TransactionService = class {
2814
2950
  const account = await wallet.getAccount(0);
2815
2951
  try {
2816
2952
  const balance = await account.getBalance();
2953
+ const balanceStr = balance.toString();
2954
+ const priceUsd = await getPriceForChain2(chain);
2955
+ const balanceNum = parseFloat(balanceStr) || 0;
2956
+ const balanceUsd = balanceNum * priceUsd;
2817
2957
  return {
2818
- balance: balance.toString(),
2819
- balanceUsd: 0
2820
- // TODO: Implement price fetching
2958
+ balance: balanceStr,
2959
+ balanceUsd
2821
2960
  };
2822
2961
  } catch (error) {
2823
2962
  console.error(`Error getting balance for ${chain}:`, error);