@arkade-os/sdk 0.3.0-alpha.7 → 0.3.0

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 (109) hide show
  1. package/README.md +99 -14
  2. package/dist/cjs/adapters/expo.js +8 -0
  3. package/dist/cjs/arknote/index.js +3 -3
  4. package/dist/cjs/forfeit.js +2 -2
  5. package/dist/cjs/identity/singleKey.js +8 -8
  6. package/dist/cjs/index.js +14 -5
  7. package/dist/cjs/{bip322 → intent}/index.js +38 -61
  8. package/dist/cjs/musig2/index.js +2 -1
  9. package/dist/cjs/musig2/nonces.js +4 -0
  10. package/dist/cjs/providers/ark.js +76 -45
  11. package/dist/cjs/providers/errors.js +59 -0
  12. package/dist/cjs/providers/expoArk.js +82 -0
  13. package/dist/cjs/providers/expoIndexer.js +105 -0
  14. package/dist/cjs/providers/expoUtils.js +124 -0
  15. package/dist/cjs/providers/indexer.js +3 -1
  16. package/dist/cjs/providers/onchain.js +19 -20
  17. package/dist/cjs/repositories/walletRepository.js +64 -28
  18. package/dist/cjs/script/base.js +15 -7
  19. package/dist/cjs/script/tapscript.js +20 -21
  20. package/dist/cjs/script/vhtlc.js +2 -2
  21. package/dist/cjs/tree/signingSession.js +44 -11
  22. package/dist/cjs/tree/txTree.js +3 -4
  23. package/dist/cjs/tree/validation.js +2 -3
  24. package/dist/cjs/utils/arkTransaction.js +118 -15
  25. package/dist/cjs/utils/transaction.js +28 -0
  26. package/dist/cjs/utils/unknownFields.js +7 -7
  27. package/dist/cjs/wallet/index.js +1 -1
  28. package/dist/cjs/wallet/onchain.js +6 -7
  29. package/dist/cjs/wallet/serviceWorker/response.js +32 -0
  30. package/dist/cjs/wallet/serviceWorker/utils.js +2 -9
  31. package/dist/cjs/wallet/serviceWorker/wallet.js +7 -8
  32. package/dist/cjs/wallet/serviceWorker/worker.js +48 -32
  33. package/dist/cjs/wallet/unroll.js +7 -9
  34. package/dist/cjs/wallet/utils.js +20 -0
  35. package/dist/cjs/wallet/vtxo-manager.js +323 -0
  36. package/dist/cjs/wallet/wallet.js +165 -174
  37. package/dist/esm/adapters/expo.js +3 -0
  38. package/dist/esm/arknote/index.js +2 -2
  39. package/dist/esm/forfeit.js +1 -1
  40. package/dist/esm/identity/singleKey.js +9 -9
  41. package/dist/esm/index.js +14 -10
  42. package/dist/esm/{bip322 → intent}/index.js +32 -54
  43. package/dist/esm/musig2/index.js +1 -1
  44. package/dist/esm/musig2/nonces.js +3 -0
  45. package/dist/esm/providers/ark.js +76 -45
  46. package/dist/esm/providers/errors.js +54 -0
  47. package/dist/esm/providers/expoArk.js +78 -0
  48. package/dist/esm/providers/expoIndexer.js +101 -0
  49. package/dist/esm/providers/expoUtils.js +87 -0
  50. package/dist/esm/providers/indexer.js +3 -1
  51. package/dist/esm/providers/onchain.js +19 -20
  52. package/dist/esm/repositories/walletRepository.js +64 -28
  53. package/dist/esm/script/base.js +12 -4
  54. package/dist/esm/script/tapscript.js +1 -2
  55. package/dist/esm/script/vhtlc.js +1 -1
  56. package/dist/esm/tree/signingSession.js +45 -12
  57. package/dist/esm/tree/txTree.js +3 -4
  58. package/dist/esm/tree/validation.js +2 -3
  59. package/dist/esm/utils/arkTransaction.js +110 -9
  60. package/dist/esm/utils/transaction.js +24 -0
  61. package/dist/esm/utils/unknownFields.js +3 -3
  62. package/dist/esm/wallet/index.js +1 -1
  63. package/dist/esm/wallet/onchain.js +3 -4
  64. package/dist/esm/wallet/serviceWorker/response.js +32 -0
  65. package/dist/esm/wallet/serviceWorker/utils.js +1 -8
  66. package/dist/esm/wallet/serviceWorker/wallet.js +8 -9
  67. package/dist/esm/wallet/serviceWorker/worker.js +49 -33
  68. package/dist/esm/wallet/unroll.js +5 -7
  69. package/dist/esm/wallet/utils.js +16 -0
  70. package/dist/esm/wallet/vtxo-manager.js +317 -0
  71. package/dist/esm/wallet/wallet.js +159 -168
  72. package/dist/types/adapters/expo.d.ts +4 -0
  73. package/dist/types/arknote/index.d.ts +1 -1
  74. package/dist/types/forfeit.d.ts +2 -2
  75. package/dist/types/identity/index.d.ts +2 -2
  76. package/dist/types/identity/singleKey.d.ts +2 -2
  77. package/dist/types/index.d.ts +11 -9
  78. package/dist/types/intent/index.d.ts +41 -0
  79. package/dist/types/musig2/index.d.ts +1 -1
  80. package/dist/types/musig2/nonces.d.ts +1 -0
  81. package/dist/types/providers/ark.d.ts +197 -27
  82. package/dist/types/providers/errors.d.ts +13 -0
  83. package/dist/types/providers/expoArk.d.ts +22 -0
  84. package/dist/types/providers/expoIndexer.d.ts +18 -0
  85. package/dist/types/providers/expoUtils.d.ts +18 -0
  86. package/dist/types/providers/indexer.d.ts +8 -8
  87. package/dist/types/providers/onchain.d.ts +6 -2
  88. package/dist/types/repositories/walletRepository.d.ts +9 -5
  89. package/dist/types/script/base.d.ts +5 -2
  90. package/dist/types/tree/signingSession.d.ts +16 -11
  91. package/dist/types/utils/anchor.d.ts +2 -2
  92. package/dist/types/utils/arkTransaction.d.ts +15 -5
  93. package/dist/types/utils/transaction.d.ts +13 -0
  94. package/dist/types/utils/unknownFields.d.ts +4 -4
  95. package/dist/types/wallet/index.d.ts +47 -7
  96. package/dist/types/wallet/onchain.d.ts +1 -1
  97. package/dist/types/wallet/serviceWorker/response.d.ts +16 -2
  98. package/dist/types/wallet/serviceWorker/utils.d.ts +1 -2
  99. package/dist/types/wallet/serviceWorker/wallet.d.ts +2 -2
  100. package/dist/types/wallet/serviceWorker/worker.d.ts +7 -1
  101. package/dist/types/wallet/unroll.d.ts +1 -1
  102. package/dist/types/wallet/utils.d.ts +3 -0
  103. package/dist/types/wallet/vtxo-manager.d.ts +179 -0
  104. package/dist/types/wallet/wallet.d.ts +17 -5
  105. package/package.json +11 -3
  106. package/dist/cjs/bip322/errors.js +0 -13
  107. package/dist/esm/bip322/errors.js +0 -9
  108. package/dist/types/bip322/errors.d.ts +0 -6
  109. package/dist/types/bip322/index.d.ts +0 -57
