@routstr/sdk 0.3.2 → 0.3.4

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.
Files changed (39) hide show
  1. package/dist/client/index.d.mts +9 -5
  2. package/dist/client/index.d.ts +9 -5
  3. package/dist/client/index.js +70 -131
  4. package/dist/client/index.js.map +1 -1
  5. package/dist/client/index.mjs +70 -131
  6. package/dist/client/index.mjs.map +1 -1
  7. package/dist/discovery/index.d.mts +8 -2
  8. package/dist/discovery/index.d.ts +8 -2
  9. package/dist/discovery/index.js +27 -16
  10. package/dist/discovery/index.js.map +1 -1
  11. package/dist/discovery/index.mjs +27 -16
  12. package/dist/discovery/index.mjs.map +1 -1
  13. package/dist/index.d.mts +10 -8
  14. package/dist/index.d.ts +10 -8
  15. package/dist/index.js +141 -185
  16. package/dist/index.js.map +1 -1
  17. package/dist/index.mjs +140 -186
  18. package/dist/index.mjs.map +1 -1
  19. package/dist/{interfaces-C5fLD3jB.d.mts → interfaces-Bp0Ngmqv.d.mts} +1 -1
  20. package/dist/{interfaces-BxDEka72.d.ts → interfaces-CIfd_phZ.d.ts} +1 -1
  21. package/dist/{interfaces-BWJJTCXO.d.mts → interfaces-Cxi8R4TT.d.mts} +1 -1
  22. package/dist/{interfaces-B62Rw-dd.d.ts → interfaces-D2FDCLyP.d.ts} +1 -1
  23. package/dist/storage/index.d.mts +9 -7
  24. package/dist/storage/index.d.ts +9 -7
  25. package/dist/storage/index.js +51 -34
  26. package/dist/storage/index.js.map +1 -1
  27. package/dist/storage/index.mjs +51 -34
  28. package/dist/storage/index.mjs.map +1 -1
  29. package/dist/{store-h7m23ffq.d.ts → store-BD5zF9Hp.d.ts} +4 -4
  30. package/dist/{store-DGeLPv9E.d.mts → store-CBSyK2qg.d.mts} +4 -4
  31. package/dist/{types-BYj_8c5c.d.mts → types-DPQM6tIG.d.mts} +10 -1
  32. package/dist/{types-BYj_8c5c.d.ts → types-DPQM6tIG.d.ts} +10 -1
  33. package/dist/wallet/index.d.mts +8 -6
  34. package/dist/wallet/index.d.ts +8 -6
  35. package/dist/wallet/index.js +43 -52
  36. package/dist/wallet/index.js.map +1 -1
  37. package/dist/wallet/index.mjs +43 -52
  38. package/dist/wallet/index.mjs.map +1 -1
  39. package/package.json +3 -2
package/dist/index.js CHANGED
@@ -8,6 +8,30 @@ var vanilla = require('zustand/vanilla');
8
8
  var stream = require('stream');
9
9
  var string_decoder = require('string_decoder');
10
10
 
11
+ // core/types.ts
12
+ function makeConsoleLogger(prefix) {
13
+ const fmt = (args) => prefix ? [prefix, ...args] : args;
14
+ return {
15
+ log: (...args) => console.log(...fmt(args)),
16
+ warn: (...args) => console.warn(...fmt(args)),
17
+ error: (...args) => console.error(...fmt(args)),
18
+ debug: (...args) => console.log(...fmt(args)),
19
+ child: (p) => makeConsoleLogger(prefix ? `${prefix}:${p}` : p)
20
+ };
21
+ }
22
+ var consoleLogger = makeConsoleLogger();
23
+ var noopLogger = {
24
+ log: () => {
25
+ },
26
+ warn: () => {
27
+ },
28
+ error: () => {
29
+ },
30
+ debug: () => {
31
+ },
32
+ child: () => noopLogger
33
+ };
34
+
11
35
  // core/errors.ts
