@unicitylabs/sphere-sdk 0.14.11 → 0.15.0-dev.1

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 (46) hide show
  1. package/README.md +55 -17
  2. package/dist/connect/index.cjs +10 -17
  3. package/dist/connect/index.cjs.map +1 -1
  4. package/dist/connect/index.js +10 -17
  5. package/dist/connect/index.js.map +1 -1
  6. package/dist/core/index.cjs +69 -84
  7. package/dist/core/index.cjs.map +1 -1
  8. package/dist/core/index.d.cts +5 -14
  9. package/dist/core/index.d.ts +5 -14
  10. package/dist/core/index.js +69 -84
  11. package/dist/core/index.js.map +1 -1
  12. package/dist/impl/browser/connect/index.cjs +3 -3
  13. package/dist/impl/browser/connect/index.cjs.map +1 -1
  14. package/dist/impl/browser/connect/index.js +3 -3
  15. package/dist/impl/browser/connect/index.js.map +1 -1
  16. package/dist/impl/browser/index.cjs.map +1 -1
  17. package/dist/impl/browser/index.js.map +1 -1
  18. package/dist/impl/nodejs/connect/index.cjs +2 -2
  19. package/dist/impl/nodejs/connect/index.cjs.map +1 -1
  20. package/dist/impl/nodejs/connect/index.js +2 -2
  21. package/dist/impl/nodejs/connect/index.js.map +1 -1
  22. package/dist/impl/nodejs/index.cjs.map +1 -1
  23. package/dist/impl/nodejs/index.js.map +1 -1
  24. package/dist/impl/wallet-api-v2/index.cjs +92 -92
  25. package/dist/impl/wallet-api-v2/index.cjs.map +1 -1
  26. package/dist/impl/wallet-api-v2/index.js +92 -92
  27. package/dist/impl/wallet-api-v2/index.js.map +1 -1
  28. package/dist/index.cjs +69 -84
  29. package/dist/index.cjs.map +1 -1
  30. package/dist/index.d.cts +6 -11
  31. package/dist/index.d.ts +6 -11
  32. package/dist/index.js +69 -84
  33. package/dist/index.js.map +1 -1
  34. package/dist/modules/payments-v2/index.cjs +116 -174
  35. package/dist/modules/payments-v2/index.cjs.map +1 -1
  36. package/dist/modules/payments-v2/index.d.cts +3 -5
  37. package/dist/modules/payments-v2/index.d.ts +3 -5
  38. package/dist/modules/payments-v2/index.js +114 -173
  39. package/dist/modules/payments-v2/index.js.map +1 -1
  40. package/dist/token-engine/index.cjs +43 -57
  41. package/dist/token-engine/index.cjs.map +1 -1
  42. package/dist/token-engine/index.d.cts +0 -4
  43. package/dist/token-engine/index.d.ts +0 -4
  44. package/dist/token-engine/index.js +43 -57
  45. package/dist/token-engine/index.js.map +1 -1
  46. package/package.json +2 -2
@@ -442,6 +442,8 @@ interface StorageProvider extends BaseProvider {
442
442
  loadTrackedAddresses(): Promise<TrackedAddressEntry[]>;
443
443
  }
444
444
 