package/README.md CHANGED
@@ -108,26 +108,60 @@ const settleTxid = await wallet.settle({
108
108
  })
109
109
  ```
110
110
 
111
+ ### VTXO Management (Renewal & Recovery)
112
+
113
+ VTXOs have an expiration time (batch expiry). The SDK provides the `VtxoManager` class to handle both:
114
+
115
+ - **Renewal**: Renew VTXOs before they expire to maintain unilateral control of the funds.
116
+ - **Recovery**: Reclaim swept or expired VTXOs back to the wallet in case renewal window was missed.
117
+
118
+ ```typescript
119
+ import { VtxoManager } from '@arkade-os/sdk'
120
+
121
+ // Create manager with optional renewal configuration
122
+ const manager = new VtxoManager(wallet, {
123
+ enabled: true, // Enable expiration monitoring
124
+ thresholdPercentage: 10 // Alert when 10% of lifetime remains (default)
125
+ })
126
+ ```
127
+
128
+ #### Renewal: Prevent Expiration
129
+
130
+ Renew VTXOs before they expire to retain unilateral control of funds.
131
+ This settles expiring and recoverable VTXOs back to your wallet, refreshing their expiration time.
132
+
133
+ ```typescript
134
+ // Renew all VTXOs to prevent expiration
135
+ const txid = await manager.renewVtxos()
136
+ console.log('Renewed:', txid)
137
+
138
+ // Check which VTXOs are expiring soon
139
+ const expiringVtxos = await manager.getExpiringVtxos()
140
+ // Override threshold percentage (e.g., renew when 5% of time remains)
141
+ const urgentlyExpiring = await manager.getExpiringVtxos(5)
142
+ ```
143
+
144
+
145
+ #### Recovery: Reclaim Swept VTXOs
146
+
147
+ Recover VTXOs that have been swept by the server or consolidate small amounts (subdust).
148
+
149
+ ```typescript
150
+ // Recover swept VTXOs and preconfirmed subdust
151
+ const txid = await manager.recoverVtxos((event) => {
152
+ console.log('Settlement event:', event.type)
153
+ })
154
+ console.log('Recovered:', txid)
155
+ // Check what's recoverable
156
+ const balance = await manager.getRecoverableBalance()
157
+ ```
158
+
111
159
 
112
160
  ### Transaction History
113
161
 
114
162
  ```typescript