12
36
  var InsufficientBalanceError = class extends Error {
13
37
  constructor(required, available, maxMintBalance = 0, maxMintUrl = "", customMessage) {
@@ -104,11 +128,13 @@ var ModelManager = class _ModelManager {
104
128
  this.cacheTTL = config.cacheTTL || 210 * 60 * 1e3;
105
129
  this.includeProviderUrls = config.includeProviderUrls || [];
106
130
  this.excludeProviderUrls = config.excludeProviderUrls || [];
131
+ this.logger = (config.logger ?? consoleLogger).child("ModelManager");
107
132
  }
108
133
  cacheTTL;
109
134
  providerDirectoryUrl;
110
135
  includeProviderUrls;
111
136
  excludeProviderUrls;
137
+ logger;
112
138
  /**
113
139
  * Get the list of bootstrapped provider base URLs
114
140
  * @returns Array of provider base URLs
@@ -154,7 +180,7 @@ var ModelManager = class _ModelManager {
154
180
  return filtered;
155
181
  }
156
182
  } catch (e) {
157
- console.warn("Nostr bootstrap failed, falling back to HTTP:", e);
183
+ this.logger.warn("Nostr bootstrap failed, falling back to HTTP:", e);
158
184
  }
159
185
  return this.bootstrapFromHttp(torMode, forceRefresh);
160
186
  }
@@ -230,10 +256,7 @@ var ModelManager = class _ModelManager {
230
256
  }
231
257
  }
232
258
  } catch {
233
- console.warn(
234
- "[NostrBootstrap] Failed to parse Nostr event content:",
235
- event.id
236
- );
259
+ this.logger.warn("NostrBootstrap: failed to parse event content:", event.id);
237
260
  }
238
261
  }
239
262
  }
@@ -287,7 +310,7 @@ var ModelManager = class _ModelManager {
287
310
  }
288
311
  return list;
289
312
  } catch (e) {
290
- console.error("Failed to bootstrap providers", e);
313
+ this.logger.error("Failed to bootstrap providers", e);
291
314
  throw new ProviderBootstrapError([], `Provider bootstrap failed: ${e}`);
292
315
  }
293
316
  }
@@ -353,9 +376,9 @@ var ModelManager = class _ModelManager {
353
376
  return { success: true, base, list };
354
377
  } catch (error) {
355
378
  if (this.isProviderDownError(error)) {
356
- console.warn(`Provider ${base} is down right now.`);
379
+ this.logger.warn(`Provider ${base} is down right now.`);
357
380
  } else {
358
- console.warn(`Failed to fetch models from ${base}:`, error);
381
+ this.logger.warn(`Failed to fetch models from ${base}:`, error);
359
382
  }
360
383
  this.adapter.setProviderLastUpdate(base, Date.now());
361
384
  return { success: false, base };
@@ -512,10 +535,7 @@ var ModelManager = class _ModelManager {
512
535
  this.adapter.setRoutstr21ModelsLastUpdate(Date.now());
513
536
  return models;
514
537
  } catch {
515
- console.warn(
516
- "[Routstr21Models] Failed to parse Nostr event content:",
517
- event.id
518
- );
538
+ this.logger.warn("Routstr21Models: failed to parse Nostr event content:", event.id);
519
539
  return cachedModels.length > 0 ? cachedModels : [];
520
540
  }
521
541
  }
@@ -526,8 +546,10 @@ var MintDiscovery = class {
526
546
  constructor(adapter, config = {}) {
527
547
  this.adapter = adapter;
528
548
  this.cacheTTL = config.cacheTTL || 21 * 60 * 1e3;
549
+ this.logger = (config.logger ?? consoleLogger).child("MintDiscovery");
529
550
  }
530
551
  cacheTTL;
552
+ logger;
531
553
  /**
532
554
  * Fetch mints from all providers via their /v1/info endpoints
533
555
  * Caches mints and full provider info for later access
@@ -578,9 +600,9 @@ var MintDiscovery = class {
578
600
  } catch (error) {
579
601
  this.adapter.setProviderLastUpdate(base, Date.now());
580
602
  if (this.isProviderDownError(error)) {
581
- console.warn(`Provider ${base} is down right now.`);
603
+ this.logger.warn(`Provider ${base} is down right now.`);
582
604
  } else {
583
- console.warn(`Failed to fetch mints from ${base}:`, error);
605
+ this.logger.warn(`Failed to fetch mints from ${base}:`, error);
584
606
  }
585
607
  return { success: false, base, mints: [], info: null };
586
608
  }
@@ -594,14 +616,14 @@ var MintDiscovery = class {
594
616
  infoFromAllProviders[base] = info;
595
617
  }
596
618
  } else {
597
- console.error("Mint discovery error:", result.reason);
619
+ this.logger.error("Mint discovery error:", result.reason);
598
620
  }
599
621
  }
600
622
  try {
601
623
  this.adapter.setCachedMints(mintsFromAllProviders);
602
624
  this.adapter.setCachedProviderInfo(infoFromAllProviders);
603
625
  } catch (error) {
604
- console.error("Error caching mint discovery results:", error);
626
+ this.logger.error("Error caching mint discovery results:", error);
605
627
  }
606
628
  return {
607
629
  mintsFromProviders: mintsFromAllProviders,
@@ -740,14 +762,16 @@ function selectMintWithBalance(balances, units, amount, excludeMints = []) {
740
762
  return { selectedMintUrl: null, selectedMintBalance: 0 };
741
763
  }
742
764
  var CashuSpender = class {
743
- constructor(walletAdapter, storageAdapter, _providerRegistry, balanceManager) {
765
+ constructor(walletAdapter, storageAdapter, _providerRegistry, balanceManager, logger) {
744
766
  this.walletAdapter = walletAdapter;
745
767
  this.storageAdapter = storageAdapter;
746
768
  this._providerRegistry = _providerRegistry;
747
769
  this.balanceManager = balanceManager;
770
+ this.logger = (logger ?? consoleLogger).child("CashuSpender");
748
771
  }
749
772
  _isBusy = false;
750
773
  debugLevel = "WARN";
774
+ logger;
751
775
  async receiveToken(token) {
752
776
  try {
753
777
  const result = await this.walletAdapter.receiveToken(token);
@@ -843,13 +867,13 @@ var CashuSpender = class {
843
867
  if (levelPriority[level] >= levelPriority[this.debugLevel]) {
844
868
  switch (level) {
845
869
  case "DEBUG":
846
- console.log(...args);
870
+ this.logger.log(...args);
847
871
  break;
848
872
  case "WARN":
849
- console.warn(...args);
873
+ this.logger.warn(...args);
850
874
  break;
851
875
  case "ERROR":
852
- console.error(...args);
876
+ this.logger.error(...args);
853
877
  break;
854
878
  }
855
879
  }
@@ -1276,10 +1300,11 @@ var CashuSpender = class {
1276
1300
 
1277
1301
  // wallet/BalanceManager.ts
1278
1302
  var BalanceManager = class _BalanceManager {
1279
- constructor(walletAdapter, storageAdapter, providerRegistry, cashuSpender) {
1303
+ constructor(walletAdapter, storageAdapter, providerRegistry, cashuSpender, logger) {
1280
1304
  this.walletAdapter = walletAdapter;
1281
1305
  this.storageAdapter = storageAdapter;
1282
1306
  this.providerRegistry = providerRegistry;
1307
+ this.logger = (logger ?? consoleLogger).child("BalanceManager");
1283
1308
  if (cashuSpender) {
1284
1309
  this.cashuSpender = cashuSpender;
1285
1310
  } else {
@@ -1296,6 +1321,7 @@ var BalanceManager = class _BalanceManager {
1296
1321
  providerWalletOps = /* @__PURE__ */ new Map();
1297
1322
  /** Cooldown (ms) between opposite operations on the same provider */
1298
1323
  static PROVIDER_WALLET_COOLDOWN_MS = 1e4;
1324
+ logger;
1299
1325
  /**
1300
1326
  * Check whether a wallet operation (topup/refund) may run for a provider.
1301
1327
  * Returns the reason when blocked.
@@ -1370,7 +1396,7 @@ var BalanceManager = class _BalanceManager {
1370
1396
  const { mintUrl, baseUrl, apiKey, forceRefund } = options;
1371
1397
  const guard = this._canRunProviderWalletOperation(baseUrl, "refund");
1372
1398
  if (!guard.allowed) {
1373
- console.log(`[BalanceManager] Skipping refund for ${baseUrl} - ${guard.reason}`);
1399
+ this.logger.log(`Skipping refund for ${baseUrl} - ${guard.reason}`);
1374
1400
  return { success: false, message: guard.reason };
1375
1401
  }
1376
1402
  this._beginProviderWalletOperation(baseUrl, "refund");
@@ -1390,9 +1416,7 @@ var BalanceManager = class _BalanceManager {
1390
1416
  if (apiKeyEntry?.lastUsed) {
1391
1417
  const fiveMinutesAgo = Date.now() - 5 * 60 * 1e3;
1392
1418
  if (apiKeyEntry.lastUsed > fiveMinutesAgo) {
1393
- console.log(
1394
- `[BalanceManager] Skipping refund for ${baseUrl} - used ${Math.round((Date.now() - apiKeyEntry.lastUsed) / 1e3)}s ago`
1395
- );
1419
+ this.logger.log(`Skipping refund for ${baseUrl} - used ${Math.round((Date.now() - apiKeyEntry.lastUsed) / 1e3)}s ago`);
1396
1420
  return {
1397
1421
  success: false,
1398
1422
  message: "API key was used recently, skipping refund"
@@ -1434,7 +1458,7 @@ var BalanceManager = class _BalanceManager {
1434
1458
  requestId: fetchResult.requestId
1435
1459
  };
1436
1460
  } catch (error) {
1437
- console.error("[BalanceManager] API key refund error", error);
1461
+ this.logger.error("API key refund error", error);
1438
1462
  return this._handleRefundError(error, mintUrl, fetchResult?.requestId);
1439
1463
  }
1440
1464
  }
@@ -1486,7 +1510,7 @@ var BalanceManager = class _BalanceManager {
1486
1510
  };
1487
1511
  } catch (error) {
1488
1512
  clearTimeout(timeoutId);
1489
- console.error("[BalanceManager.fetchRefundToken] Fetch error", error);
1513
+ this.logger.error("fetchRefundToken fetch error", error);
1490
1514
  if (error instanceof Error) {
1491
1515
  if (error.name === "AbortError") {
1492
1516
  return {
@@ -1512,7 +1536,7 @@ var BalanceManager = class _BalanceManager {
1512
1536
  const { mintUrl, baseUrl, amount, token: providedToken } = options;
1513
1537
  const guard = this._canRunProviderWalletOperation(baseUrl, "topup");
1514
1538
  if (!guard.allowed) {
1515
- console.log(`[BalanceManager] Skipping topup for ${baseUrl} - ${guard.reason}`);
1539
+ this.logger.log(`Skipping topup for ${baseUrl} - ${guard.reason}`);
1516
1540
  return { success: false, message: guard.reason };
1517
1541
  }
1518
1542
  this._beginProviderWalletOperation(baseUrl, "topup");
@@ -1549,7 +1573,7 @@ var BalanceManager = class _BalanceManager {
1549
1573
  cashuToken = tokenResult.token;
1550
1574
  const topUpResult = await this._postTopUp(baseUrl, apiKey, cashuToken);
1551
1575
  requestId = topUpResult.requestId;
1552
- console.log(topUpResult);
1576
+ this.logger.log("topUpResult:", topUpResult);
1553
1577
  if (!topUpResult.success) {
1554
1578
  await this._recoverFailedTopUp(cashuToken);
1555
1579
  return {
@@ -1565,10 +1589,7 @@ var BalanceManager = class _BalanceManager {
1565
1589
  requestId
1566
1590
  };
1567
1591
  } catch (error) {
1568
- console.log(
1569
- "DEBUG",
1570
- `[TopuPU] topup: Topup result for ${baseUrl}: error=${error}`
1571
- );
1592
+ this.logger.log(`topup error for ${baseUrl}: ${error}`);
1572
1593
  if (cashuToken) {
1573
1594
  await this._recoverFailedTopUp(cashuToken);
1574
1595
  }
@@ -1585,13 +1606,9 @@ var BalanceManager = class _BalanceManager {
1585
1606
  p2pkPubkey
1586
1607
  } = options;
1587
1608
  const adjustedAmount = Math.ceil(amount);
1588
- console.log(
1589
- `[BalanceManager.createProviderToken] Starting: baseUrl=${baseUrl}, mintUrl=${mintUrl}, amount=${amount}, adjustedAmount=${adjustedAmount}, retryCount=${retryCount}`
1590
- );
1609
+ this.logger.log(`createProviderToken: baseUrl=${baseUrl} mintUrl=${mintUrl} amount=${amount} adjustedAmount=${adjustedAmount} retryCount=${retryCount}`);
1591
1610
  if (!adjustedAmount || isNaN(adjustedAmount)) {
1592
- console.error(
1593
- `[BalanceManager.createProviderToken] FAILURE: Invalid amount - amount=${amount}, adjustedAmount=${adjustedAmount}`
1594
- );
1611
+ this.logger.error(`createProviderToken: invalid amount=${amount}`);
1595
1612
  return { success: false, error: "Invalid top up amount" };
1596
1613
  }
1597
1614
  const balanceState = await this.getBalanceState();
@@ -1622,9 +1639,7 @@ var BalanceManager = class _BalanceManager {
1622
1639
  { url: "", balance: 0 }
1623
1640
  ).url
1624
1641
  );
1625
- console.error(
1626
- `[BalanceManager.createProviderToken] FAILURE: Insufficient balance - required=${adjustedAmount}, available=${totalMintBalance + targetProviderBalance}, totalMintBalance=${totalMintBalance}, targetProviderBalance=${targetProviderBalance}, refundableProviderBalance=${refundableProviderBalance}`
1627
- );
1642
+ this.logger.error(`createProviderToken: insufficient balance required=${adjustedAmount} available=${totalMintBalance + targetProviderBalance} totalMint=${totalMintBalance} targetProvider=${targetProviderBalance}`);
1628
1643
  return { success: false, error: error.message };
1629
1644
  }
1630
1645
  const providerMints = baseUrl && this.providerRegistry ? this.providerRegistry.getProviderMints(baseUrl) : [];
@@ -1660,9 +1675,7 @@ var BalanceManager = class _BalanceManager {
1660
1675
  maxMintUrl = mintUrl2;
1661
1676
  }
1662
1677
  }
1663
- console.error(
1664
- `[BalanceManager.createProviderToken] FAILURE: No candidate mints found - requiredAmount=${requiredAmount}, totalMintBalance=${totalMintBalance}, maxBalance=${maxBalance}, maxMintUrl=${maxMintUrl}, providerMints=${JSON.stringify(providerMints)}`
1665
- );
1678
+ this.logger.error(`createProviderToken: no candidate mints required=${requiredAmount} totalMint=${totalMintBalance} maxBalance=${maxBalance} maxMint=${maxMintUrl}`);
1666
1679
  const error = new InsufficientBalanceError(
1667
1680
  adjustedAmount,
1668
1681
  totalMintBalance,
@@ -1674,17 +1687,13 @@ var BalanceManager = class _BalanceManager {
1674
1687
  let lastError;
1675
1688
  for (const candidateMint of candidates) {
1676
1689
  try {
1677
- console.log(
1678
- `[BalanceManager.createProviderToken] Attempting mint: ${candidateMint}, amount: ${requiredAmount}`
1679
- );
1690
+ this.logger.log(`createProviderToken: attempting mint=${candidateMint} amount=${requiredAmount}`);
1680
1691
  const token = await this.walletAdapter.sendToken(
1681
1692
  candidateMint,
1682
1693
  requiredAmount,
1683
1694
  p2pkPubkey
1684
1695
  );
1685
- console.log(
1686
- `[BalanceManager.createProviderToken] SUCCESS: Token created from mint ${candidateMint}, all mint balances: ${JSON.stringify(Object.fromEntries(Object.entries(balances).map(([mint, balance]) => [mint, getBalanceInSats(balance, units[mint])])))}`
1687
- );
1696
+ this.logger.log(`createProviderToken: success from mint=${candidateMint}`);
1688
1697
  return {
1689
1698
  success: true,
1690
1699
  token,
@@ -1693,15 +1702,11 @@ var BalanceManager = class _BalanceManager {
1693
1702
  };
1694
1703
  } catch (error) {
1695
1704
  const errorMsg = error instanceof Error ? error.message : String(error);
1696
- console.error(
1697
- `[BalanceManager.createProviderToken] FAILURE: Mint ${candidateMint} failed with error: ${errorMsg}`
1698
- );
1705
+ this.logger.error(`createProviderToken: mint=${candidateMint} failed: ${errorMsg}`);
1699
1706
  if (error instanceof Error) {
1700
1707
  lastError = errorMsg;
1701
1708
  if (isNetworkErrorMessage(error.message)) {
1702
- console.warn(
1703
- `[BalanceManager.createProviderToken] Network error from ${candidateMint}, trying next mint...`
1704
- );
1709
+ this.logger.warn(`createProviderToken: network error from ${candidateMint}, trying next mint...`);
1705
1710
  continue;
1706
1711
  }
1707
1712
  }
@@ -1711,9 +1716,7 @@ var BalanceManager = class _BalanceManager {
1711
1716
  };
1712
1717
  }
1713
1718
  }
1714
- console.error(
1715
- `[BalanceManager.createProviderToken] FAILURE: All candidate mints exhausted - lastError=${lastError}, candidates=${JSON.stringify(candidates)}`
1716
- );
1719
+ this.logger.error(`createProviderToken: all candidate mints exhausted lastError=${lastError}`);
1717
1720
  return {
1718
1721
  success: false,
1719
1722
  error: lastError || "All candidate mints failed while creating top up token"
@@ -1828,7 +1831,7 @@ var BalanceManager = class _BalanceManager {
1828
1831
  return { success: true, requestId };
1829
1832
  } catch (error) {
1830
1833
  clearTimeout(timeoutId);
1831
- console.error("[BalanceManager._postTopUp] Fetch error", error);
1834
+ this.logger.error("_postTopUp fetch error", error);
1832
1835
  if (error instanceof Error) {
1833
1836
  if (error.name === "AbortError") {
1834
1837
  return {
@@ -1854,10 +1857,7 @@ var BalanceManager = class _BalanceManager {
1854
1857
  try {
1855
1858
  await this.cashuSpender.receiveToken(cashuToken);
1856
1859
  } catch (error) {
1857
- console.error(
1858
- "[BalanceManager._recoverFailedTopUp] Failed to recover token",
1859
- error
1860
- );
1860
+ this.logger.error("_recoverFailedTopUp: failed to recover token", error);
1861
1861
  }
1862
1862
  }
1863
1863
  /**
@@ -1910,9 +1910,9 @@ var BalanceManager = class _BalanceManager {
1910
1910
  apiKey: data.api_key
1911
1911
  };
1912
1912
  } else {
1913
- console.log(response.status);
1913
+ this.logger.warn(`getTokenBalance: status=${response.status}`);
1914
1914
  const data = await response.json();
1915
- console.log("FAILED ", data);
1915
+ this.logger.warn("getTokenBalance: FAILED", data);
1916
1916
  const isInvalidApiKey = response.status === 401 && data?.detail?.error?.code === "invalid_api_key" && data?.detail?.error?.message?.includes("proofs already spent");
1917
1917
  return {
1918
1918
  amount: -1,
@@ -1923,7 +1923,7 @@ var BalanceManager = class _BalanceManager {
1923
1923
  };
1924
1924
  }
1925
1925
  } catch (error) {
1926
- console.error("ERRORR IN RESTPONSE", error);
1926
+ this.logger.error("getTokenBalance error", error);
1927
1927
  }
1928
1928
  return { amount: -1, reserved: 0, unit: "sat", apiKey: "" };
1929
1929
  }
@@ -2445,9 +2445,10 @@ function isInsecureHttpUrl(url) {
2445
2445
  return url.startsWith("http://");
2446
2446
  }
2447
2447
  var ProviderManager = class _ProviderManager {
2448
- constructor(providerRegistry, store) {
2448
+ constructor(providerRegistry, store, logger) {
2449
2449
  this.providerRegistry = providerRegistry;
2450
2450
  this.instanceId = `pm_${Date.now().toString(36)}_${Math.random().toString(36).slice(2, 8)}`;
2451
+ this.logger = (logger ?? consoleLogger).child(`ProviderManager:${this.instanceId}`);
2451
2452
  if (store) {
2452
2453
  this.store = store;
2453
2454
  this.hydrateFromStore();
@@ -2464,6 +2465,7 @@ var ProviderManager = class _ProviderManager {
2464
2465
  store = null;
2465
2466
  /** Instance ID for debugging */
2466
2467
  instanceId;
2468
+ logger;
2467
2469
  /**
2468
2470
  * Hydrate in-memory state from persistent store
2469
2471
  */
@@ -2476,10 +2478,7 @@ var ProviderManager = class _ProviderManager {
2476
2478
  this.providersOnCoolDown = state.providersOnCooldown.filter(
2477
2479
  (entry) => now - entry.timestamp < _ProviderManager.COOLDOWN_DURATION_MS
2478
2480
  ).map((entry) => [entry.baseUrl, entry.timestamp]);
2479
- console.log(`[ProviderManager:${this.instanceId}] Hydrated from store:`);
2480
- console.log(` failedProviders: ${this.failedProviders.size}`);
2481
- console.log(` lastFailed: ${this.lastFailed.size}`);
2482
- console.log(` providersOnCooldown: ${this.providersOnCoolDown.length}`);
2481
+ this.logger.log(`Hydrated from store: failedProviders=${this.failedProviders.size} lastFailed=${this.lastFailed.size} providersOnCooldown=${this.providersOnCoolDown.length}`);
2483
2482
  }
2484
2483
  /**
2485
2484
  * Get instance ID for debugging
@@ -2499,9 +2498,7 @@ var ProviderManager = class _ProviderManager {
2499
2498
  const age = now - timestamp;
2500
2499
  const isExpired = age >= _ProviderManager.COOLDOWN_DURATION_MS;
2501
2500
  if (isExpired) {
2502
- console.log(
2503
- `[cleanupExpiredCooldowns:${this.instanceId}] Removing expired cooldown for ${url} (age: ${age}ms, cooldown: ${_ProviderManager.COOLDOWN_DURATION_MS}ms)`
2504
- );
2501
+ this.logger.log(`Removing expired cooldown for ${url} (age: ${age}ms)`);
2505
2502
  this.failedProviders.delete(url);
2506
2503
  if (this.store) {
2507
2504
  this.store.getState().removeFailedProvider(url);
@@ -2512,9 +2509,7 @@ var ProviderManager = class _ProviderManager {
2512
2509
  );
2513
2510
  const after = this.providersOnCoolDown.length;
2514
2511
  if (before !== after) {
2515
- console.log(
2516
- `[cleanupExpiredCooldowns:${this.instanceId}] Cleaned up ${before - after} expired cooldown(s), ${after} remaining`
2517
- );
2512
+ this.logger.log(`Cleaned up ${before - after} expired cooldown(s), ${after} remaining`);
2518
2513
  }
2519
2514
  }
2520
2515
  /**
@@ -2566,24 +2561,10 @@ var ProviderManager = class _ProviderManager {
2566
2561
  markFailed(baseUrl) {
2567
2562
  const now = Date.now();
2568
2563
  const lastFailure = this.lastFailed.get(baseUrl);
2569
- console.log(`[markFailed:${this.instanceId}] baseUrl: ${baseUrl}`);
2570
- console.log(
2571
- `[markFailed:${this.instanceId}] lastFailure from map: ${lastFailure}`
2572
- );
2573
- console.log(
2574
- `[markFailed:${this.instanceId}] current timestamp (now): ${now}`
2575
- );
2576
- console.log(
2577
- `[markFailed:${this.instanceId}] COOLDOWN_DURATION_MS: ${_ProviderManager.COOLDOWN_DURATION_MS}`
2578
- );
2564
+ this.logger.log(`markFailed: ${baseUrl} lastFailure=${lastFailure} now=${now}`);
2579
2565
  if (lastFailure !== void 0) {
2580
2566
  const timeSinceLastFailure = now - lastFailure;
2581
- console.log(
2582
- `[markFailed:${this.instanceId}] timeSinceLastFailure: ${timeSinceLastFailure}ms`
2583
- );
2584
- console.log(
2585
- `[markFailed:${this.instanceId}] isWithinCooldownWindow: ${timeSinceLastFailure < _ProviderManager.COOLDOWN_DURATION_MS}`
2586
- );
2567
+ this.logger.log(`markFailed: timeSinceLastFailure=${timeSinceLastFailure}ms withinCooldown=${timeSinceLastFailure < _ProviderManager.COOLDOWN_DURATION_MS}`);
2587
2568
  }
2588
2569
  this.lastFailed.set(baseUrl, now);
2589
2570
  this.failedProviders.add(baseUrl);
@@ -2591,38 +2572,23 @@ var ProviderManager = class _ProviderManager {
2591
2572
  this.store.getState().setLastFailedTimestamp(baseUrl, now);
2592
2573
  this.store.getState().addFailedProvider(baseUrl);
2593
2574
  }
2594
- console.log(
2595
- `[markFailed:${this.instanceId}] Updated lastFailed map for ${baseUrl} to ${now}`
2596
- );
2597
- console.log(
2598
- `[markFailed:${this.instanceId}] failedProviders set size: ${this.failedProviders.size}`
2599
- );
2575
+ this.logger.log(`markFailed: updated ${baseUrl} to ${now}, failedProviders=${this.failedProviders.size}`);
2600
2576
  if (lastFailure !== void 0 && now - lastFailure < _ProviderManager.COOLDOWN_DURATION_MS) {
2601
- console.log(
2602
- `[markFailed:${this.instanceId}] Second failure detected within cooldown window for ${baseUrl}`
2603
- );
2577
+ this.logger.log(`markFailed: second failure within cooldown window for ${baseUrl}`);
2604
2578
  if (!this.isOnCooldown(baseUrl)) {
2605
2579
  this.providersOnCoolDown.push([baseUrl, now]);
2606
2580
  if (this.store) {
2607
2581
  this.store.getState().addProviderOnCooldown(baseUrl, now);
2608
2582
  }
2609
- console.log(
2610
- `[markFailed:${this.instanceId}] Provider ${baseUrl} added to cooldown after second failure within 5 minutes`
2611
- );
2583
+ this.logger.log(`markFailed: ${baseUrl} added to cooldown`);
2612
2584
  } else {
2613
- console.log(
2614
- `[markFailed:${this.instanceId}] Provider ${baseUrl} is already on cooldown`
2615
- );
2585
+ this.logger.log(`markFailed: ${baseUrl} already on cooldown`);
2616
2586
  }
2617
2587
  } else {
2618
2588
  if (lastFailure === void 0) {
2619
- console.log(
2620
- `[markFailed:${this.instanceId}] First failure for ${baseUrl} - not adding to cooldown yet`
2621
- );
2589
+ this.logger.log(`markFailed: first failure for ${baseUrl}`);
2622
2590
  } else {
2623
- console.log(
2624
- `[markFailed:${this.instanceId}] Failure outside cooldown window for ${baseUrl} (timeSinceLastFailure: ${now - lastFailure}ms)`
2625
- );
2591
+ this.logger.log(`markFailed: failure outside cooldown window for ${baseUrl} (${now - lastFailure}ms ago)`);
2626
2592
  }
2627
2593
  }
2628
2594
  }
@@ -2679,25 +2645,12 @@ var ProviderManager = class _ProviderManager {
2679
2645
  const disabledProviders = new Set(
2680
2646
  this.providerRegistry.getDisabledProviders()
2681
2647
  );
2682
- console.log(
2683
- `[findNextBestProvider:${this.instanceId}] Starting search for model: ${modelId}`
2684
- );
2685
- console.log(
2686
- `[findNextBestProvider:${this.instanceId}] disabledProviders: ${[...disabledProviders]}`
2687
- );
2688
- console.log(
2689
- `[findNextBestProvider:${this.instanceId}] providersOnCooldown: ${this.providersOnCoolDown.map(([url]) => url)}`
2690
- );
2648
+ this.logger.log(`findNextBestProvider: model=${modelId} disabled=${[...disabledProviders].length} onCooldown=${this.providersOnCoolDown.length}`);
2691
2649
  const allProviders = this.providerRegistry.getAllProvidersModels();
2692
- console.log(
2693
- `[findNextBestProvider:${this.instanceId}] Total providers in registry: ${Object.keys(allProviders).length}`
2694
- );
2650
+ this.logger.log(`findNextBestProvider: total providers=${Object.keys(allProviders).length}`);
2695
2651
  const candidates = [];
2696
2652
  for (const [baseUrl, models] of Object.entries(allProviders)) {
2697
2653
  if (baseUrl === currentBaseUrl) {
2698
- console.log(
2699
- `[findNextBestProvider:${this.instanceId}] SKIP (current): ${baseUrl}`
2700
- );
2701
2654
  continue;
2702
2655
  }
2703
2656
  if (disabledProviders.has(baseUrl)) {
@@ -2723,7 +2676,7 @@ var ProviderManager = class _ProviderManager {
2723
2676
  return null;
2724
2677
  }
2725
2678
  } catch (error) {
2726
- console.error("Error finding next best provider:", error);
2679
+ this.logger.error("findNextBestProvider error:", error);
2727
2680
  return null;
2728
2681
  }
2729
2682
  }
@@ -2850,16 +2803,9 @@ var ProviderManager = class _ProviderManager {
2850
2803
  res.height
2851
2804
  );
2852
2805
  imageTokens += tokensFromImage;
2853
- console.log("IMAGE INPUT RESOLUTION", {
2854
- width: res.width,
2855
- height: res.height,
2856
- tokensFromImage
2857
- });
2806
+ this.logger.log(`IMAGE INPUT RESOLUTION width=${res.width} height=${res.height} tokens=${tokensFromImage}`);
2858
2807
  } else {
2859
- console.log(
2860
- "IMAGE INPUT RESOLUTION",
2861
- "unknown (unsupported format or parse failure)"
2862
- );
2808
+ this.logger.log("IMAGE INPUT RESOLUTION: unknown format");
2863
2809
  }
2864
2810
  }
2865
2811
  }
@@ -2892,7 +2838,7 @@ var ProviderManager = class _ProviderManager {
2892
2838
  const totalEstimatedCosts = (promptCosts + completionCost) * 1.05;
2893
2839
  return totalEstimatedCosts;
2894
2840
  } catch (e) {
2895
- console.error(e);
2841
+ this.logger.error("getRequiredSatsForModel error:", e);
2896
2842
  return 0;
2897
2843
  }
2898
2844
  }
@@ -3091,7 +3037,8 @@ var createSqliteDriver = (options = {}) => {
3091
3037
  }
3092
3038
  };
3093
3039
  };
3094
- async function createBunSqliteDriver(dbPath) {
3040
+ async function createBunSqliteDriver(dbPath, options) {
3041
+ const logger = (options?.logger ?? consoleLogger).child("BunSqliteDriver");
3095
3042
  const SQLite = (await import(
3096
3043
  /* webpackIgnore: true */
3097
3044
  'bun:sqlite'
@@ -3117,7 +3064,7 @@ async function createBunSqliteDriver(dbPath) {
3117
3064
  throw parseError;
3118
3065
  }
3119
3066
  } catch (error) {
3120
- console.error(`SQLite getItem failed for key "${key}":`, error);
3067
+ logger.error(`getItem failed for key "${key}":`, error);
3121
3068
  return defaultValue;
3122
3069
  }
3123
3070
  },