445
+ /** Never `storage.clear()` — that takes the keys too. */
446
+ declare function sweepSupersededState(storage: StorageProvider): Promise<void>;
445
447
  interface ScopedKV {
446
448
  get<T>(key: string): Promise<T | null>;
447
449
  set<T>(key: string, value: T): Promise<void>;
@@ -544,10 +546,6 @@ interface SphereValue {
544
546
  * `token`, so it is NOT stored — only cached at runtime on SphereToken.value.
545
547
  */
546
548
  interface TokenBlob {
547
- /** Blob format version (sphere storage migrations; independent of SDK CBOR). */
548
- readonly v: number;
549
- /** NetworkId.id the token belongs to (mainnet=1 / testnet=2 / local=3). */
550
- readonly network: number;
551
549
  /**
552
550
  * Genesis-stable token id — 64-char lowercase hex of the v2 `TokenId.bytes`
553
551
  * (same across every state of the token). Stored on the blob so dedup / listing
@@ -1179,4 +1177,4 @@ declare class PaymentsFacade implements PaymentsV2 {
1179
1177
  declare const HEARTBEAT_SEED_MS = 5000;
1180
1178
  declare const HEARTBEAT_CAP_MS = 120000;
1181
1179
 
1182
- export { ATTENTION_MINT_UNRESOLVED, ATTENTION_RECIPIENT_NETWORK_UNVERIFIED, ATTENTION_RESEED_REJECTED, type AckOutcome, type AckRequest, type ApplyDeltaResult, type CheckpointReseeder, type ConnectionStatus, type DeliverOptions, type DeliveryJournalEntry, type DeliveryPort, type DeliveryReceipt, type DeterministicMintCapable, type FacadeClient, type FacadeSession, HEARTBEAT_CAP_MS, HEARTBEAT_SEED_MS, type HistoryEntry, type HistoryPage, type IncomingDelivery, type IntentBackstopEntry, type IntentPayload, type InventoryAsset, type InventoryItem, type InventoryPage, MAX_RESELECT, type MintJournalEntry, type MintResult, type OpOutcome, type OutcomeClass, type PaymentRequestStatus, type PaymentRequestView, PaymentsFacade, type PaymentsFacadeDeps, type PaymentsRequestsApi, type PaymentsV2, type PaymentsV2Events, type PendingTransfer, type PlannedOp, type RecipientInfo, type RetryableAckError, STORE_KEYS, type ScopedKV, type SendRequest, type SettlingLink, type ShortfallEntry, type StoragePort, type StreamCursor, type StreamName, createScopedKV, isRetryableAckError, supportsDeterministicMint };
1180
+ export { ATTENTION_MINT_UNRESOLVED, ATTENTION_RECIPIENT_NETWORK_UNVERIFIED, ATTENTION_RESEED_REJECTED, type AckOutcome, type AckRequest, type ApplyDeltaResult, type CheckpointReseeder, type ConnectionStatus, type DeliverOptions, type DeliveryJournalEntry, type DeliveryPort, type DeliveryReceipt, type DeterministicMintCapable, type FacadeClient, type FacadeSession, HEARTBEAT_CAP_MS, HEARTBEAT_SEED_MS, type HistoryEntry, type HistoryPage, type IncomingDelivery, type IntentBackstopEntry, type IntentPayload, type InventoryAsset, type InventoryItem, type InventoryPage, MAX_RESELECT, type MintJournalEntry, type MintResult, type OpOutcome, type OutcomeClass, type PaymentRequestStatus, type PaymentRequestView, PaymentsFacade, type PaymentsFacadeDeps, type PaymentsRequestsApi, type PaymentsV2, type PaymentsV2Events, type PendingTransfer, type PlannedOp, type RecipientInfo, type RetryableAckError, STORE_KEYS, type ScopedKV, type SendRequest, type SettlingLink, type ShortfallEntry, type StoragePort, type StreamCursor, type StreamName, createScopedKV, isRetryableAckError, supportsDeterministicMint, sweepSupersededState };
@@ -442,6 +442,8 @@ interface StorageProvider extends BaseProvider {
442
442
  loadTrackedAddresses(): Promise<TrackedAddressEntry[]>;
443
443
  }
444
444
 
445
+ /** Never `storage.clear()` — that takes the keys too. */
446
+ declare function sweepSupersededState(storage: StorageProvider): Promise<void>;
445
447
  interface ScopedKV {
446
448
  get<T>(key: string): Promise<T | null>;
447
449
  set<T>(key: string, value: T): Promise<void>;
@@ -544,10 +546,6 @@ interface SphereValue {
544
546
  * `token`, so it is NOT stored — only cached at runtime on SphereToken.value.
545
547
  */
546
548
  interface TokenBlob {
547
- /** Blob format version (sphere storage migrations; independent of SDK CBOR). */
548
- readonly v: number;
549
- /** NetworkId.id the token belongs to (mainnet=1 / testnet=2 / local=3). */
550
- readonly network: number;
551
549
  /**
552
550
  * Genesis-stable token id — 64-char lowercase hex of the v2 `TokenId.bytes`
553
551
  * (same across every state of the token). Stored on the blob so dedup / listing
@@ -1179,4 +1177,4 @@ declare class PaymentsFacade implements PaymentsV2 {
1179
1177
  declare const HEARTBEAT_SEED_MS = 5000;
1180
1178
  declare const HEARTBEAT_CAP_MS = 120000;
1181
1179
 
1182
- export { ATTENTION_MINT_UNRESOLVED, ATTENTION_RECIPIENT_NETWORK_UNVERIFIED, ATTENTION_RESEED_REJECTED, type AckOutcome, type AckRequest, type ApplyDeltaResult, type CheckpointReseeder, type ConnectionStatus, type DeliverOptions, type DeliveryJournalEntry, type DeliveryPort, type DeliveryReceipt, type DeterministicMintCapable, type FacadeClient, type FacadeSession, HEARTBEAT_CAP_MS, HEARTBEAT_SEED_MS, type HistoryEntry, type HistoryPage, type IncomingDelivery, type IntentBackstopEntry, type IntentPayload, type InventoryAsset, type InventoryItem, type InventoryPage, MAX_RESELECT, type MintJournalEntry, type MintResult, type OpOutcome, type OutcomeClass, type PaymentRequestStatus, type PaymentRequestView, PaymentsFacade, type PaymentsFacadeDeps, type PaymentsRequestsApi, type PaymentsV2, type PaymentsV2Events, type PendingTransfer, type PlannedOp, type RecipientInfo, type RetryableAckError, STORE_KEYS, type ScopedKV, type SendRequest, type SettlingLink, type ShortfallEntry, type StoragePort, type StreamCursor, type StreamName, createScopedKV, isRetryableAckError, supportsDeterministicMint };
1180
+ export { ATTENTION_MINT_UNRESOLVED, ATTENTION_RECIPIENT_NETWORK_UNVERIFIED, ATTENTION_RESEED_REJECTED, type AckOutcome, type AckRequest, type ApplyDeltaResult, type CheckpointReseeder, type ConnectionStatus, type DeliverOptions, type DeliveryJournalEntry, type DeliveryPort, type DeliveryReceipt, type DeterministicMintCapable, type FacadeClient, type FacadeSession, HEARTBEAT_CAP_MS, HEARTBEAT_SEED_MS, type HistoryEntry, type HistoryPage, type IncomingDelivery, type IntentBackstopEntry, type IntentPayload, type InventoryAsset, type InventoryItem, type InventoryPage, MAX_RESELECT, type MintJournalEntry, type MintResult, type OpOutcome, type OutcomeClass, type PaymentRequestStatus, type PaymentRequestView, PaymentsFacade, type PaymentsFacadeDeps, type PaymentsRequestsApi, type PaymentsV2, type PaymentsV2Events, type PendingTransfer, type PlannedOp, type RecipientInfo, type RetryableAckError, STORE_KEYS, type ScopedKV, type SendRequest, type SettlingLink, type ShortfallEntry, type StoragePort, type StreamCursor, type StreamName, createScopedKV, isRetryableAckError, supportsDeterministicMint, sweepSupersededState };
@@ -3,9 +3,112 @@ function isRetryableAckError(err) {
3
3
  return err !== null && typeof err === "object" && err.retryable === true;
4
4
  }
5
5
 
6
+ // core/logger.ts
7
+ var LOGGER_KEY = "__sphere_sdk_logger__";
8
+ function getState() {
9
+ const g = globalThis;
10
+ if (!g[LOGGER_KEY]) {
11
+ g[LOGGER_KEY] = { debug: false, tags: {}, handler: null };
12
+ }
13
+ return g[LOGGER_KEY];
14
+ }
15
+ function isEnabled(tag) {
16
+ const state = getState();
17
+ if (tag in state.tags) return state.tags[tag];
18
+ return state.debug;
19
+ }
20
+ var logger = {
21
+ /**
22
+ * Configure the logger. Can be called multiple times (last write wins).
23
+ * Typically called by createBrowserProviders(), createNodeProviders(), or Sphere.init().
24
+ */
25
+ configure(config) {
26
+ const state = getState();
27
+ if (config.debug !== void 0) state.debug = config.debug;
28
+ if (config.handler !== void 0) state.handler = config.handler;
29
+ },
30
+ /**
31
+ * Enable/disable debug logging for a specific tag.
32
+ * Per-tag setting overrides the global debug flag.
33
+ *
34
+ * @example
35
+ * ```ts
36
+ * logger.setTagDebug('Nostr', true); // enable only Nostr logs
37
+ * logger.setTagDebug('Nostr', false); // disable Nostr logs even if global debug=true
38
+ * ```
39
+ */
40
+ setTagDebug(tag, enabled) {
41
+ getState().tags[tag] = enabled;
42
+ },
43
+ /**
44
+ * Clear per-tag override, falling back to global debug flag.
45
+ */
46
+ clearTagDebug(tag) {
47
+ delete getState().tags[tag];
48
+ },
49
+ /** Returns true if debug mode is enabled for the given tag (or globally). */
50
+ isDebugEnabled(tag) {
51
+ if (tag) return isEnabled(tag);
52
+ return getState().debug;
53
+ },
54
+ /**
55
+ * Debug-level log. Only shown when debug is enabled (globally or for this tag).
56
+ * Use for detailed operational information.
57
+ */
58
+ debug(tag, message, ...args) {
59
+ if (!isEnabled(tag)) return;
60
+ const state = getState();
61
+ if (state.handler) {
62
+ state.handler("debug", tag, message, ...args);
63
+ } else {
64
+ console.log(`[${tag}]`, message, ...args);
65
+ }
66
+ },
67
+ /**
68
+ * Warning-level log. ALWAYS shown regardless of debug flag.
69
+ * Use for important but non-critical issues (timeouts, retries, degraded state).
70
+ */
71
+ warn(tag, message, ...args) {
72
+ const state = getState();
73
+ if (state.handler) {
74
+ state.handler("warn", tag, message, ...args);
75
+ } else {
76
+ console.warn(`[${tag}]`, message, ...args);
77
+ }
78
+ },
79
+ /**
80
+ * Error-level log. ALWAYS shown regardless of debug flag.
81
+ * Use for critical failures that should never be silenced.
82
+ */
83
+ error(tag, message, ...args) {
84
+ const state = getState();
85
+ if (state.handler) {
86
+ state.handler("error", tag, message, ...args);
87
+ } else {
88
+ console.error(`[${tag}]`, message, ...args);
89
+ }
90
+ },
91
+ /** Reset all logger state (debug flag, tags, handler). Primarily for tests. */
92
+ reset() {
93
+ const g = globalThis;
94
+ delete g[LOGGER_KEY];
95
+ }
96
+ };
97
+
6
98
  // modules/payments-v2/stores.ts
99
+ var KV_PREFIX = "pv2g2:";
100
+ var SUPERSEDED_KV_PREFIXES = ["pv2:"];
101
+ async function sweepSupersededState(storage) {
102
+ for (const prefix of SUPERSEDED_KV_PREFIXES) {
103
+ try {
104
+ await storage.clear(prefix);
105
+ } catch (err) {
106
+ logger.warn("PaymentsV2", `could not clear superseded state under "${prefix}": ${String(err)}`);
107
+ }
108
+ }
109
+ }
7
110
  function createScopedKV(storage, network, chainPubkey) {
8
- const prefix = `pv2:${network}:${chainPubkey}:`;
111
+ const prefix = `${KV_PREFIX}${network}:${chainPubkey}:`;
9
112
  return {
10
113
  async get(key) {
11
114
  const raw = await storage.get(prefix + key);
@@ -454,69 +557,6 @@ function randomUUID() {
454
557
  return `${h[0]}${h[1]}${h[2]}${h[3]}-${h[4]}${h[5]}-${h[6]}${h[7]}-${h[8]}${h[9]}-${h[10]}${h[11]}${h[12]}${h[13]}${h[14]}${h[15]}`;
455
558
  }
456
559
 
457
- // token-engine/sdk.ts
458
- import { StateTransitionClient } from "@unicitylabs/state-transition-sdk/lib/StateTransitionClient.js";
459
- import { AggregatorClient } from "@unicitylabs/state-transition-sdk/lib/api/AggregatorClient.js";
460
- import { NetworkId } from "@unicitylabs/state-transition-sdk/lib/api/NetworkId.js";
461
- import { CertificationData } from "@unicitylabs/state-transition-sdk/lib/api/CertificationData.js";
462
- import { CertificationResponse, CertificationStatus } from "@unicitylabs/state-transition-sdk/lib/api/CertificationResponse.js";
463
- import { StateId } from "@unicitylabs/state-transition-sdk/lib/api/StateId.js";
464
- import { InclusionProof } from "@unicitylabs/state-transition-sdk/lib/api/InclusionProof.js";
465
- import { InclusionProofResponse } from "@unicitylabs/state-transition-sdk/lib/api/InclusionProofResponse.js";
466
- import { JsonRpcNetworkError } from "@unicitylabs/state-transition-sdk/lib/api/json-rpc/JsonRpcNetworkError.js";
467
- import { RootTrustBase } from "@unicitylabs/state-transition-sdk/lib/api/bft/RootTrustBase.js";
468
- import { waitInclusionProof } from "@unicitylabs/state-transition-sdk/lib/util/InclusionProofUtils.js";
469
- import { InclusionProofVerificationStatus } from "@unicitylabs/state-transition-sdk/lib/transaction/verification/rule/InclusionProofVerificationRule.js";
470
- import { Token } from "@unicitylabs/state-transition-sdk/lib/transaction/Token.js";
471
- import { MintTransaction } from "@unicitylabs/state-transition-sdk/lib/transaction/MintTransaction.js";
472
- import { TransferTransaction } from "@unicitylabs/state-transition-sdk/lib/transaction/TransferTransaction.js";
473
- import { CertifiedMintTransaction } from "@unicitylabs/state-transition-sdk/lib/transaction/CertifiedMintTransaction.js";
474
- import { CertifiedTransferTransaction } from "@unicitylabs/state-transition-sdk/lib/transaction/CertifiedTransferTransaction.js";
475
- import { TokenId } from "@unicitylabs/state-transition-sdk/lib/transaction/TokenId.js";
476
- import { TokenType } from "@unicitylabs/state-transition-sdk/lib/transaction/TokenType.js";
477
- import { TokenSalt } from "@unicitylabs/state-transition-sdk/lib/transaction/TokenSalt.js";
478
- import { StateMask } from "@unicitylabs/state-transition-sdk/lib/transaction/StateMask.js";
479
- import { MintJustificationVerifierService } from "@unicitylabs/state-transition-sdk/lib/transaction/verification/MintJustificationVerifierService.js";
480
- import { TokenIssuanceVerifierService } from "@unicitylabs/state-transition-sdk/lib/transaction/verification/TokenIssuanceVerifierService.js";
481
- import { VerificationContext } from "@unicitylabs/state-transition-sdk/lib/transaction/verification/VerificationContext.js";
482
- import { UnicityCertificateVerifier } from "@unicitylabs/state-transition-sdk/lib/api/bft/verification/UnicityCertificateVerifier.js";
483
- import { UnicitySealQuorumSignaturesVerificationRule } from "@unicitylabs/state-transition-sdk/lib/api/bft/verification/rule/UnicitySealQuorumSignaturesVerificationRule.js";
484
- import { VerifiedSealCache } from "@unicitylabs/state-transition-sdk/lib/api/bft/verification/VerifiedSealCache.js";
485
- import { Secp256k1SignatureVerifier } from "@unicitylabs/state-transition-sdk/lib/crypto/secp256k1/Secp256k1SignatureVerifier.js";
486
- import { WorkerTokenVerifier } from "@unicitylabs/state-transition-sdk/lib/transaction/verification/worker/WorkerTokenVerifier.js";
487
- import { EncodedPredicate } from "@unicitylabs/state-transition-sdk/lib/predicate/EncodedPredicate.js";
488
- import { SignaturePredicate } from "@unicitylabs/state-transition-sdk/lib/predicate/builtin/SignaturePredicate.js";
489
- import { SignaturePredicateUnlockScript } from "@unicitylabs/state-transition-sdk/lib/predicate/builtin/SignaturePredicateUnlockScript.js";
490
- import { BurnPredicate } from "@unicitylabs/state-transition-sdk/lib/predicate/builtin/BurnPredicate.js";
491
- import { PredicateVerifierService } from "@unicitylabs/state-transition-sdk/lib/predicate/verification/PredicateVerifierService.js";
492
- import { SigningService } from "@unicitylabs/state-transition-sdk/lib/crypto/secp256k1/SigningService.js";
493
- import { Signature } from "@unicitylabs/state-transition-sdk/lib/crypto/secp256k1/Signature.js";
494
- import { MintSigningService } from "@unicitylabs/state-transition-sdk/lib/crypto/MintSigningService.js";
495
- import { HashAlgorithm } from "@unicitylabs/state-transition-sdk/lib/crypto/hash/HashAlgorithm.js";
496
- import { DataHash } from "@unicitylabs/state-transition-sdk/lib/crypto/hash/DataHash.js";
497
- import { DataHasher } from "@unicitylabs/state-transition-sdk/lib/crypto/hash/DataHasher.js";
498
- import { DataHasherFactory } from "@unicitylabs/state-transition-sdk/lib/crypto/hash/DataHasherFactory.js";
499
- import { CborSerializer } from "@unicitylabs/state-transition-sdk/lib/serialization/cbor/CborSerializer.js";
500
- import { CborDeserializer } from "@unicitylabs/state-transition-sdk/lib/serialization/cbor/CborDeserializer.js";
501
- import { CborError } from "@unicitylabs/state-transition-sdk/lib/serialization/cbor/CborError.js";
502
- import { Asset } from "@unicitylabs/state-transition-sdk/lib/payment/asset/Asset.js";
503
- import { AssetId } from "@unicitylabs/state-transition-sdk/lib/payment/asset/AssetId.js";
504
- import { PaymentAssetCollection } from "@unicitylabs/state-transition-sdk/lib/payment/asset/PaymentAssetCollection.js";
505
- import { TokenSplit } from "@unicitylabs/state-transition-sdk/lib/payment/TokenSplit.js";
506
- import { SplitTokenRequest } from "@unicitylabs/state-transition-sdk/lib/payment/SplitTokenRequest.js";
507
- import { SplitToken } from "@unicitylabs/state-transition-sdk/lib/payment/SplitToken.js";
508
- import { SplitAllocationProof } from "@unicitylabs/state-transition-sdk/lib/payment/SplitAllocationProof.js";
509
- import { SplitMintJustification } from "@unicitylabs/state-transition-sdk/lib/payment/SplitMintJustification.js";
510
- import { SplitMintJustificationVerifier } from "@unicitylabs/state-transition-sdk/lib/payment/SplitMintJustificationVerifier.js";
511
- import { VerificationStatus } from "@unicitylabs/state-transition-sdk/lib/verification/VerificationStatus.js";
512
- import { VerificationResult } from "@unicitylabs/state-transition-sdk/lib/verification/VerificationResult.js";
513
- import { HexConverter } from "@unicitylabs/state-transition-sdk/lib/util/HexConverter.js";
514
- import { BigintConverter } from "@unicitylabs/state-transition-sdk/lib/util/BigintConverter.js";
515
- import { BitString } from "@unicitylabs/state-transition-sdk/lib/util/BitString.js";
516
-
517
- // token-engine/token-blob.ts
518
- var TOKEN_BLOB_VERSION = 1;
519
-
520
560
  // modules/payments-v2/async.ts
521
561
  var SingleFlight = class {
522
562
  flight = null;
@@ -1161,12 +1201,7 @@ var TransferMachine = class {
1161
1201
  let total = 0n;
1162
1202
  for (const outcome of committed) {
1163
1203
  if (outcome.recipientBlob === void 0) continue;
1164
- const token = await engine.decodeToken({
1165
- v: TOKEN_BLOB_VERSION,
1166
- network: 0,
1167
- tokenId: "",
1168
- token: outcome.recipientBlob
1169
- });
1204
+ const token = await engine.decodeToken({ tokenId: "", token: outcome.recipientBlob });
1170
1205
  total += engine.balanceOf(token, coinId);
1171
1206
  }
1172
1207
  return total.toString();
@@ -1282,8 +1317,9 @@ async function fetchSources(deps, jobs) {
1282
1317
  const engine = deps.engine();
1283
1318
  for (const [tokenId, bytes] of blobs) {
1284
1319
  try {
1285
- decoded.set(tokenId, await engine.decodeToken({ v: TOKEN_BLOB_VERSION, network: 0, tokenId, token: bytes }));
1286
- } catch {
1320
+ decoded.set(tokenId, await engine.decodeToken({ tokenId, token: bytes }));
1321
+ } catch (err) {
1322
+ logger.warn("PaymentsV2", `resume: source ${tokenId} did not decode \u2014 ${String(err)}`);
1287
1323
  }
1288
1324
  }
1289
1325
  return decoded;
@@ -3107,98 +3143,6 @@ var InventoryView = class {
3107
3143
  }
3108
3144
  };
3109
3145
 
3110
- // core/logger.ts
3111
- var LOGGER_KEY = "__sphere_sdk_logger__";
3112
- function getState() {
3113
- const g = globalThis;
3114
- if (!g[LOGGER_KEY]) {
3115
- g[LOGGER_KEY] = { debug: false, tags: {}, handler: null };
3116
- }
3117
- return g[LOGGER_KEY];
3118
- }
3119
- function isEnabled(tag) {
3120
- const state = getState();
3121
- if (tag in state.tags) return state.tags[tag];
3122
- return state.debug;
3123
- }
3124
- var logger = {
3125
- /**
3126
- * Configure the logger. Can be called multiple times (last write wins).
3127
- * Typically called by createBrowserProviders(), createNodeProviders(), or Sphere.init().
3128
- */
3129
- configure(config) {
3130
- const state = getState();
3131
- if (config.debug !== void 0) state.debug = config.debug;
3132
- if (config.handler !== void 0) state.handler = config.handler;
3133
- },
3134
- /**
3135
- * Enable/disable debug logging for a specific tag.
3136
- * Per-tag setting overrides the global debug flag.
3137
- *
3138
- * @example
3139
- * ```ts
3140
- * logger.setTagDebug('Nostr', true); // enable only Nostr logs
3141
- * logger.setTagDebug('Nostr', false); // disable Nostr logs even if global debug=true
3142
- * ```
3143
- */
3144
- setTagDebug(tag, enabled) {
3145
- getState().tags[tag] = enabled;
3146
- },
3147
- /**
3148
- * Clear per-tag override, falling back to global debug flag.
3149
- */
3150
- clearTagDebug(tag) {
3151
- delete getState().tags[tag];
3152
- },
3153
- /** Returns true if debug mode is enabled for the given tag (or globally). */
3154
- isDebugEnabled(tag) {
3155
- if (tag) return isEnabled(tag);
3156
- return getState().debug;
3157
- },
3158
- /**
3159
- * Debug-level log. Only shown when debug is enabled (globally or for this tag).
3160
- * Use for detailed operational information.
3161
- */
3162
- debug(tag, message, ...args) {
3163
- if (!isEnabled(tag)) return;
3164
- const state = getState();
3165
- if (state.handler) {
3166
- state.handler("debug", tag, message, ...args);
3167
- } else {
3168
- console.log(`[${tag}]`, message, ...args);
3169
- }
3170
- },
3171
- /**
3172
- * Warning-level log. ALWAYS shown regardless of debug flag.
3173
- * Use for important but non-critical issues (timeouts, retries, degraded state).
3174
- */
3175
- warn(tag, message, ...args) {
3176
- const state = getState();
3177
- if (state.handler) {
3178
- state.handler("warn", tag, message, ...args);
3179
- } else {
3180
- console.warn(`[${tag}]`, message, ...args);
3181
- }
3182
- },
3183
- /**
3184
- * Error-level log. ALWAYS shown regardless of debug flag.
3185
- * Use for critical failures that should never be silenced.
3186
- */
3187
- error(tag, message, ...args) {
3188
- const state = getState();
3189
- if (state.handler) {
3190
- state.handler("error", tag, message, ...args);
3191
- } else {
3192
- console.error(`[${tag}]`, message, ...args);
3193
- }
3194
- },
3195
- /** Reset all logger state (debug flag, tags, handler). Primarily for tests. */
3196
- reset() {
3197
- const g = globalThis;
3198
- delete g[LOGGER_KEY];
3199
- }
3200
- };
3201
-
3202
3146
  // modules/payments-v2/receive/Receive.ts
3203
3147
  var ACK_BATCH_SIZE = 200;
3204
3148
  var REFRESH_INTERVAL_MS = 2500;
@@ -3320,13 +3264,9 @@ async function screen(deps, engine, entry) {
3320
3264
  const blobBytes = await entry.fetchBlob();
3321
3265
  let token;
3322
3266
  try {
3323
- token = await engine.decodeToken({
3324
- v: TOKEN_BLOB_VERSION,
3325
- network: 0,
3326
- tokenId: "",
3327
- token: blobBytes
3328
- });
3329
- } catch {
3267
+ token = await engine.decodeToken({ tokenId: "", token: blobBytes });
3268
+ } catch (err) {
3269
+ logger.warn("PaymentsV2", `receive: undecodable blob rejected \u2014 ${String(err)}`);
3330
3270
  return { kind: "ack", ack: rejectAck(entry, "invalid") };
3331
3271
  }
3332
3272
  const verdict = await engine.verify(token);
@@ -4729,7 +4669,7 @@ var PaymentsFacade = class {
4729
4669
  if (bytes === void 0) {
4730
4670
  throw new SphereError(`Selected source ${tokenId} has no blob in storage`, "STORAGE_ERROR");
4731
4671
  }
4732
- const token = await engine.decodeToken({ v: TOKEN_BLOB_VERSION, network: 0, tokenId, token: bytes });
4672
+ const token = await engine.decodeToken({ tokenId, token: bytes });
4733
4673
  const keys = await engine.deliveryKeys(bytes);
4734
4674
  spentStates[tokenId] = { local: keys.stateHash, protocol: keys.stateHash };
4735
4675
  sources.set(tokenId, token);
@@ -4994,7 +4934,8 @@ export {
4994
4934
  STORE_KEYS,
4995
4935
  createScopedKV,
4996
4936
  isRetryableAckError,
4997
- supportsDeterministicMint
4937
+ supportsDeterministicMint,
4938
+ sweepSupersededState
4998
4939
  };
4999
4940
  /*! Bundled license information:
5000
4941