From d7892f4404bddb8cd4a840450286a951ec8256a1 Mon Sep 17 00:00:00 2001 From: Jeff Emmett Date: Fri, 13 Feb 2026 07:17:36 -0700 Subject: [PATCH] Speed up data fetching: parallel across chains, sequential within Each chain has its own API server (different subdomain) so rate limits are independent. Now fetches all chains in parallel while keeping requests within each chain sequential. Removes unnecessary sleep() delays between requests to the same server. Co-Authored-By: Claude Opus 4.6 --- js/safe-api.js | 30 +++++++++++----------------- wallet-multichain-visualization.html | 2 +- wallet-timeline-visualization.html | 2 +- wallet-visualization.html | 2 +- 4 files changed, 15 insertions(+), 21 deletions(-) diff --git a/js/safe-api.js b/js/safe-api.js index 9365667..9f3cbdf 100644 --- a/js/safe-api.js +++ b/js/safe-api.js @@ -147,39 +147,33 @@ const SafeAPI = (() => { /** * Detect which chains have a Safe deployed for this address. - * Checks all supported chains in parallel. + * Each chain has its own API server, so we can check all in parallel. * Returns array of { chainId, chain, safeInfo } */ async function detectSafeChains(address) { - const entries = Object.entries(CHAINS); - const results = []; - - // Check chains sequentially with small delay to avoid rate limits - for (const [chainId, chain] of entries) { + const checks = Object.entries(CHAINS).map(async ([chainId, chain]) => { try { const info = await getSafeInfo(address, parseInt(chainId)); - if (info) results.push({ chainId: parseInt(chainId), chain, safeInfo: info }); + if (info) return { chainId: parseInt(chainId), chain, safeInfo: info }; } catch (e) { // Chain doesn't have this Safe or API error - skip } - await sleep(300); - } + return null; + }); - return results; + const results = await Promise.all(checks); + return results.filter(Boolean); } /** * Fetch comprehensive wallet data for a single chain. + * Sequential within the same chain to respect per-server rate limits. * Returns { info, balances, outgoing, incoming } */ async function fetchChainData(address, chainId) { - // Fetch sequentially to avoid rate limits const info = await getSafeInfo(address, chainId); - await sleep(200); const balances = await getBalances(address, chainId); - await sleep(200); const outgoing = await getAllMultisigTransactions(address, chainId); - await sleep(200); const incoming = await getAllIncomingTransfers(address, chainId); return { chainId, info, balances, outgoing, incoming }; @@ -187,18 +181,18 @@ const SafeAPI = (() => { /** * Fetch wallet data across all detected chains. + * Parallel across chains (different servers), sequential within each chain. * Returns Map */ async function fetchAllChainsData(address, detectedChains) { const dataMap = new Map(); - // Fetch chains sequentially to avoid rate limits - for (const { chainId } of detectedChains) { + const fetches = detectedChains.map(async ({ chainId }) => { const data = await fetchChainData(address, chainId); dataMap.set(chainId, data); - await sleep(200); - } + }); + await Promise.all(fetches); return dataMap; } diff --git a/wallet-multichain-visualization.html b/wallet-multichain-visualization.html index 0d7c5a0..87a6115 100644 --- a/wallet-multichain-visualization.html +++ b/wallet-multichain-visualization.html @@ -5,7 +5,7 @@ Multi-Chain Flow | rWallet.online - +