115
163
  // Get transaction history
116
164
  const history = await wallet.getTransactionHistory()
117
- console.log('History:', history)
118
-
119
- // Example history entry:
120
- {
121
- key: {
122
- boardingTxid: '...', // for boarding transactions
123
- commitmentTxid: '...', // for commitment transactions
124
- redeemTxid: '...' // for regular transactions
125
- },
126
- type: TxType.TxReceived, // or TxType.TxSent
127
- amount: 50000,
128
- settled: true,
129
- createdAt: 1234567890
130
- }
131
165
  ```
132
166
 
133
167
  ### Offboarding
@@ -288,6 +322,55 @@ const wallet = await Wallet.create({
288
322
  })
289
323
  ```
290
324
 
325
+ ### Using with Expo/React Native
326
+
327
+ For React Native and Expo applications where standard EventSource and fetch streaming may not work properly, use the Expo-compatible providers:
328
+
329
+ ```typescript
330
+ import { Wallet, SingleKey } from '@arkade-os/sdk'
331
+ import { ExpoArkProvider, ExpoIndexerProvider } from '@arkade-os/sdk/adapters/expo'
332
+
333
+ const identity = SingleKey.fromHex('your_private_key_hex')
334
+
335
+ const wallet = await Wallet.create({
336
+ identity: identity,
337
+ esploraUrl: 'https://mutinynet.com/api',
338
+ arkProvider: new ExpoArkProvider('https://mutinynet.arkade.sh'), // For settlement events and transactions streaming
339
+ indexerProvider: new ExpoIndexerProvider('https://mutinynet.arkade.sh'), // For address subscriptions and VTXO updates
340
+ })
341
+
342
+ // use expo/fetch for streaming support (SSE)
343
+ // All other wallet functionality remains the same
344
+ const balance = await wallet.getBalance()
345
+ const address = await wallet.getAddress()
346
+ ```
347
+
348
+ Both ExpoArkProvider and ExpoIndexerProvider are available as adapters following the SDK's modular architecture pattern. This keeps the main SDK bundle clean while providing opt-in functionality for specific environments:
349
+
350
+ - **ExpoArkProvider**: Handles settlement events and transaction streaming using expo/fetch for Server-Sent Events
351
+ - **ExpoIndexerProvider**: Handles address subscriptions and VTXO updates using expo/fetch for JSON streaming
352
+
353
+ #### Crypto Polyfill Requirement
354
+
355
+ Install `expo-crypto` and polyfill `crypto.getRandomValues()` at the top of your app entry point:
356
+
357
+ ```bash
358
+ npx expo install expo-crypto
359
+ ```
360
+
361
+ ```typescript
362
+ // App.tsx or index.js - MUST be first import
363
+ import * as Crypto from 'expo-crypto';
364
+ if (!global.crypto) global.crypto = {} as any;
365
+ global.crypto.getRandomValues = Crypto.getRandomValues;
366
+
367
+ // Now import the SDK
368
+ import { Wallet, SingleKey } from '@arkade-os/sdk';
369
+ import { ExpoArkProvider, ExpoIndexerProvider } from '@arkade-os/sdk/adapters/expo';
370
+ ```
371
+
372
+ This is required for MuSig2 settlements and cryptographic operations.
373
+
291
374
  ### Repository Pattern
292
375
 
293
376
  Access low-level data management through repositories:
