@arkade-os/sdk 0.4.9 → 0.4.11

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 (32) hide show
  1. package/dist/cjs/contracts/contractManager.js +173 -25
  2. package/dist/cjs/index.js +4 -3
  3. package/dist/cjs/providers/indexer.js +27 -4
  4. package/dist/cjs/utils/arkTransaction.js +17 -6
  5. package/dist/cjs/utils/syncCursors.js +136 -0
  6. package/dist/cjs/wallet/delegator.js +9 -6
  7. package/dist/cjs/wallet/serviceWorker/wallet-message-handler.js +63 -33
  8. package/dist/cjs/wallet/serviceWorker/wallet.js +5 -3
  9. package/dist/cjs/wallet/vtxo-manager.js +30 -9
  10. package/dist/cjs/wallet/wallet.js +180 -38
  11. package/dist/cjs/worker/errors.js +3 -4
  12. package/dist/esm/contracts/contractManager.js +173 -25
  13. package/dist/esm/index.js +2 -2
  14. package/dist/esm/providers/indexer.js +27 -4
  15. package/dist/esm/utils/arkTransaction.js +17 -6
  16. package/dist/esm/utils/syncCursors.js +125 -0
  17. package/dist/esm/wallet/delegator.js +9 -6
  18. package/dist/esm/wallet/serviceWorker/wallet-message-handler.js +63 -33
  19. package/dist/esm/wallet/serviceWorker/wallet.js +6 -4
  20. package/dist/esm/wallet/vtxo-manager.js +30 -9
  21. package/dist/esm/wallet/wallet.js +180 -38
  22. package/dist/esm/worker/errors.js +2 -3
  23. package/dist/types/contracts/contractManager.d.ts +28 -7
  24. package/dist/types/contracts/index.d.ts +1 -1
  25. package/dist/types/index.d.ts +2 -2
  26. package/dist/types/providers/indexer.d.ts +16 -14
  27. package/dist/types/utils/syncCursors.d.ts +58 -0
  28. package/dist/types/wallet/serviceWorker/wallet-message-handler.d.ts +14 -2
  29. package/dist/types/wallet/vtxo-manager.d.ts +3 -2
  30. package/dist/types/wallet/wallet.d.ts +14 -0
  31. package/dist/types/worker/errors.d.ts +1 -0
  32. package/package.json +2 -2
@@ -43,6 +43,11 @@ import { ContractRepository } from "../repositories";
43
43
  * manager.dispose();
44
44
  * ```
45
45
  */
46
+ export type RefreshVtxosOptions = {
47
+ scripts?: string[];
48
+ after?: number;
49
+ before?: number;
50
+ };
46
51
  export interface IContractManager extends Disposable {
47
52
  /**
48
53
  * Create and register a new contract.
@@ -103,10 +108,12 @@ export interface IContractManager extends Disposable {
103
108
  */
104
109
  onContractEvent(callback: ContractEventCallback): () => void;
105
110
  /**
106
- * Force a full VTXO refresh from the indexer for all contracts.
107
- * Populates the wallet repository with complete VTXO history.
111
+ * Force a VTXO refresh from the indexer.
112
+ *
113
+ * Without options, refreshes all contracts from scratch.
114
+ * With options, narrows the refresh to specific scripts and/or a time window.
108
115
  */
109
- refreshVtxos(): Promise<void>;
116
+ refreshVtxos(opts?: RefreshVtxosOptions): Promise<void>;
110
117
  /**
111
118
  * Whether the underlying watcher is currently active.
112
119
  */
@@ -240,7 +247,7 @@ export declare class ContractManager implements IContractManager {
240
247
  * ```
241
248
  */
242
249
  getContracts(filter?: GetContractsFilter): Promise<Contract[]>;
243
- getContractsWithVtxos(filter?: GetContractsFilter): Promise<ContractWithVtxos[]>;
250
+ getContractsWithVtxos(filter?: GetContractsFilter, pageSize?: number): Promise<ContractWithVtxos[]>;
244
251
  private buildContractsDbFilter;
245
252
  /**
246
253
  * Update a contract.
@@ -298,10 +305,12 @@ export declare class ContractManager implements IContractManager {
298
305
  */
299
306
  onContractEvent(callback: ContractEventCallback): () => void;