@@ -3127,14 +3074,14 @@ async function createBunSqliteDriver(dbPath) {
3127
3074
  "INSERT INTO sdk_storage (key, value) VALUES (?, ?) ON CONFLICT(key) DO UPDATE SET value = excluded.value"
3128
3075
  ).run(key, JSON.stringify(value));
3129
3076
  } catch (error) {
3130
- console.error(`SQLite setItem failed for key "${key}":`, error);
3077
+ logger.error(`setItem failed for key "${key}":`, error);
3131
3078
  }
3132
3079
  },
3133
3080
  async removeItem(key) {
3134
3081
  try {
3135
3082
  db.query("DELETE FROM sdk_storage WHERE key = ?").run(key);
3136
3083
  } catch (error) {
3137
- console.error(`SQLite removeItem failed for key "${key}":`, error);
3084
+ logger.error(`removeItem failed for key "${key}":`, error);
3138
3085
  }
3139
3086
  }
3140
3087
  };
@@ -4485,37 +4432,40 @@ var createStorageAdapterFromStore = (store) => ({
4485
4432
  store.getState().updateXcashuTokenTryCount(token, tryCount);
4486
4433
  }
4487
4434
  });
4488
- var createProviderRegistryFromStore = (store) => ({
4489
- getModelsForProvider: (baseUrl) => {
4490
- const normalized = normalizeBaseUrl5(baseUrl);
4491
- return store.getState().modelsFromAllProviders[normalized] || [];
4492
- },
4493
- getDisabledProviders: () => store.getState().disabledProviders,
4494
- getProviderMints: (baseUrl) => {
4495
- const normalized = normalizeBaseUrl5(baseUrl);
4496
- return store.getState().mintsFromAllProviders[normalized] || [];
4497
- },
4498
- getProviderInfo: async (baseUrl) => {
4499
- const normalized = normalizeBaseUrl5(baseUrl);
4500
- const cached = store.getState().infoFromAllProviders[normalized];
4501
- if (cached) return cached;
4502
- try {
4503
- const response = await fetch(`${normalized}v1/info`);
4504
- if (!response.ok) {
4505
- throw new Error(`Failed ${response.status}`);
4435
+ var createProviderRegistryFromStore = (store, logger) => {
4436
+ const log = (logger ?? consoleLogger).child("ProviderRegistry");
4437
+ return {
4438
+ getModelsForProvider: (baseUrl) => {
4439
+ const normalized = normalizeBaseUrl5(baseUrl);
4440
+ return store.getState().modelsFromAllProviders[normalized] || [];
4441
+ },
4442
+ getDisabledProviders: () => store.getState().disabledProviders,
4443
+ getProviderMints: (baseUrl) => {
4444
+ const normalized = normalizeBaseUrl5(baseUrl);
4445
+ return store.getState().mintsFromAllProviders[normalized] || [];
4446
+ },
4447
+ getProviderInfo: async (baseUrl) => {
4448
+ const normalized = normalizeBaseUrl5(baseUrl);
4449
+ const cached = store.getState().infoFromAllProviders[normalized];
4450
+ if (cached) return cached;
4451
+ try {
4452
+ const response = await fetch(`${normalized}v1/info`);
4453
+ if (!response.ok) {
4454
+ throw new Error(`Failed ${response.status}`);
4455
+ }
4456
+ const info = await response.json();
4457
+ const next = { ...store.getState().infoFromAllProviders };
4458
+ next[normalized] = info;
4459
+ store.getState().setInfoFromAllProviders(next);
4460
+ return info;
4461
+ } catch (error) {
4462
+ log.warn(`Failed to fetch provider info from ${normalized}:`, error);
4463
+ return null;
4506
4464
  }
4507
- const info = await response.json();
4508
- const next = { ...store.getState().infoFromAllProviders };
4509
- next[normalized] = info;
4510
- store.getState().setInfoFromAllProviders(next);
4511
- return info;
4512
- } catch (error) {
4513
- console.warn(`Failed to fetch provider info from ${normalized}:`, error);
4514
- return null;
4515
- }
4516
- },
4517
- getAllProvidersModels: () => store.getState().modelsFromAllProviders
4518
- });
4465
+ },
4466
+ getAllProvidersModels: () => store.getState().modelsFromAllProviders
4467
+ };
4468
+ };
4519
4469
 
4520
4470
  // storage/index.ts
4521
4471
  var isBrowser3 = () => {
@@ -4786,6 +4736,7 @@ var RoutstrClient = class {
4786
4736
  this.walletAdapter = walletAdapter;
4787
4737
  this.storageAdapter = storageAdapter;
4788
4738
  this.providerRegistry = providerRegistry;
4739
+ this.logger = (options.logger ?? consoleLogger).child("RoutstrClient");
4789
4740
  this.balanceManager = new BalanceManager(
4790
4741
  walletAdapter,
4791
4742
  storageAdapter,
@@ -4802,7 +4753,7 @@ var RoutstrClient = class {
4802
4753
  this.mode = mode;
4803
4754
  this.usageTrackingDriver = options.usageTrackingDriver;
4804
4755
  this.sdkStore = options.sdkStore;
4805
- this.providerManager = options.providerManager ?? new ProviderManager(providerRegistry, this.sdkStore);
4756
+ this.providerManager = options.providerManager ?? new ProviderManager(providerRegistry, this.sdkStore, this.logger);
4806
4757
  }
4807
4758
  cashuSpender;
4808
4759
  balanceManager;
@@ -4813,6 +4764,7 @@ var RoutstrClient = class {
4813
4764
  debugLevel = "WARN";
4814
4765
  usageTrackingDriver;
4815
4766
  sdkStore;
4767
+ logger;
4816
4768
  /**
4817
4769
  * Get the current client mode
4818
4770
  */
@@ -4834,13 +4786,13 @@ var RoutstrClient = class {
4834
4786
  if (levelPriority[level] >= levelPriority[this.debugLevel]) {
4835
4787
  switch (level) {
4836
4788
  case "DEBUG":
4837
- console.log(...args);
4789
+ this.logger.log(...args);
4838
4790
  break;
4839
4791
  case "WARN":
4840
- console.warn(...args);
4792
+ this.logger.warn(...args);
4841
4793
  break;
4842
4794
  case "ERROR":
4843
- console.error(...args);
4795
+ this.logger.error(...args);
4844
4796
  break;
4845
4797
  }
4846
4798
  }
@@ -5444,7 +5396,7 @@ var RoutstrClient = class {
5444
5396
  tryNextProvider = true;
5445
5397
  }
5446
5398
  }
5447
- if ((status === 401 || status === 403 || status === 413 || status === 400 || status === 429 || status === 500 || status === 502 || status === 503 || status === 504 || status === 521) && !tryNextProvider) {
5399
+ if ((status === 401 || status === 403 || status === 404 || status === 413 || status === 400 || status === 429 || status === 500 || status === 502 || status === 503 || status === 504 || status === 521) && !tryNextProvider) {
5448
5400
  this._log(
5449
5401
  "DEBUG",
5450
5402
  `[RoutstrClient] _handleErrorResponse: Status ${status} (${status === 429 ? "rate limited" : "auth/server error"}), attempting refund for ${baseUrl}, mode=${this.mode}`
@@ -5948,7 +5900,8 @@ async function resolveRouteRequestContext(options) {
5948
5900
  mode = "apikeys",
5949
5901
  usageTrackingDriver,
5950
5902
  sdkStore,
5951
- providerManager: providedProviderManager
5903
+ providerManager: providedProviderManager,
5904
+ logger
5952
5905
  } = options;
5953
5906
  let modelManager;
5954
5907
  let providers;
@@ -5960,7 +5913,8 @@ async function resolveRouteRequestContext(options) {
5960
5913
  }
5961
5914
  } else {
5962
5915
  modelManager = new ModelManager(discoveryAdapter, {
5963
- includeProviderUrls: forcedProvider ? [forcedProvider, ...includeProviderUrls] : includeProviderUrls
5916
+ includeProviderUrls: forcedProvider ? [forcedProvider, ...includeProviderUrls] : includeProviderUrls,
5917
+ logger
5964
5918
  });
5965
5919
  providers = await modelManager.bootstrapProviders(torMode);
5966
5920
  if (providers.length === 0) {
@@ -5968,7 +5922,7 @@ async function resolveRouteRequestContext(options) {
5968
5922
  }
5969
5923
  await modelManager.fetchModels(providers, forceRefresh);
5970
5924
  }
5971
- const providerManager = providedProviderManager ?? new ProviderManager(providerRegistry, sdkStore);
5925
+ const providerManager = providedProviderManager ?? new ProviderManager(providerRegistry, sdkStore, logger);
5972
5926
  let baseUrl;
5973
5927
  let selectedModel;
5974
5928
  if (forcedProvider) {
@@ -6013,7 +5967,7 @@ async function resolveRouteRequestContext(options) {
6013
5967
  providerRegistry,
6014
5968
  "min",
6015
5969
  mode,
6016
- { usageTrackingDriver, sdkStore, providerManager }
5970
+ { usageTrackingDriver, sdkStore, providerManager, logger }
6017
5971
  );
6018
5972
  if (debugLevel) {
6019
5973
  client.setDebugLevel(debugLevel);
@@ -6096,6 +6050,7 @@ exports.SDK_STORAGE_KEYS = SDK_STORAGE_KEYS;
6096
6050
  exports.StreamProcessor = StreamProcessor;
6097
6051
  exports.StreamingError = StreamingError;
6098
6052
  exports.TokenOperationError = TokenOperationError;
6053
+ exports.consoleLogger = consoleLogger;
6099
6054
  exports.createBunSqliteDriver = createBunSqliteDriver;
6100
6055
  exports.createBunSqliteUsageTrackingDriver = createBunSqliteUsageTrackingDriver;
6101
6056
  exports.createDiscoveryAdapterFromStore = createDiscoveryAdapterFromStore;
@@ -6121,6 +6076,7 @@ exports.inspectSSEWebStream = inspectSSEWebStream;
6121
6076
  exports.isOnionUrl = isOnionUrl;
6122
6077
  exports.isTorContext = isTorContext;
6123
6078
  exports.localStorageDriver = localStorageDriver;
6079
+ exports.noopLogger = noopLogger;
6124
6080
  exports.normalizeProviderUrl = normalizeProviderUrl;
6125
6081
  exports.routeRequests = routeRequests;
6126
6082
  exports.setDefaultUsageTrackingDriver = setDefaultUsageTrackingDriver;