@@ -311,6 +394,8 @@ await wallet.contractRepository.saveToContractCollection(
311
394
  const swaps = await wallet.contractRepository.getContractCollection('swaps')
312
395
  ```
313
396
 
397
+ _For complete API documentation, visit our [TypeScript documentation](https://arkade-os.github.io/ts-sdk/)._
398
+
314
399
  ## Development
315
400
 
316
401
  ### Requirements
@@ -0,0 +1,8 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.ExpoIndexerProvider = exports.ExpoArkProvider = void 0;
4
+ // Expo adapter for React Native/Expo environments
5
+ var expoArk_1 = require("../providers/expoArk");
6
+ Object.defineProperty(exports, "ExpoArkProvider", { enumerable: true, get: function () { return expoArk_1.ExpoArkProvider; } });
7
+ var expoIndexer_1 = require("../providers/expoIndexer");
8
+ Object.defineProperty(exports, "ExpoIndexerProvider", { enumerable: true, get: function () { return expoIndexer_1.ExpoIndexerProvider; } });
@@ -2,9 +2,9 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.ArkNote = void 0;
4
4
  const base_1 = require("@scure/base");
5
- const base_2 = require("../script/base");
6
5
  const utils_js_1 = require("@scure/btc-signer/utils.js");
7
- const script_js_1 = require("@scure/btc-signer/script.js");
6
+ const btc_signer_1 = require("@scure/btc-signer");
7
+ const base_2 = require("../script/base");
8
8
  /**
9
9
  * ArkNotes are special virtual coins in the Ark protocol that can be created
10
10
  * and spent without requiring any transactions. The server mints them, and they
@@ -85,5 +85,5 @@ function readUInt32BE(array, offset) {
85
85
  return view.getUint32(0, false);
86
86
  }
87
87
  function noteTapscript(preimageHash) {
88
- return script_js_1.Script.encode(["SHA256", preimageHash, "EQUAL"]);
88
+ return btc_signer_1.Script.encode(["SHA256", preimageHash, "EQUAL"]);
89
89
  }
@@ -1,10 +1,10 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.buildForfeitTx = buildForfeitTx;
4
- const transaction_js_1 = require("@scure/btc-signer/transaction.js");
4
+ const transaction_1 = require("./utils/transaction");
5
5
  const anchor_1 = require("./utils/anchor");
6
6
  function buildForfeitTx(inputs, forfeitPkScript, txLocktime) {
7
- const tx = new transaction_js_1.Transaction({
7
+ const tx = new transaction_1.Transaction({
8
8
  version: 3,
9
9
  lockTime: txLocktime,
10
10
  });
@@ -2,12 +2,11 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.SingleKey = void 0;
4
4
  const utils_js_1 = require("@scure/btc-signer/utils.js");
5
+ const btc_signer_1 = require("@scure/btc-signer");
5
6
  const base_1 = require("@scure/base");
6
- const transaction_js_1 = require("@scure/btc-signer/transaction.js");
7
7
  const signingSession_1 = require("../tree/signingSession");
8
8
  const secp256k1_1 = require("@noble/secp256k1");
9
- const ZERO_32 = new Uint8Array(32).fill(0);
10
- const ALL_SIGHASH = Object.values(transaction_js_1.SigHash).filter((x) => typeof x === "number");
9
+ const ALL_SIGHASH = Object.values(btc_signer_1.SigHash).filter((x) => typeof x === "number");
11
10
  /**
12
11
  * In-memory single key implementation for Bitcoin transaction signing.
13
12
  *
@@ -51,7 +50,7 @@ class SingleKey {
51
50
  const txCpy = tx.clone();
52
51
  if (!inputIndexes) {
53
52
  try {
54
- if (!txCpy.sign(this.key, ALL_SIGHASH, ZERO_32)) {
53
+ if (!txCpy.sign(this.key, ALL_SIGHASH)) {
55
54
  throw new Error("Failed to sign transaction");
56
55
  }
57
56
  }
@@ -67,7 +66,7 @@ class SingleKey {
67
66
  return txCpy;
68
67
  }
69
68
  for (const inputIndex of inputIndexes) {
70
- if (!txCpy.signIdx(this.key, inputIndex, ALL_SIGHASH, ZERO_32)) {
69
+ if (!txCpy.signIdx(this.key, inputIndex, ALL_SIGHASH)) {
71
70
  throw new Error(`Failed to sign input #${inputIndex}`);
72
71
  }
73
72
  }