300
307
  /**
301
- * Force a full VTXO refresh from the indexer for all contracts.
302
- * Populates the wallet repository with complete VTXO history.
308
+ * Force a VTXO refresh from the indexer.
309
+ *
310
+ * Without options, clears all sync cursors and re-fetches every contract.
311
+ * With options, narrows the refresh to specific scripts and/or a time window.
303
312
  */
304
- refreshVtxos(): Promise<void>;
313
+ refreshVtxos(opts?: RefreshVtxosOptions): Promise<void>;
305
314
  /**
306
315
  * Check if currently watching.
307
316
  */
@@ -315,6 +324,18 @@ export declare class ContractManager implements IContractManager {
315
324
  */
316
325
  private handleContractEvent;
317
326
  private getVtxosForContracts;
327
+ /**
328
+ * Incrementally sync VTXOs for the given contracts.
329
+ * Uses per-script cursors to fetch only what changed since the last sync.
330
+ * Scripts without a cursor are bootstrapped with a full fetch.
331
+ */
332
+ private deltaSyncContracts;
333
+ /**
334
+ * Fetch all pending (not-yet-finalized) VTXOs and upsert them into the
335
+ * repository. This catches VTXOs whose state changed outside the delta
336
+ * window (e.g. a spend that hasn't settled yet).
337
+ */
338
+ private reconcilePendingFrontier;
318
339
  private fetchContractVxosFromIndexer;
319
340
  private fetchContractVtxosBulk;
320
341
  private fetchContractVtxosPaginated;
@@ -11,4 +11,4 @@ export type { ParsedArkContract } from "./arkcontract";
11
11
  export { ContractWatcher } from "./contractWatcher";
12
12
  export type { ContractWatcherConfig } from "./contractWatcher";
13
13
  export { ContractManager } from "./contractManager";
14
- export type { ContractManagerConfig, CreateContractParams, } from "./contractManager";
14
+ export type { ContractManagerConfig, CreateContractParams, RefreshVtxosOptions, } from "./contractManager";
@@ -48,6 +48,6 @@ import type { Contract, ContractVtxo, ContractState, ContractEvent, ContractEven
48
48
  import { IContractManager } from "./contracts/contractManager";
49
49
  import { closeDatabase, openDatabase } from "./repositories/indexedDB/manager";
50
50
  import { WalletMessageHandler, WalletNotInitializedError, ReadonlyWalletError, DelegatorNotConfiguredError } from "./wallet/serviceWorker/wallet-message-handler";
51
- import { MessageBusNotInitializedError, ServiceWorkerTimeoutError } from "./worker/errors";
52
- export { Wallet, ReadonlyWallet, SingleKey, ReadonlySingleKey, SeedIdentity, MnemonicIdentity, ReadonlyDescriptorIdentity, OnchainWallet, Ramps, VtxoManager, DelegatorManagerImpl, RestDelegatorProvider, ESPLORA_URL, EsploraProvider, RestArkProvider, RestIndexerProvider, ArkAddress, DefaultVtxo, DelegateVtxo, VtxoScript, VHTLC, TxType, IndexerTxType, ChainTxType, SettlementEventType, setupServiceWorker, MessageBus, WalletMessageHandler, WalletNotInitializedError, ReadonlyWalletError, DelegatorNotConfiguredError, MessageBusNotInitializedError, ServiceWorkerTimeoutError, ServiceWorkerWallet, ServiceWorkerReadonlyWallet, decodeTapscript, MultisigTapscript, CSVMultisigTapscript, ConditionCSVMultisigTapscript, ConditionMultisigTapscript, CLTVMultisigTapscript, TapTreeCoder, ArkPsbtFieldKey, ArkPsbtFieldKeyType, setArkPsbtField, getArkPsbtFields, CosignerPublicKey, VtxoTreeExpiry, VtxoTaprootTree, ConditionWitness, buildOffchainTx, verifyTapscriptSignatures, waitForIncomingFunds, hasBoardingTxExpired, combineTapscriptSigs, isVtxoExpiringSoon, isValidArkAddress, ArkNote, networks, closeDatabase, openDatabase, IndexedDBWalletRepository, IndexedDBContractRepository, InMemoryWalletRepository, InMemoryContractRepository, MIGRATION_KEY, migrateWalletRepository, requiresMigration, getMigrationStatus, rollbackMigration, WalletRepositoryImpl, ContractRepositoryImpl, Intent, BIP322, TxTree, P2A, Unroll, Transaction, ArkError, maybeArkError, Batch, validateVtxoTxGraph, validateConnectorsTxGraph, buildForfeitTx, isRecoverable, isSpendable, isSubdust, isExpired, getSequence, ContractManager, ContractWatcher, contractHandlers, DefaultContractHandler, DelegateContractHandler, VHTLCContractHandler, encodeArkContract, decodeArkContract, contractFromArkContract, contractFromArkContractWithAddress, isArkContract, };
51
+ import { MESSAGE_BUS_NOT_INITIALIZED, MessageBusNotInitializedError, ServiceWorkerTimeoutError } from "./worker/errors";
52
+ export { Wallet, ReadonlyWallet, SingleKey, ReadonlySingleKey, SeedIdentity, MnemonicIdentity, ReadonlyDescriptorIdentity, OnchainWallet, Ramps, VtxoManager, DelegatorManagerImpl, RestDelegatorProvider, ESPLORA_URL, EsploraProvider, RestArkProvider, RestIndexerProvider, ArkAddress, DefaultVtxo, DelegateVtxo, VtxoScript, VHTLC, TxType, IndexerTxType, ChainTxType, SettlementEventType, setupServiceWorker, MessageBus, WalletMessageHandler, WalletNotInitializedError, ReadonlyWalletError, DelegatorNotConfiguredError, MESSAGE_BUS_NOT_INITIALIZED, MessageBusNotInitializedError, ServiceWorkerTimeoutError, ServiceWorkerWallet, ServiceWorkerReadonlyWallet, decodeTapscript, MultisigTapscript, CSVMultisigTapscript, ConditionCSVMultisigTapscript, ConditionMultisigTapscript, CLTVMultisigTapscript, TapTreeCoder, ArkPsbtFieldKey, ArkPsbtFieldKeyType, setArkPsbtField, getArkPsbtFields, CosignerPublicKey, VtxoTreeExpiry, VtxoTaprootTree, ConditionWitness, buildOffchainTx, verifyTapscriptSignatures, waitForIncomingFunds, hasBoardingTxExpired, combineTapscriptSigs, isVtxoExpiringSoon, isValidArkAddress, ArkNote, networks, closeDatabase, openDatabase, IndexedDBWalletRepository, IndexedDBContractRepository, InMemoryWalletRepository, InMemoryContractRepository, MIGRATION_KEY, migrateWalletRepository, requiresMigration, getMigrationStatus, rollbackMigration, WalletRepositoryImpl, ContractRepositoryImpl, Intent, BIP322, TxTree, P2A, Unroll, Transaction, ArkError, maybeArkError, Batch, validateVtxoTxGraph, validateConnectorsTxGraph, buildForfeitTx, isRecoverable, isSpendable, isSubdust, isExpired, getSequence, ContractManager, ContractWatcher, contractHandlers, DefaultContractHandler, DelegateContractHandler, VHTLCContractHandler, encodeArkContract, decodeArkContract, contractFromArkContract, contractFromArkContractWithAddress, isArkContract, };
53
53
  export type { Identity, ReadonlyIdentity, IWallet, IReadonlyWallet, BaseWalletConfig, WalletConfig, ReadonlyWalletConfig, ProviderClass, ArkTransaction, Coin, ExtendedCoin, ExtendedVirtualCoin, WalletBalance, SendBitcoinParams, SettleParams, Status, VirtualStatus, Outpoint, VirtualCoin, TxKey, TapscriptType, ArkTxInput, OffchainTx, TapLeaves, IncomingFunds, SeedIdentityOptions, MnemonicOptions, NetworkOptions, DescriptorOptions, IndexerProvider, PageResponse, BatchInfo, ChainTx, CommitmentTx, TxHistoryRecord, Vtxo, VtxoChain, Tx, OnchainProvider, ArkProvider, SettlementEvent, FeeInfo, ArkInfo, SignedIntent, Output, TxNotification, ExplorerTransaction, BatchFinalizationEvent, BatchFinalizedEvent, BatchFailedEvent, TreeSigningStartedEvent, TreeNoncesEvent, BatchStartedEvent, TreeTxEvent, TreeSignatureEvent, ScheduledSession, PaginationOptions, SubscriptionResponse, SubscriptionHeartbeat, SubscriptionEvent, Network, NetworkName, ArkTapscript, RelativeTimelock, EncodedVtxoScript, TapLeafScript, SignerSession, TreeNonces, TreePartialSigs, GetVtxosFilter, SettlementConfig, IVtxoManager, Asset, Recipient, IssuanceParams, IssuanceResult, ReissuanceParams, BurnParams, AssetDetails, AssetMetadata, KnownMetadata, Nonces, PartialSig, ArkPsbtFieldCoder, TxTreeNode, AnchorBumper, StorageConfig, Contract, ContractVtxo, ContractState, ContractEvent, ContractEventCallback, ContractBalance, ContractWithVtxos, ContractHandler, IContractManager, PathSelection, PathContext, ContractManagerConfig, CreateContractParams, ContractWatcherConfig, ParsedArkContract, DefaultContractParams, DelegateContractParams, VHTLCContractParams, MessageHandler, RequestEnvelope, ResponseEnvelope, IDelegatorManager, DelegatorProvider, DelegateInfo, DelegateOptions, WalletRepository, ContractRepository, MigrationStatus, };
@@ -101,6 +101,20 @@ export interface SubscriptionHeartbeat {
101
101
  export interface SubscriptionEvent extends SubscriptionResponse {
102
102
  type: "event";
103
103
  }
104
+ export type GetVtxosOptions = PaginationOptions & {
105
+ spendableOnly?: boolean;
106
+ spentOnly?: boolean;
107
+ recoverableOnly?: boolean;
108
+ pendingOnly?: boolean;
109
+ after?: number;
110
+ before?: number;
111
+ } & ({
112
+ scripts: string[];
113
+ outpoints?: never;
114
+ } | {
115
+ outpoints: Outpoint[];
116
+ scripts?: never;
117
+ });
104
118
  export interface IndexerProvider {
105
119
  getVtxoTree(batchOutpoint: Outpoint, opts?: PaginationOptions): Promise<{
106
120
  vtxoTree: Tx[];
@@ -128,13 +142,7 @@ export interface IndexerProvider {
128
142
  page?: PageResponse;
129
143
  }>;
130
144
  getVtxoChain(vtxoOutpoint: Outpoint, opts?: PaginationOptions): Promise<VtxoChain>;
131
- getVtxos(opts?: PaginationOptions & {
132
- scripts?: string[];
133
- outpoints?: Outpoint[];
134
- spendableOnly?: boolean;
135
- spentOnly?: boolean;
136
- recoverableOnly?: boolean;
137
- }): Promise<{
145
+ getVtxos(opts?: GetVtxosOptions): Promise<{
138
146
  vtxos: VirtualCoin[];
139
147
  page?: PageResponse;
140
148
  }>;
@@ -180,13 +188,7 @@ export declare class RestIndexerProvider implements IndexerProvider {
180
188
  page?: PageResponse;
181
189
  }>;
182
190
  getVtxoChain(vtxoOutpoint: Outpoint, opts?: PaginationOptions): Promise<VtxoChain>;
183
- getVtxos(opts?: PaginationOptions & {
184
- scripts?: string[];
185
- outpoints?: Outpoint[];
186
- spendableOnly?: boolean;
187
- spentOnly?: boolean;
188
- recoverableOnly?: boolean;
189
- }): Promise<{
191
+ getVtxos(opts?: GetVtxosOptions): Promise<{
190
192
  vtxos: VirtualCoin[];
191
193
  page?: PageResponse;
192
194
  }>;
@@ -0,0 +1,58 @@
1
+ import { WalletRepository, WalletState } from "../repositories/walletRepository";
2
+ /** Lag behind real-time to avoid racing with indexer writes. */
3
+ export declare const SAFETY_LAG_MS = 30000;
4
+ /** Overlap window so boundary VTXOs are never missed. */
5
+ export declare const OVERLAP_MS = 60000;
6
+ type SyncCursors = Record<string, number>;
7
+ /**
8
+ * Atomically read, mutate, and persist wallet state.
9
+ * All callers that modify wallet state should go through this helper
10
+ * to avoid lost-update races between interleaved async operations.
11
+ */
12
+ export declare function updateWalletState(repo: WalletRepository, updater: (state: WalletState) => WalletState): Promise<void>;
13
+ /**
14
+ * Read the high-water mark for a single script.
15
+ * Returns `undefined` when the script has never been synced (bootstrap case).
16
+ */
17
+ export declare function getSyncCursor(repo: WalletRepository, script: string): Promise<number | undefined>;
18
+ /**
19
+ * Read cursors for every previously-synced script.
20
+ */
21
+ export declare function getAllSyncCursors(repo: WalletRepository): Promise<SyncCursors>;
22
+ /**
23
+ * Advance the cursor for one script after a successful delta sync.
24
+ * `cursor` should be the `before` cutoff used in the request.
25
+ */
26
+ export declare function advanceSyncCursor(repo: WalletRepository, script: string, cursor: number): Promise<void>;
27
+ /**
28
+ * Advance cursors for multiple scripts in a single write.
29
+ */
30
+ export declare function advanceSyncCursors(repo: WalletRepository, updates: Record<string, number>): Promise<void>;
31
+ /**
32
+ * Remove sync cursors, forcing a full re-bootstrap on next sync.
33
+ * When `scripts` is provided, only those cursors are cleared.
34
+ */
35
+ export declare function clearSyncCursors(repo: WalletRepository, scripts?: string[]): Promise<void>;
36
+ /**
37
+ * Compute the `after` lower-bound for a delta sync query.
38
+ * Returns `undefined` when the script has no cursor (bootstrap needed).
39
+ *
40
+ * No upper bound (`before`) is applied to the query so that freshly
41
+ * created VTXOs are never excluded. The safety lag is applied only
42
+ * when advancing the cursor (see {@link cursorCutoff}).
43
+ */
44
+ export declare function computeSyncWindow(cursor: number | undefined): {
45
+ after: number;
46
+ } | undefined;
47
+ /**
48
+ * The safe high-water mark for cursor advancement.
49
+ * Lags behind real-time by {@link SAFETY_LAG_MS} so that VTXOs still
50
+ * being indexed are re-queried on the next sync.
51
+ *
52
+ * When `requestStartedAt` is provided the cutoff is frozen to the
53
+ * request start rather than wall-clock at commit time, preventing
54
+ * long-running paginated fetches from advancing the cursor past the
55
+ * data they actually observed.
56
+ */
57
+ export declare function cursorCutoff(requestStartedAt?: number): number;
58
+ export {};
@@ -230,6 +230,11 @@ export type ResponseIsContractManagerWatching = ResponseEnvelope & {
230
230
  };
231
231
  export type RequestRefreshVtxos = RequestEnvelope & {
232
232
  type: "REFRESH_VTXOS";
233
+ payload?: {
234
+ scripts?: string[];
235
+ after?: number;
236
+ before?: number;
237
+ };
233
238
  };
234
239
  export type ResponseRefreshVtxos = ResponseEnvelope & {
235
240
  type: "REFRESH_VTXOS_SUCCESS";
@@ -474,8 +479,15 @@ export declare class WalletMessageHandler implements MessageHandler<WalletUpdate
474
479
  private getSpendableVtxos;
475
480
  private onWalletInitialized;
476
481
  /**
477
- * Force a full VTXO refresh from the indexer, then re-run bootstrap.
478
- * Used by RELOAD_WALLET to ensure fresh data.
482
+ * Refresh VTXOs, boarding UTXOs, and transaction history from cache.
483
+ * Shared by onWalletInitialized (full bootstrap) and reloadWallet
484
+ * (post-refresh), avoiding duplicate subscriptions and VtxoManager restarts.
485
+ */
486
+ private refreshCachedData;
487
+ /**
488
+ * Force a full VTXO refresh from the indexer, then refresh cached data.
489
+ * Used by RELOAD_WALLET to ensure fresh data without re-subscribing
490
+ * to incoming funds or restarting the VtxoManager.
479
491
  */
480
492
  private reloadWallet;
481
493
  private handleSettle;
@@ -171,6 +171,7 @@ export declare class VtxoManager implements AsyncDisposable, IVtxoManager {
171
171
  private knownBoardingUtxos;
172
172
  private sweptBoardingUtxos;
173
173
  private pollInProgress;
174
+ private pollDone?;
174
175
  private disposed;
175
176
  private consecutivePollFailures;
176
177
  private startupPollTimeoutId?;
@@ -296,7 +297,7 @@ export declare class VtxoManager implements AsyncDisposable, IVtxoManager {
296
297
  * }
297
298
  * ```
298
299
  */
299
- getExpiredBoardingUtxos(): Promise<ExtendedCoin[]>;
300
+ getExpiredBoardingUtxos(prefetchedUtxos?: ExtendedCoin[]): Promise<ExtendedCoin[]>;
300
301
  /**
301
302
  * Sweep expired boarding UTXOs back to a fresh boarding address via
302
303
  * the unilateral exit path (on-chain self-spend).
@@ -328,7 +329,7 @@ export declare class VtxoManager implements AsyncDisposable, IVtxoManager {
328
329
  * }
329
330
  * ```
330
331
  */
331
- sweepExpiredBoardingUtxos(): Promise<string>;
332
+ sweepExpiredBoardingUtxos(prefetchedUtxos?: ExtendedCoin[]): Promise<string>;
332
333
  /** Asserts sweep capability and returns the typed wallet. */
333
334
  private getSweepWallet;
334
335
  /** Decodes the boarding tapscript exit path to extract the CSV timelock. */
@@ -76,6 +76,17 @@ export declare class ReadonlyWallet implements IReadonlyWallet {
76
76
  getBalance(): Promise<WalletBalance>;
77
77
  getVtxos(filter?: GetVtxosFilter): Promise<ExtendedVirtualCoin[]>;
78
78
  getTransactionHistory(): Promise<ArkTransaction[]>;
79
+ /**
80
+ * Delta-sync wallet VTXOs: fetch only changed VTXOs since the last
81
+ * cursor, or do a full bootstrap when no cursor exists. Upserts
82
+ * the result into the cache and advances the sync cursors.
83
+ */
84
+ private syncVtxos;
85
+ /**
86
+ * Clear all VTXO sync cursors, forcing a full re-bootstrap on next sync.
87
+ * Useful for recovery after indexer reprocessing or debugging.
88
+ */
89
+ clearSyncCursors(): Promise<void>;
79
90
  getBoardingTxs(): Promise<{
80
91
  boardingTxs: ArkTransaction[];
81
92
  commitmentsToIgnore: Set<string>;
@@ -233,6 +244,7 @@ export declare class Wallet extends ReadonlyWallet implements IWallet {
233
244
  makeGetPendingTxIntentSignature(coins: ExtendedVirtualCoin[]): Promise<SignedIntent<Intent.GetPendingTxMessage>>;
234
245
  /**
235
246
  * Finalizes pending transactions by retrieving them from the server and finalizing each one.
247
+ * Skips the server check entirely when no send was interrupted (no pending tx flag set).
236
248
  * @param vtxos - Optional list of VTXOs to use instead of retrieving them from the server
237
249
  * @returns Array of transaction IDs that were finalized
238
250
  */
@@ -240,6 +252,8 @@ export declare class Wallet extends ReadonlyWallet implements IWallet {
240
252
  finalized: string[];
241
253
  pending: string[];
242
254
  }>;
255
+ private hasPendingTxFlag;
256
+ private setPendingTxFlag;
243
257
  /**
244
258
  * Send BTC and/or assets to one or more recipients.
245
259
  *
@@ -1,3 +1,4 @@
1
+ export declare const MESSAGE_BUS_NOT_INITIALIZED = "MessageBus not initialized";
1
2
  export declare class MessageBusNotInitializedError extends Error {
2
3
  constructor();
3
4
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@arkade-os/sdk",
3
- "version": "0.4.9",
3
+ "version": "0.4.11",
4
4
  "description": "Bitcoin wallet SDK with Taproot and Ark integration",
5
5
  "type": "module",
6
6
  "main": "./dist/cjs/index.js",
@@ -80,7 +80,7 @@
80
80
  "registry": "https://registry.npmjs.org/"
81
81
  },
82
82
  "dependencies": {
83
- "@kukks/bitcoin-descriptors": "3.1.0",
83
+ "@kukks/bitcoin-descriptors": "3.2.3",
84
84
  "@marcbachmann/cel-js": "7.3.1",
85
85
  "@noble/curves": "2.0.0",
86
86
  "@noble/secp256k1": "3.0.0",