@@ -82,9 +81,10 @@ class SingleKey {
82
81
  signerSession() {
83
82
  return signingSession_1.TreeSignerSession.random();
84
83
  }
85
- async signMessage(message) {
86
- const msgBytes = new TextEncoder().encode(message);
87
- return secp256k1_1.schnorr.sign((0, utils_js_1.sha256)(msgBytes), this.key);
84
+ async signMessage(message, signatureType = "schnorr") {
85
+ if (signatureType === "ecdsa")
86
+ return (0, secp256k1_1.sign)(message, this.key, { prehash: false });
87
+ return secp256k1_1.schnorr.sign(message, this.key);
88
88
  }
89
89
  }
90
90
  exports.SingleKey = SingleKey;
package/dist/cjs/index.js CHANGED
@@ -1,8 +1,9 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.Transaction = exports.Unroll = exports.P2A = exports.TxTree = exports.BIP322 = exports.ContractRepositoryImpl = exports.WalletRepositoryImpl = exports.networks = exports.ArkNote = exports.waitForIncomingFunds = exports.buildOffchainTx = exports.ConditionWitness = exports.VtxoTaprootTree = exports.VtxoTreeExpiry = exports.CosignerPublicKey = exports.getArkPsbtFields = exports.setArkPsbtField = exports.ArkPsbtFieldKeyType = exports.ArkPsbtFieldKey = exports.CLTVMultisigTapscript = exports.ConditionMultisigTapscript = exports.ConditionCSVMultisigTapscript = exports.CSVMultisigTapscript = exports.MultisigTapscript = exports.decodeTapscript = exports.Response = exports.Request = exports.ServiceWorkerWallet = exports.Worker = exports.setupServiceWorker = exports.SettlementEventType = exports.ChainTxType = exports.IndexerTxType = exports.TxType = exports.VHTLC = exports.VtxoScript = exports.DefaultVtxo = exports.ArkAddress = exports.RestIndexerProvider = exports.RestArkProvider = exports.EsploraProvider = exports.ESPLORA_URL = exports.Ramps = exports.OnchainWallet = exports.SingleKey = exports.Wallet = void 0;
4
- const transaction_js_1 = require("@scure/btc-signer/transaction.js");
5
- Object.defineProperty(exports, "Transaction", { enumerable: true, get: function () { return transaction_js_1.Transaction; } });
3
+ exports.Transaction = exports.Unroll = exports.P2A = exports.TxTree = exports.Intent = exports.ContractRepositoryImpl = exports.WalletRepositoryImpl = exports.networks = exports.ArkNote = exports.hasBoardingTxExpired = exports.waitForIncomingFunds = exports.verifyTapscriptSignatures = exports.buildOffchainTx = exports.ConditionWitness = exports.VtxoTaprootTree = exports.VtxoTreeExpiry = exports.CosignerPublicKey = exports.getArkPsbtFields = exports.setArkPsbtField = exports.ArkPsbtFieldKeyType = exports.ArkPsbtFieldKey = exports.TapTreeCoder = exports.CLTVMultisigTapscript = exports.ConditionMultisigTapscript = exports.ConditionCSVMultisigTapscript = exports.CSVMultisigTapscript = exports.MultisigTapscript = exports.decodeTapscript = exports.Response = exports.Request = exports.ServiceWorkerWallet = exports.Worker = exports.setupServiceWorker = exports.SettlementEventType = exports.ChainTxType = exports.IndexerTxType = exports.TxType = exports.VHTLC = exports.VtxoScript = exports.DefaultVtxo = exports.ArkAddress = exports.RestIndexerProvider = exports.RestArkProvider = exports.EsploraProvider = exports.ESPLORA_URL = exports.VtxoManager = exports.Ramps = exports.OnchainWallet = exports.SingleKey = exports.Wallet = void 0;
4
+ exports.maybeArkError = exports.ArkError = void 0;
5
+ const transaction_1 = require("./utils/transaction");
6
+ Object.defineProperty(exports, "Transaction", { enumerable: true, get: function () { return transaction_1.Transaction; } });
6
7
  const singleKey_1 = require("./identity/singleKey");
7
8
  Object.defineProperty(exports, "SingleKey", { enumerable: true, get: function () { return singleKey_1.SingleKey; } });
8
9
  const address_1 = require("./script/address");
@@ -13,6 +14,7 @@ const default_1 = require("./script/default");
13
14
  Object.defineProperty(exports, "DefaultVtxo", { enumerable: true, get: function () { return default_1.DefaultVtxo; } });
14
15
  const base_1 = require("./script/base");
15
16
  Object.defineProperty(exports, "VtxoScript", { enumerable: true, get: function () { return base_1.VtxoScript; } });
17
+ Object.defineProperty(exports, "TapTreeCoder", { enumerable: true, get: function () { return base_1.TapTreeCoder; } });
16
18
  const wallet_1 = require("./wallet");
17
19
  Object.defineProperty(exports, "TxType", { enumerable: true, get: function () { return wallet_1.TxType; } });
18
20
  const wallet_2 = require("./wallet/wallet");
@@ -22,6 +24,8 @@ const txTree_1 = require("./tree/txTree");
22
24
  Object.defineProperty(exports, "TxTree", { enumerable: true, get: function () { return txTree_1.TxTree; } });
23
25
  const ramps_1 = require("./wallet/ramps");
24
26
  Object.defineProperty(exports, "Ramps", { enumerable: true, get: function () { return ramps_1.Ramps; } });
27
+ const vtxo_manager_1 = require("./wallet/vtxo-manager");
28
+ Object.defineProperty(exports, "VtxoManager", { enumerable: true, get: function () { return vtxo_manager_1.VtxoManager; } });
25
29
  const wallet_3 = require("./wallet/serviceWorker/wallet");
26
30
  Object.defineProperty(exports, "ServiceWorkerWallet", { enumerable: true, get: function () { return wallet_3.ServiceWorkerWallet; } });
27
31
  const onchain_1 = require("./wallet/onchain");
@@ -48,7 +52,9 @@ Object.defineProperty(exports, "CSVMultisigTapscript", { enumerable: true, get:
48
52
  Object.defineProperty(exports, "decodeTapscript", { enumerable: true, get: function () { return tapscript_1.decodeTapscript; } });
49
53
  Object.defineProperty(exports, "MultisigTapscript", { enumerable: true, get: function () { return tapscript_1.MultisigTapscript; } });
50
54
  const arkTransaction_1 = require("./utils/arkTransaction");
55
+ Object.defineProperty(exports, "hasBoardingTxExpired", { enumerable: true, get: function () { return arkTransaction_1.hasBoardingTxExpired; } });
51
56
  Object.defineProperty(exports, "buildOffchainTx", { enumerable: true, get: function () { return arkTransaction_1.buildOffchainTx; } });
57
+ Object.defineProperty(exports, "verifyTapscriptSignatures", { enumerable: true, get: function () { return arkTransaction_1.verifyTapscriptSignatures; } });
52
58
  const unknownFields_1 = require("./utils/unknownFields");
53
59
  Object.defineProperty(exports, "VtxoTaprootTree", { enumerable: true, get: function () { return unknownFields_1.VtxoTaprootTree; } });
54
60
  Object.defineProperty(exports, "ConditionWitness", { enumerable: true, get: function () { return unknownFields_1.ConditionWitness; } });
@@ -58,8 +64,8 @@ Object.defineProperty(exports, "ArkPsbtFieldKey", { enumerable: true, get: funct
58
64
  Object.defineProperty(exports, "ArkPsbtFieldKeyType", { enumerable: true, get: function () { return unknownFields_1.ArkPsbtFieldKeyType; } });
59
65
  Object.defineProperty(exports, "CosignerPublicKey", { enumerable: true, get: function () { return unknownFields_1.CosignerPublicKey; } });
60
66
  Object.defineProperty(exports, "VtxoTreeExpiry", { enumerable: true, get: function () { return unknownFields_1.VtxoTreeExpiry; } });
61
- const bip322_1 = require("./bip322");
62
- Object.defineProperty(exports, "BIP322", { enumerable: true, get: function () { return bip322_1.BIP322; } });
67
+ const intent_1 = require("./intent");
68
+ Object.defineProperty(exports, "Intent", { enumerable: true, get: function () { return intent_1.Intent; } });
63
69
  const arknote_1 = require("./arknote");
64
70
  Object.defineProperty(exports, "ArkNote", { enumerable: true, get: function () { return arknote_1.ArkNote; } });
65
71
  const networks_1 = require("./networks");
@@ -76,3 +82,6 @@ const walletRepository_1 = require("./repositories/walletRepository");
76
82
  Object.defineProperty(exports, "WalletRepositoryImpl", { enumerable: true, get: function () { return walletRepository_1.WalletRepositoryImpl; } });
77
83
  const contractRepository_1 = require("./repositories/contractRepository");
78
84
  Object.defineProperty(exports, "ContractRepositoryImpl", { enumerable: true, get: function () { return contractRepository_1.ContractRepositoryImpl; } });
85
+ const errors_1 = require("./providers/errors");
86
+ Object.defineProperty(exports, "ArkError", { enumerable: true, get: function () { return errors_1.ArkError; } });
87
+ Object.defineProperty(exports, "maybeArkError", { enumerable: true, get: function () { return errors_1.maybeArkError; } });
@@ -1,26 +1,23 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.BIP322 = void 0;
4
- exports.craftToSpendTx = craftToSpendTx;
5
- const script_js_1 = require("@scure/btc-signer/script.js");
6
- const transaction_js_1 = require("@scure/btc-signer/transaction.js");
7
- const script_js_2 = require("@scure/btc-signer/script.js");
8
- const errors_1 = require("./errors");
3
+ exports.Intent = void 0;
4
+ const btc_signer_1 = require("@scure/btc-signer");
9
5
  const secp256k1_js_1 = require("@noble/curves/secp256k1.js");
10
- const base_1 = require("@scure/base");
6
+ const transaction_1 = require("../utils/transaction");
11
7
  /**
12
- * BIP-322 signature implementation for Bitcoin message signing.
8
+ * Intent proof implementation for Bitcoin message signing.
13
9
  *
14
- * BIP-322 defines a standard for signing Bitcoin messages as well as proving
10
+ * Intent proof defines a standard for signing Bitcoin messages as well as proving
15
11
  * ownership of coins. This namespace provides utilities for creating and
16
- * validating BIP-322.
12
+ * validating Intent proof.
17
13
  *
14
+ * it is greatly inspired by BIP322.
18
15
  * @see https://github.com/bitcoin/bips/blob/master/bip-0322.mediawiki
19
16
  *
20
17
  * @example
21
18
  * ```typescript
22
- * // Create a BIP-322 proof
23
- * const proof = BIP322.create(
19
+ * // Create a Intent proof
20
+ * const proof = Intent.create(
24
21
  * "Hello Bitcoin!",
25
22
  * [input],
26
23
  * [output]
@@ -29,65 +26,46 @@ const base_1 = require("@scure/base");
29
26
  * // Sign the proof
30
27
  * const signedProof = await identity.sign(proof);
31
28
  *
32
- * // Extract the signature
33
- * const signature = BIP322.signature(signedProof);
34
- * ```
35
29
  */
36
- var BIP322;
37
- (function (BIP322) {
30
+ var Intent;
31
+ (function (Intent) {
38
32
  /**
39
- * Creates a new BIP-322 "full" proof of funds unsigned transaction.
33
+ * Creates a new Intent proof unsigned transaction.
40
34
  *
41
35
  * This function constructs a special transaction that can be signed to prove
42
36
  * ownership of VTXOs and UTXOs. The proof includes the message to be
43
37
  * signed and the inputs/outputs that demonstrate ownership.
44
38
  *
45
- * @param message - The BIP-322 message to be signed
39
+ * @param message - The Intent message to be signed
46
40
  * @param inputs - Array of transaction inputs to prove ownership of
47
41
  * @param outputs - Optional array of transaction outputs
48
- * @returns An unsigned BIP-322 proof transaction
42
+ * @returns An unsigned Intent proof transaction
49
43
  */
50
44
  function create(message, inputs, outputs = []) {
51
45
  if (inputs.length == 0)
52
- throw errors_1.ErrMissingInputs;
46
+ throw new Error("intent proof requires at least one input");
53
47
  if (!validateInputs(inputs))
54
- throw errors_1.ErrMissingData;
48
+ throw new Error("invalid inputs");
55
49
  if (!validateOutputs(outputs))
56
- throw errors_1.ErrMissingData;
50
+ throw new Error("invalid outputs");
57
51
  // create the initial transaction to spend
58
52
  const toSpend = craftToSpendTx(message, inputs[0].witnessUtxo.script);
59
53
  // create the transaction to sign
60
54
  return craftToSignTx(toSpend, inputs, outputs);
61
55
  }
62
- BIP322.create = create;
63
- /**
64
- * Finalizes and extracts the FullProof transaction into a BIP-322 signature.
65
- *
66
- * This function takes a signed proof transaction and converts it into a
67
- * base64-encoded signature string. If the proof's inputs have special
68
- * spending conditions, a custom finalizer can be provided.
69
- *
70
- * @param signedProof - The signed BIP-322 proof transaction
71
- * @param finalizer - Optional custom finalizer function
72
- * @returns Base64-encoded BIP-322 signature
73
- */
74
- function signature(signedProof, finalizer = (tx) => tx.finalize()) {
75
- finalizer(signedProof);
76
- return base_1.base64.encode(signedProof.extract());
77
- }
78
- BIP322.signature = signature;
79
- })(BIP322 || (exports.BIP322 = BIP322 = {}));
80
- const OP_RETURN_EMPTY_PKSCRIPT = new Uint8Array([script_js_1.OP.RETURN]);
56
+ Intent.create = create;
57
+ })(Intent || (exports.Intent = Intent = {}));
58
+ const OP_RETURN_EMPTY_PKSCRIPT = new Uint8Array([btc_signer_1.OP.RETURN]);
81
59
  const ZERO_32 = new Uint8Array(32).fill(0);
82
60
  const MAX_INDEX = 0xffffffff;
83
- const TAG_BIP322 = "BIP0322-signed-message";
61
+ const TAG_INTENT_PROOF = "ark-intent-proof-message";
84
62
  function validateInput(input) {
85
63
  if (input.index === undefined)
86
- throw errors_1.ErrMissingData;
64
+ throw new Error("intent proof input requires index");
87
65
  if (input.txid === undefined)
88
- throw errors_1.ErrMissingData;
66
+ throw new Error("intent proof input requires txid");
89
67
  if (input.witnessUtxo === undefined)
90
- throw errors_1.ErrMissingWitnessUtxo;
68
+ throw new Error("intent proof input requires witness utxo");
91
69
  return true;
92
70
  }
93
71
  function validateInputs(inputs) {
@@ -96,9 +74,9 @@ function validateInputs(inputs) {
96
74
  }
97
75
  function validateOutput(output) {
98
76
  if (output.amount === undefined)
99
- throw errors_1.ErrMissingData;
77
+ throw new Error("intent proof output requires amount");
100
78
  if (output.script === undefined)
101
- throw errors_1.ErrMissingData;
79
+ throw new Error("intent proof output requires script");
102
80
  return true;
103
81
  }
104
82
  function validateOutputs(outputs) {
@@ -108,11 +86,8 @@ function validateOutputs(outputs) {
108
86
  // craftToSpendTx creates the initial transaction that will be spent in the proof
109
87
  function craftToSpendTx(message, pkScript) {
110
88
  const messageHash = hashMessage(message);
111
- const tx = new transaction_js_1.Transaction({
89
+ const tx = new transaction_1.Transaction({
112
90
  version: 0,
113
- allowUnknownOutputs: true,
114
- allowUnknown: true,
115
- allowUnknownInputs: true,
116
91
  });
117
92
  // add input with zero hash and max index
118
93
  tx.addInput({
@@ -126,18 +101,15 @@ function craftToSpendTx(message, pkScript) {
126
101
  script: pkScript,
127
102
  });
128
103
  tx.updateInput(0, {
129
- finalScriptSig: script_js_2.Script.encode(["OP_0", messageHash]),
104
+ finalScriptSig: btc_signer_1.Script.encode(["OP_0", messageHash]),
130
105
  });
131
106
  return tx;
132
107
  }
133
108
  // craftToSignTx creates the transaction that will be signed for the proof
134
109
  function craftToSignTx(toSpend, inputs, outputs) {
135
110
  const firstInput = inputs[0];
136
- const tx = new transaction_js_1.Transaction({
111
+ const tx = new transaction_1.Transaction({
137
112
  version: 2,
138
- allowUnknownOutputs: outputs.length === 0,
139
- allowUnknown: true,
140
- allowUnknownInputs: true,
141
113
  lockTime: 0,
142
114
  });
143
115
  // add the first "toSpend" input
@@ -149,14 +121,19 @@ function craftToSignTx(toSpend, inputs, outputs) {
149
121
  script: firstInput.witnessUtxo.script,
150
122
  amount: 0n,
151
123
  },
152
- sighashType: transaction_js_1.SigHash.ALL,
124
+ sighashType: btc_signer_1.SigHash.ALL,
153
125
  });
154
126
  // add other inputs
155
- for (const input of inputs) {
127
+ for (const [i, input] of inputs.entries()) {
156
128
  tx.addInput({
157
129
  ...input,
158
- sighashType: transaction_js_1.SigHash.ALL,
130
+ sighashType: btc_signer_1.SigHash.ALL,
159
131
  });
132
+ if (input.unknown?.length) {
133
+ tx.updateInput(i + 1, {
134
+ unknown: input.unknown,
135
+ });
136
+ }
160
137
  }
161
138
  // add the special OP_RETURN output if no outputs are provided
162
139
  if (outputs.length === 0) {
@@ -176,5 +153,5 @@ function craftToSignTx(toSpend, inputs, outputs) {
176
153
  return tx;
177
154
  }
178
155
  function hashMessage(message) {
179
- return secp256k1_js_1.schnorr.utils.taggedHash(TAG_BIP322, new TextEncoder().encode(message));
156
+ return secp256k1_js_1.schnorr.utils.taggedHash(TAG_INTENT_PROOF, new TextEncoder().encode(message));
180
157
  }
@@ -1,8 +1,9 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.aggregateKeys = exports.sign = exports.PartialSig = exports.generateNonces = void 0;
3
+ exports.aggregateKeys = exports.sign = exports.PartialSig = exports.aggregateNonces = exports.generateNonces = void 0;
4
4
  var nonces_1 = require("./nonces");
5
5
  Object.defineProperty(exports, "generateNonces", { enumerable: true, get: function () { return nonces_1.generateNonces; } });
6
+ Object.defineProperty(exports, "aggregateNonces", { enumerable: true, get: function () { return nonces_1.aggregateNonces; } });
6
7
  var sign_1 = require("./sign");
7
8
  Object.defineProperty(exports, "PartialSig", { enumerable: true, get: function () { return sign_1.PartialSig; } });
8
9
  Object.defineProperty(exports, "sign", { enumerable: true, get: function () { return sign_1.sign; } });
@@ -34,6 +34,7 @@ var __importStar = (this && this.__importStar) || (function () {
34
34
  })();
35
35
  Object.defineProperty(exports, "__esModule", { value: true });
36
36
  exports.generateNonces = generateNonces;
37
+ exports.aggregateNonces = aggregateNonces;
37
38
  const musig = __importStar(require("@scure/btc-signer/musig2.js"));
38
39
  /**
39
40
  * Generates a pair of public and secret nonces for MuSig2 signing
@@ -42,3 +43,6 @@ function generateNonces(publicKey) {
42
43
  const nonces = musig.nonceGen(publicKey);
43
44
  return { secNonce: nonces.secret, pubNonce: nonces.public };
44
45
  }
46
+ function aggregateNonces(pubNonces) {
47
+ return musig.nonceAggregate(pubNonces);
48
+ }