@utexo/rgb-sdk 1.0.3 → 1.0.5

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 (37) hide show
  1. package/Readme.md +267 -301
  2. package/cli/README.md +348 -0
  3. package/cli/commands/address.mjs +16 -0
  4. package/cli/commands/blindreceive.mjs +15 -0
  5. package/cli/commands/btcbalance.mjs +11 -0
  6. package/cli/commands/createlightninginvoice.mjs +14 -0
  7. package/cli/commands/createutxos.mjs +13 -0
  8. package/cli/commands/decodergbinvoice.mjs +9 -0
  9. package/cli/commands/generate_keys.mjs +35 -0
  10. package/cli/commands/getlightningreceiverequest.mjs +10 -0
  11. package/cli/commands/getlightningsendrequest.mjs +10 -0
  12. package/cli/commands/getonchainsendstatus.mjs +20 -0
  13. package/cli/commands/listassets.mjs +11 -0
  14. package/cli/commands/listtransfers.mjs +10 -0
  15. package/cli/commands/listunspents.mjs +10 -0
  16. package/cli/commands/onchainreceive.mjs +16 -0
  17. package/cli/commands/onchainsend.mjs +11 -0
  18. package/cli/commands/onchainsendbegin.mjs +9 -0
  19. package/cli/commands/onchainsendend.mjs +9 -0
  20. package/cli/commands/paylightninginvoice.mjs +11 -0
  21. package/cli/commands/paylightninginvoicebegin.mjs +10 -0
  22. package/cli/commands/paylightninginvoiceend.mjs +9 -0
  23. package/cli/commands/refresh.mjs +9 -0
  24. package/cli/commands/send.mjs +31 -0
  25. package/cli/commands/sign-psbt.mjs +12 -0
  26. package/cli/commands/signpsbt.mjs +10 -0
  27. package/cli/commands/witnessreceive.mjs +15 -0
  28. package/cli/generate_keys.mjs +66 -0
  29. package/cli/run.mjs +291 -0
  30. package/cli/utils.mjs +220 -0
  31. package/dist/index.cjs +1606 -121
  32. package/dist/index.cjs.map +1 -1
  33. package/dist/index.d.mts +1235 -145
  34. package/dist/index.d.ts +1235 -145
  35. package/dist/index.mjs +1592 -116
  36. package/dist/index.mjs.map +1 -1
  37. package/package.json +21 -8
package/dist/index.mjs CHANGED
@@ -1,12 +1,31 @@
1
- import * as path from 'path';
2
- import path__default from 'path';
3
- import * as fs from 'fs';
1
+ import * as path3 from 'path';
2
+ import path3__default from 'path';
3
+ import * as fs2 from 'fs';
4
+ import fs2__default from 'fs';
4
5
  import rgblib from '@utexo/rgb-lib';
5
6
  import * as noble from '@noble/hashes/legacy.js';
6
- import * as os from 'os';
7
+ import { hmac } from '@noble/hashes/hmac.js';
8
+ import { sha256 as sha256$1 } from '@noble/hashes/sha2.js';
9
+ import axios from 'axios';
7
10
 
8
11
  // src/client/rgb-lib-client.ts
9
12
 
13
+ // src/client/network-config.ts
14
+ var DEFAULT_TRANSPORT_ENDPOINTS = {
15
+ mainnet: "rpcs://rgb-proxy-mainnet.utexo.com/json-rpc",
16
+ testnet: "rpcs://rgb-proxy-testnet3.utexo.com/json-rpc",
17
+ testnet4: "rpcs://proxy.iriswallet.com/0.2/json-rpc",
18
+ signet: "rpcs://rgb-proxy-utexo.utexo.com/json-rpc",
19
+ regtest: "rpcs://proxy.iriswallet.com/0.2/json-rpc"
20
+ };
21
+ var DEFAULT_INDEXER_URLS = {
22
+ mainnet: "ssl://electrum.iriswallet.com:50003",
23
+ testnet: "ssl://electrum.iriswallet.com:50013",
24
+ testnet4: "ssl://electrum.iriswallet.com:50053",
25
+ signet: "https://esplora-api.utexo.com",
26
+ regtest: "tcp://regtest.thunderstack.org:50001"
27
+ };
28
+
10
29
  // src/errors/index.ts
11
30
  var SDKError = class _SDKError extends Error {
12
31
  constructor(message, code, statusCode, cause) {
@@ -105,6 +124,135 @@ var DERIVATION_ACCOUNT = 0;
105
124
  var KEYCHAIN_RGB = 0;
106
125
  var KEYCHAIN_BTC = 0;
107
126
 
127
+ // src/utexo/config/utexo-presets.ts
128
+ function withGetAssetById(config) {
129
+ return {
130
+ ...config,
131
+ getAssetById(tokenId) {
132
+ return config.assets.find((a) => a.tokenId === tokenId);
133
+ }
134
+ };
135
+ }
136
+ var testnetPreset = {
137
+ networkMap: {
138
+ mainnet: "testnet",
139
+ utexo: "signet"
140
+ },
141
+ networkIdMap: {
142
+ mainnet: withGetAssetById({
143
+ networkName: "RGB",
144
+ networkId: 36,
145
+ assets: [
146
+ {
147
+ assetId: "rgb:WPRv95Nj-icdrgPp-zpQhIp_-2TyJ~Ge-k~FvuMZ-~vVnkA0",
148
+ tokenName: "tUSD",
149
+ longName: "USDT",
150
+ precision: 6,
151
+ tokenId: 4
152
+ }
153
+ ]
154
+ }),
155
+ mainnetLightning: withGetAssetById({
156
+ networkName: "RGB Lightning",
157
+ networkId: 94,
158
+ assets: [
159
+ {
160
+ assetId: "rgb:WPRv95Nj-icdrgPp-zpQhIp_-2TyJ~Ge-k~FvuMZ-~vVnkA0",
161
+ tokenName: "tUSD",
162
+ longName: "USDT",
163
+ precision: 6,
164
+ tokenId: 4
165
+ }
166
+ ]
167
+ }),
168
+ utexo: withGetAssetById({
169
+ networkName: "UTEXO",
170
+ networkId: 96,
171
+ assets: [
172
+ {
173
+ assetId: "rgb:yJW4k8si-~8JdNfl-nM91qFu-r5rH_HS-1hM7jpi-L~lBf90",
174
+ tokenName: "tUSD",
175
+ longName: "USDT",
176
+ precision: 6,
177
+ tokenId: 4
178
+ }
179
+ ]
180
+ })
181
+ }
182
+ };
183
+ var mainnetPreset = {
184
+ networkMap: {
185
+ mainnet: "mainnet",
186
+ utexo: "signet"
187
+ },
188
+ networkIdMap: {
189
+ mainnet: withGetAssetById({
190
+ networkName: "RGB",
191
+ networkId: 36,
192
+ // TODO: Update to production network ID
193
+ assets: [
194
+ {
195
+ assetId: "rgb:WPRv95Nj-icdrgPp-zpQhIp_-2TyJ~Ge-k~FvuMZ-~vVnkA0",
196
+ // TODO: Update to production asset ID
197
+ tokenName: "tUSD",
198
+ longName: "USDT",
199
+ precision: 6,
200
+ tokenId: 4
201
+ }
202
+ ]
203
+ }),
204
+ mainnetLightning: withGetAssetById({
205
+ networkName: "RGB Lightning",
206
+ networkId: 94,
207
+ // TODO: Update to production network ID
208
+ assets: [
209
+ {
210
+ assetId: "rgb:WPRv95Nj-icdrgPp-zpQhIp_-2TyJ~Ge-k~FvuMZ-~vVnkA0",
211
+ // TODO: Update to production asset ID
212
+ tokenName: "tUSD",
213
+ longName: "USDT",
214
+ precision: 6,
215
+ tokenId: 4
216
+ }
217
+ ]
218
+ }),
219
+ utexo: withGetAssetById({
220
+ networkName: "UTEXO",
221
+ networkId: 96,
222
+ // TODO: Update to production network ID
223
+ assets: [
224
+ {
225
+ assetId: "rgb:yJW4k8si-~8JdNfl-nM91qFu-r5rH_HS-1hM7jpi-L~lBf90",
226
+ // TODO: Update to production asset ID
227
+ tokenName: "tUSD",
228
+ longName: "USDT",
229
+ precision: 6,
230
+ tokenId: 4
231
+ }
232
+ ]
233
+ })
234
+ }
235
+ };
236
+
237
+ // src/utexo/utils/network.ts
238
+ var NETWORK_PRESETS = {
239
+ mainnet: mainnetPreset,
240
+ testnet: testnetPreset
241
+ };
242
+ function getUtxoNetworkConfig(preset) {
243
+ return NETWORK_PRESETS[preset];
244
+ }
245
+ var utexoNetworkMap = testnetPreset.networkMap;
246
+ var utexoNetworkIdMap = testnetPreset.networkIdMap;
247
+ function getDestinationAsset(senderNetwork, destinationNetwork, assetIdSender) {
248
+ const destinationConfig = utexoNetworkIdMap[destinationNetwork];
249
+ if (assetIdSender == null) return destinationConfig.assets[0];
250
+ const senderConfig = utexoNetworkIdMap[senderNetwork];
251
+ const senderAsset = senderConfig.assets.find((a) => a.assetId === assetIdSender);
252
+ if (!senderAsset) return void 0;
253
+ return destinationConfig.assets.find((a) => a.tokenId === senderAsset.tokenId);
254
+ }
255
+
108
256
  // src/constants/network.ts
109
257
  var COIN_RGB_MAINNET = 827166;
110
258
  var COIN_RGB_TESTNET = 827167;
@@ -220,7 +368,6 @@ function validateString(value, field) {
220
368
  throw new ValidationError(`${field} must be a non-empty string`, field);
221
369
  }
222
370
  }
223
- var DEFAULT_TRANSPORT_ENDPOINT = "rpcs://proxy.iriswallet.com/0.2/json-rpc";
224
371
  function mapNetworkToRgbLib(network) {
225
372
  const networkMap = {
226
373
  "mainnet": "Mainnet",
@@ -234,10 +381,10 @@ function mapNetworkToRgbLib(network) {
234
381
  }
235
382
  var restoreWallet = (params) => {
236
383
  const { backupFilePath, password, dataDir } = params;
237
- if (!fs.existsSync(backupFilePath)) {
384
+ if (!fs2.existsSync(backupFilePath)) {
238
385
  throw new ValidationError("Backup file not found", "backup");
239
386
  }
240
- if (!fs.existsSync(dataDir)) {
387
+ if (!fs2.existsSync(dataDir)) {
241
388
  throw new ValidationError(`Restore directory does not exist: ${dataDir}`, "restoreDir");
242
389
  }
243
390
  rgblib.restoreBackup(backupFilePath, password, dataDir);
@@ -245,6 +392,26 @@ var restoreWallet = (params) => {
245
392
  message: "Wallet restored successfully"
246
393
  };
247
394
  };
395
+ var restoreFromVss = (params) => {
396
+ const anyLib = rgblib;
397
+ if (typeof anyLib.restoreFromVss !== "function") {
398
+ throw new WalletError("VSS restore is not available in the current rgb-lib build.");
399
+ }
400
+ if (!params.targetDir) {
401
+ throw new ValidationError("targetDir is required", "targetDir");
402
+ }
403
+ const { config, targetDir } = params;
404
+ const mappedConfig = {
405
+ server_url: config.serverUrl,
406
+ store_id: config.storeId,
407
+ signing_key: config.signingKey
408
+ };
409
+ const walletPath = anyLib.restoreFromVss(mappedConfig, targetDir);
410
+ return {
411
+ message: "Wallet restored from VSS successfully",
412
+ walletPath
413
+ };
414
+ };
248
415
  var RGBLibClient = class {
249
416
  constructor(params) {
250
417
  this.online = null;
@@ -254,21 +421,14 @@ var RGBLibClient = class {
254
421
  this.originalNetwork = params.network;
255
422
  this.network = normalizeNetwork(this.originalNetwork);
256
423
  this.dataDir = params.dataDir;
257
- this.transportEndpoint = params.transportEndpoint || DEFAULT_TRANSPORT_ENDPOINT;
424
+ this.transportEndpoint = params.transportEndpoint || DEFAULT_TRANSPORT_ENDPOINTS[this.network] || DEFAULT_TRANSPORT_ENDPOINTS.signet;
258
425
  if (params.indexerUrl) {
259
426
  this.indexerUrl = params.indexerUrl;
260
427
  } else {
261
- const defaultIndexerUrls = {
262
- "mainnet": "ssl://electrum.iriswallet.com:50003",
263
- "testnet": "ssl://electrum.iriswallet.com:50013",
264
- "testnet4": "ssl://electrum.iriswallet.com:50053",
265
- "signet": "tcp://46.224.75.237:50001",
266
- "regtest": "tcp://regtest.thunderstack.org:50001"
267
- };
268
- this.indexerUrl = defaultIndexerUrls[this.network] || defaultIndexerUrls["regtest"];
428
+ this.indexerUrl = DEFAULT_INDEXER_URLS[this.network] || DEFAULT_INDEXER_URLS.signet;
269
429
  }
270
- if (!fs.existsSync(this.dataDir)) {
271
- fs.mkdirSync(this.dataDir, { recursive: true });
430
+ if (!fs2.existsSync(this.dataDir)) {
431
+ fs2.mkdirSync(this.dataDir, { recursive: true });
272
432
  }
273
433
  const walletData = {
274
434
  dataDir: this.dataDir,
@@ -288,6 +448,7 @@ var RGBLibClient = class {
288
448
  try {
289
449
  this.wallet = new rgblib.Wallet(new rgblib.WalletData(walletData));
290
450
  } catch (error) {
451
+ console.log("error", error);
291
452
  throw new WalletError("Failed to initialize rgb-lib wallet", void 0, error);
292
453
  }
293
454
  }
@@ -299,7 +460,6 @@ var RGBLibClient = class {
299
460
  return;
300
461
  }
301
462
  try {
302
- console.log("indexerUrl", this.indexerUrl);
303
463
  this.online = this.wallet.goOnline(false, this.indexerUrl);
304
464
  } catch (error) {
305
465
  throw new WalletError("Failed to establish online connection", void 0, error);
@@ -349,10 +509,9 @@ var RGBLibClient = class {
349
509
  }
350
510
  sendBegin(params) {
351
511
  const online = this.getOnline();
352
- console.log("sendBegin params", params);
353
512
  const feeRate = String(params.feeRate ?? 1);
354
513
  const minConfirmations = String(params.minConfirmations ?? 1);
355
- const donation = false;
514
+ const donation = params.donation ?? false;
356
515
  let assetId = params.assetId;
357
516
  let amount = params.amount;
358
517
  let recipientId;
@@ -400,6 +559,37 @@ var RGBLibClient = class {
400
559
  );
401
560
  return psbt;
402
561
  }
562
+ /**
563
+ * Batch send: accepts an already-built recipientMap and calls sendBegin.
564
+ */
565
+ sendBeginBatch(params) {
566
+ const online = this.getOnline();
567
+ const feeRate = String(params.feeRate ?? 1);
568
+ const minConfirmations = String(params.minConfirmations ?? 1);
569
+ const donation = params.donation ?? true;
570
+ const { recipientMap } = params;
571
+ if (!recipientMap || typeof recipientMap !== "object") {
572
+ throw new ValidationError("recipientMap is required and must be a non-empty object", "recipientMap");
573
+ }
574
+ const assetIds = Object.keys(recipientMap);
575
+ if (assetIds.length === 0) {
576
+ throw new ValidationError("recipientMap must contain at least one asset id", "recipientMap");
577
+ }
578
+ for (const assetId of assetIds) {
579
+ const recipients = recipientMap[assetId];
580
+ if (!Array.isArray(recipients) || recipients.length === 0) {
581
+ throw new ValidationError(`recipientMap["${assetId}"] must be a non-empty array of recipients`, "recipientMap");
582
+ }
583
+ }
584
+ const psbt = this.wallet.sendBegin(
585
+ online,
586
+ recipientMap,
587
+ donation,
588
+ feeRate,
589
+ minConfirmations
590
+ );
591
+ return psbt;
592
+ }
403
593
  sendEnd(params) {
404
594
  const online = this.getOnline();
405
595
  const signedPsbt = params.signedPsbt;
@@ -503,7 +693,8 @@ var RGBLibClient = class {
503
693
  const assetId = null;
504
694
  const filter = [];
505
695
  const skipSync = false;
506
- this.wallet.refresh(online, assetId, filter, skipSync);
696
+ const result = this.wallet.refresh(online, assetId, filter, skipSync);
697
+ console.log("refresh state:", JSON.stringify(result, null, 2));
507
698
  }
508
699
  dropWallet() {
509
700
  if (this.online) {
@@ -546,16 +737,105 @@ var RGBLibClient = class {
546
737
  if (!params.password) {
547
738
  throw new ValidationError("password is required", "password");
548
739
  }
549
- if (!fs.existsSync(params.backupPath)) {
740
+ if (!fs2.existsSync(params.backupPath)) {
550
741
  throw new ValidationError(`Backup directory does not exist: ${params.backupPath}`, "backupPath");
551
742
  }
552
- const fullBackupPath = path.join(params.backupPath, `${this.masterFingerprint}.backup`);
743
+ const fullBackupPath = path3.join(params.backupPath, `${this.masterFingerprint}.backup`);
553
744
  this.wallet.backup(fullBackupPath, params.password);
554
745
  return {
555
746
  message: "Backup created successfully",
556
747
  backupPath: fullBackupPath
557
748
  };
558
749
  }
750
+ /**
751
+ * Ensure VSS backup support is available in the underlying rgb-lib bindings.
752
+ * Returns the wallet instance and rgb-lib namespace as `any` for internal use.
753
+ */
754
+ getVssBindingsOrThrow(methodName) {
755
+ const walletAny = this.wallet;
756
+ const anyLib = rgblib;
757
+ if (!walletAny || typeof anyLib.VssBackupClient !== "function" || typeof walletAny[methodName] !== "function") {
758
+ throw new WalletError("VSS backup is not available in the current rgb-lib build.");
759
+ }
760
+ return { walletAny, anyLib };
761
+ }
762
+ /**
763
+ * Configure VSS cloud backup for this wallet.
764
+ */
765
+ configureVssBackup(config) {
766
+ const walletAny = this.wallet;
767
+ if (!walletAny || typeof walletAny.configureVssBackup !== "function") {
768
+ throw new WalletError("VSS backup is not available in the current rgb-lib build.");
769
+ }
770
+ const mappedConfig = {
771
+ server_url: config.serverUrl,
772
+ store_id: config.storeId,
773
+ signing_key: config.signingKey
774
+ };
775
+ if (config.encryptionEnabled !== void 0) {
776
+ mappedConfig.encryptionEnabled = config.encryptionEnabled;
777
+ }
778
+ if (config.autoBackup !== void 0) {
779
+ mappedConfig.autoBackup = config.autoBackup;
780
+ }
781
+ if (config.backupMode !== void 0) {
782
+ mappedConfig.backupMode = config.backupMode;
783
+ }
784
+ walletAny.configureVssBackup(mappedConfig);
785
+ }
786
+ /**
787
+ * Disable automatic VSS backup for this wallet.
788
+ */
789
+ disableVssAutoBackup() {
790
+ const walletAny = this.wallet;
791
+ if (!walletAny || typeof walletAny.disableVssAutoBackup !== "function") {
792
+ throw new WalletError("VSS backup is not available in the current rgb-lib build.");
793
+ }
794
+ walletAny.disableVssAutoBackup();
795
+ }
796
+ /**
797
+ * Trigger a VSS backup immediately using a one-off client created from config.
798
+ * Returns the server version of the stored backup.
799
+ */
800
+ vssBackup(config) {
801
+ const { walletAny, anyLib } = this.getVssBindingsOrThrow("vssBackup");
802
+ const client = new anyLib.VssBackupClient({
803
+ server_url: config.serverUrl,
804
+ store_id: config.storeId,
805
+ signing_key: config.signingKey
806
+ });
807
+ try {
808
+ const version = walletAny.vssBackup(client);
809
+ return version;
810
+ } finally {
811
+ if (typeof client.drop === "function") {
812
+ client.drop();
813
+ }
814
+ }
815
+ }
816
+ /**
817
+ * Get VSS backup status information for this wallet using a one-off client.
818
+ */
819
+ vssBackupInfo(config) {
820
+ const { walletAny, anyLib } = this.getVssBindingsOrThrow("vssBackupInfo");
821
+ const client = new anyLib.VssBackupClient({
822
+ server_url: config.serverUrl,
823
+ store_id: config.storeId,
824
+ signing_key: config.signingKey
825
+ });
826
+ try {
827
+ const info = walletAny.vssBackupInfo(client);
828
+ return {
829
+ backupExists: Boolean(info.backupExists ?? info.backup_exists),
830
+ serverVersion: info.serverVersion ?? info.server_version ?? null,
831
+ backupRequired: Boolean(info.backupRequired ?? info.backup_required)
832
+ };
833
+ } finally {
834
+ if (typeof client.drop === "function") {
835
+ client.drop();
836
+ }
837
+ }
838
+ }
559
839
  /**
560
840
  * Cleanup resources
561
841
  */
@@ -932,8 +1212,8 @@ async function mnemonicToRoot(mnemonic, bitcoinNetwork) {
932
1212
  }
933
1213
  async function getAccountXpub(mnemonic, bitcoinNetwork, rgb) {
934
1214
  const root = await mnemonicToRoot(mnemonic, bitcoinNetwork);
935
- const path3 = accountDerivationPath(bitcoinNetwork, rgb);
936
- const acct = root.derivePath(path3);
1215
+ const path5 = accountDerivationPath(bitcoinNetwork, rgb);
1216
+ const acct = root.derivePath(path5);
937
1217
  return acct.neutered().toBase58();
938
1218
  }
939
1219
  async function getMasterXpriv(mnemonic, bitcoinNetwork) {
@@ -1057,6 +1337,27 @@ async function deriveKeysFromSeed(bitcoinNetwork = "regtest", seed) {
1057
1337
  throw new CryptoError("Failed to derive keys from seed", error);
1058
1338
  }
1059
1339
  }
1340
+ async function deriveKeysFromMnemonicOrSeed(bitcoinNetwork = "regtest", mnemonicOrSeed) {
1341
+ if (typeof mnemonicOrSeed === "string") {
1342
+ const trimmed = mnemonicOrSeed.trim();
1343
+ const words = trimmed.split(/\s+/);
1344
+ const isLikelyMnemonic = trimmed.includes(" ") && words.length >= 12 && words.length <= 24;
1345
+ if (isLikelyMnemonic) {
1346
+ try {
1347
+ return await deriveKeysFromMnemonic(bitcoinNetwork, trimmed);
1348
+ } catch (error) {
1349
+ if (error instanceof ValidationError) {
1350
+ return await deriveKeysFromSeed(bitcoinNetwork, trimmed);
1351
+ }
1352
+ throw error;
1353
+ }
1354
+ } else {
1355
+ return await deriveKeysFromSeed(bitcoinNetwork, trimmed);
1356
+ }
1357
+ } else {
1358
+ return await deriveKeysFromSeed(bitcoinNetwork, mnemonicOrSeed);
1359
+ }
1360
+ }
1060
1361
  async function restoreKeys(bitcoinNetwork = "regtest", mnemonic) {
1061
1362
  return deriveKeysFromMnemonic(bitcoinNetwork, mnemonic);
1062
1363
  }
@@ -1119,28 +1420,28 @@ async function accountXpubsFromMnemonic(bitcoinNetwork = "regtest", mnemonic) {
1119
1420
  }
1120
1421
 
1121
1422
  // src/crypto/signer.ts
1122
- function normalizePath(path3) {
1123
- if (typeof path3 === "string") {
1124
- if (path3.startsWith("m/m/")) {
1125
- return path3.replace(/^m\/m\//, "m/");
1126
- }
1127
- return path3;
1128
- } else if (Array.isArray(path3)) {
1129
- if (path3.length > 0 && path3[0] === 0 && path3.length > 1) {
1130
- const second = path3[1];
1423
+ function normalizePath(path5) {
1424
+ if (typeof path5 === "string") {
1425
+ if (path5.startsWith("m/m/")) {
1426
+ return path5.replace(/^m\/m\//, "m/");
1427
+ }
1428
+ return path5;
1429
+ } else if (Array.isArray(path5)) {
1430
+ if (path5.length > 0 && path5[0] === 0 && path5.length > 1) {
1431
+ const second = path5[1];
1131
1432
  if (typeof second === "number" && second >= 2147483648) {
1132
- return path3.slice(1);
1433
+ return path5.slice(1);
1133
1434
  }
1134
1435
  }
1135
- return path3;
1436
+ return path5;
1136
1437
  }
1137
- return path3;
1438
+ return path5;
1138
1439
  }
1139
- function pathToString(path3) {
1140
- if (typeof path3 === "string") {
1141
- return path3;
1142
- } else if (Array.isArray(path3)) {
1143
- return path3.map((p) => {
1440
+ function pathToString(path5) {
1441
+ if (typeof path5 === "string") {
1442
+ return path5;
1443
+ } else if (Array.isArray(path5)) {
1444
+ return path5.map((p) => {
1144
1445
  if (typeof p === "number") {
1145
1446
  return p >= 2147483648 ? `${p & 2147483647}'` : `${p}`;
1146
1447
  }
@@ -1449,6 +1750,14 @@ async function estimatePsbt(psbtBase64) {
1449
1750
  throw new ValidationError("Invalid PSBT provided", "psbt");
1450
1751
  }
1451
1752
  }
1753
+ var VSS_SIGNING_KEY_DOMAIN = "rgb-lib-vss-backup-encryption-v1";
1754
+ function deriveVssSigningKeyFromMnemonic(mnemonic) {
1755
+ validateMnemonic(mnemonic, "mnemonic");
1756
+ const keyBytes = new TextEncoder().encode(VSS_SIGNING_KEY_DOMAIN);
1757
+ const messageBytes = new TextEncoder().encode(mnemonic.trim());
1758
+ const digest = hmac(sha256$1, keyBytes, messageBytes);
1759
+ return Array.from(digest).map((b) => b.toString(16).padStart(2, "0")).join("");
1760
+ }
1452
1761
  var restoreFromBackup = (params) => {
1453
1762
  const {
1454
1763
  backupFilePath,
@@ -1492,7 +1801,7 @@ var WalletManager = class {
1492
1801
  this.mnemonic = params.mnemonic ?? null;
1493
1802
  this.xpub = params.xpub ?? null;
1494
1803
  this.masterFingerprint = params.masterFingerprint;
1495
- this.dataDir = params.dataDir ?? path__default.join(os.tmpdir(), "rgb-wallet", this.masterFingerprint);
1804
+ this.dataDir = params.dataDir ?? path3__default.join(process.cwd(), ".rgb-wallet", this.network, this.masterFingerprint);
1496
1805
  this.client = new RGBLibClient({
1497
1806
  xpubVan: params.xpubVan,
1498
1807
  xpubCol: params.xpubCol,
@@ -1503,6 +1812,12 @@ var WalletManager = class {
1503
1812
  dataDir: params.dataDir ?? this.dataDir
1504
1813
  });
1505
1814
  }
1815
+ async initialize() {
1816
+ console.log("initializing is not reqire");
1817
+ }
1818
+ async goOnline(indexerUrl, skipConsistencyCheck) {
1819
+ this.client.getOnline();
1820
+ }
1506
1821
  /**
1507
1822
  * Get wallet's extended public keys
1508
1823
  */
@@ -1523,7 +1838,7 @@ var WalletManager = class {
1523
1838
  * Clears mnemonic and seed from memory
1524
1839
  * Idempotent - safe to call multiple times
1525
1840
  */
1526
- dispose() {
1841
+ async dispose() {
1527
1842
  if (this.disposed) {
1528
1843
  return;
1529
1844
  }
@@ -1555,73 +1870,160 @@ var WalletManager = class {
1555
1870
  registerWallet() {
1556
1871
  return this.client.registerWallet();
1557
1872
  }
1558
- getBtcBalance() {
1873
+ async getBtcBalance() {
1559
1874
  return this.client.getBtcBalance();
1560
1875
  }
1561
- getAddress() {
1876
+ async getAddress() {
1562
1877
  return this.client.getAddress();
1563
1878
  }
1564
- listUnspents() {
1565
- return this.client.listUnspents();
1566
- }
1567
- listAssets() {
1568
- return this.client.listAssets();
1569
- }
1570
- getAssetBalance(asset_id) {
1571
- return this.client.getAssetBalance(asset_id);
1879
+ async listUnspents() {
1880
+ const unspents = this.client.listUnspents();
1881
+ return unspents.map((unspent) => ({
1882
+ utxo: {
1883
+ ...unspent.utxo,
1884
+ exists: unspent.utxo.exists ?? true
1885
+ },
1886
+ rgbAllocations: unspent.rgbAllocations.map((allocation) => {
1887
+ const assignmentKeys = Object.keys(allocation.assignment);
1888
+ const assignmentType = assignmentKeys[0];
1889
+ const assignment = {
1890
+ type: assignmentType ?? "Any",
1891
+ amount: assignmentType && allocation.assignment[assignmentType] ? Number(allocation.assignment[assignmentType]) : void 0
1892
+ };
1893
+ return {
1894
+ assetId: allocation.assetId,
1895
+ assignment,
1896
+ settled: allocation.settled
1897
+ };
1898
+ }),
1899
+ pendingBlinded: unspent.pendingBlinded ?? 0
1900
+ }));
1901
+ }
1902
+ async listAssets() {
1903
+ const assets = this.client.listAssets();
1904
+ return assets;
1905
+ }
1906
+ async getAssetBalance(asset_id) {
1907
+ const balance = this.client.getAssetBalance(asset_id);
1908
+ return {
1909
+ settled: balance.settled ?? 0,
1910
+ future: balance.future ?? 0,
1911
+ spendable: balance.spendable ?? 0,
1912
+ offchainOutbound: balance.offchainOutbound ?? 0,
1913
+ offchainInbound: balance.offchainInbound ?? 0
1914
+ };
1572
1915
  }
1573
- createUtxosBegin(params) {
1916
+ async createUtxosBegin(params) {
1574
1917
  return this.client.createUtxosBegin(params);
1575
1918
  }
1576
- createUtxosEnd(params) {
1919
+ async createUtxosEnd(params) {
1577
1920
  return this.client.createUtxosEnd(params);
1578
1921
  }
1579
- sendBegin(params) {
1922
+ async sendBegin(params) {
1580
1923
  return this.client.sendBegin(params);
1581
1924
  }
1582
- sendEnd(params) {
1925
+ /**
1926
+ * Batch send begin: accepts already-built recipientMap.
1927
+ * Returns unsigned PSBT (use signPsbt then sendEnd to complete).
1928
+ */
1929
+ async sendBeginBatch(params) {
1930
+ return this.client.sendBeginBatch(params);
1931
+ }
1932
+ /**
1933
+ * Complete batch send: sendBeginBatch → sign PSBT → sendEnd.
1934
+ */
1935
+ async sendBatch(params, mnemonic) {
1936
+ this.ensureNotDisposed();
1937
+ const psbt = await this.sendBeginBatch(params);
1938
+ const signedPsbt = await this.signPsbt(psbt, mnemonic);
1939
+ return await this.sendEnd({ signedPsbt });
1940
+ }
1941
+ async sendEnd(params) {
1583
1942
  return this.client.sendEnd(params);
1584
1943
  }
1585
- sendBtcBegin(params) {
1944
+ async sendBtcBegin(params) {
1586
1945
  return this.client.sendBtcBegin(params);
1587
1946
  }
1588
- sendBtcEnd(params) {
1947
+ async sendBtcEnd(params) {
1589
1948
  return this.client.sendBtcEnd(params);
1590
1949
  }
1591
- estimateFeeRate(blocks) {
1950
+ async estimateFeeRate(blocks) {
1592
1951
  if (!Number.isFinite(blocks)) {
1593
1952
  throw new ValidationError("blocks must be a finite number", "blocks");
1594
1953
  }
1595
1954
  if (!Number.isInteger(blocks) || blocks <= 0) {
1596
1955
  throw new ValidationError("blocks must be a positive integer", "blocks");
1597
1956
  }
1598
- return this.client.getFeeEstimation({ blocks });
1957
+ const feeEstimation = await this.client.getFeeEstimation({ blocks });
1958
+ return feeEstimation;
1599
1959
  }
1600
1960
  async estimateFee(psbtBase64) {
1601
1961
  return await estimatePsbt(psbtBase64);
1602
1962
  }
1603
1963
  async sendBtc(params) {
1604
1964
  this.ensureNotDisposed();
1605
- const psbt = this.sendBtcBegin(params);
1965
+ const psbt = await this.sendBtcBegin(params);
1606
1966
  const signed = await this.signPsbt(psbt);
1607
- return this.sendBtcEnd({ signedPsbt: signed });
1967
+ return await this.sendBtcEnd({ signedPsbt: signed });
1608
1968
  }
1609
- blindReceive(params) {
1610
- return this.client.blindReceive(params);
1969
+ async blindReceive(params) {
1970
+ const invoice = await this.client.blindReceive({
1971
+ ...params,
1972
+ assetId: params.assetId ?? "",
1973
+ amount: params.amount ?? 0
1974
+ });
1975
+ return {
1976
+ invoice: invoice.invoice,
1977
+ recipientId: invoice.recipientId,
1978
+ expirationTimestamp: invoice.expirationTimestamp ?? null,
1979
+ batchTransferIdx: invoice.batchTransferIdx
1980
+ };
1611
1981
  }
1612
- witnessReceive(params) {
1613
- return this.client.witnessReceive(params);
1982
+ async witnessReceive(params) {
1983
+ const invoice = await this.client.witnessReceive({
1984
+ ...params,
1985
+ assetId: params.assetId ?? "",
1986
+ amount: params.amount ?? 0
1987
+ });
1988
+ return {
1989
+ invoice: invoice.invoice,
1990
+ recipientId: invoice.recipientId,
1991
+ expirationTimestamp: invoice.expirationTimestamp ?? null,
1992
+ batchTransferIdx: invoice.batchTransferIdx
1993
+ };
1614
1994
  }
1615
- issueAssetNia(params) {
1616
- return this.client.issueAssetNia(params);
1995
+ async decodeRGBInvoice(params) {
1996
+ const invoiceData = await this.client.decodeRGBInvoice(params);
1997
+ const assignmentKeys = Object.keys(invoiceData.assignment);
1998
+ const assignmentType = assignmentKeys[0];
1999
+ const assignment = {
2000
+ type: assignmentType ?? "Any",
2001
+ amount: assignmentType && invoiceData.assignment[assignmentType] ? Number(invoiceData.assignment[assignmentType]) : void 0
2002
+ };
2003
+ return {
2004
+ invoice: params.invoice,
2005
+ recipientId: invoiceData.recipientId,
2006
+ assetSchema: invoiceData.assetSchema,
2007
+ assetId: invoiceData.assetId,
2008
+ network: invoiceData.network,
2009
+ assignment,
2010
+ assignmentName: invoiceData.assignmentName,
2011
+ expirationTimestamp: invoiceData.expirationTimestamp ?? null,
2012
+ transportEndpoints: invoiceData.transportEndpoints
2013
+ };
1617
2014
  }
1618
- issueAssetIfa(params) {
1619
- return this.client.issueAssetIfa(params);
2015
+ async issueAssetNia(params) {
2016
+ const asset = await this.client.issueAssetNia(params);
2017
+ return asset;
1620
2018
  }
1621
- inflateBegin(params) {
2019
+ async issueAssetIfa(params) {
2020
+ const asset = await this.client.issueAssetIfa(params);
2021
+ return asset;
2022
+ }
2023
+ async inflateBegin(params) {
1622
2024
  return this.client.inflateBegin(params);
1623
2025
  }
1624
- inflateEnd(params) {
2026
+ async inflateEnd(params) {
1625
2027
  return this.client.inflateEnd(params);
1626
2028
  }
1627
2029
  /**
@@ -1637,24 +2039,51 @@ var WalletManager = class {
1637
2039
  signedPsbt
1638
2040
  });
1639
2041
  }
1640
- refreshWallet() {
2042
+ async refreshWallet() {
1641
2043
  this.client.refreshWallet();
1642
2044
  }
1643
- listTransactions() {
1644
- return this.client.listTransactions();
2045
+ async listTransactions() {
2046
+ const transactions = this.client.listTransactions();
2047
+ return transactions;
1645
2048
  }
1646
- listTransfers(asset_id) {
1647
- return this.client.listTransfers(asset_id);
2049
+ async listTransfers(asset_id) {
2050
+ const transfers = this.client.listTransfers(asset_id);
2051
+ return transfers;
1648
2052
  }
1649
- failTransfers(params) {
2053
+ async failTransfers(params) {
1650
2054
  return this.client.failTransfers(params);
1651
2055
  }
1652
- decodeRGBInvoice(params) {
1653
- return this.client.decodeRGBInvoice(params);
1654
- }
1655
- createBackup(params) {
2056
+ async createBackup(params) {
1656
2057
  return this.client.createBackup(params);
1657
2058
  }
2059
+ /**
2060
+ * Configure VSS cloud backup for this wallet.
2061
+ */
2062
+ async configureVssBackup(config) {
2063
+ this.ensureNotDisposed();
2064
+ this.client.configureVssBackup(config);
2065
+ }
2066
+ /**
2067
+ * Disable automatic VSS backup.
2068
+ */
2069
+ async disableVssAutoBackup() {
2070
+ this.ensureNotDisposed();
2071
+ this.client.disableVssAutoBackup();
2072
+ }
2073
+ /**
2074
+ * Trigger a VSS backup immediately and return the server version.
2075
+ */
2076
+ async vssBackup(config) {
2077
+ this.ensureNotDisposed();
2078
+ return this.client.vssBackup(config);
2079
+ }
2080
+ /**
2081
+ * Get VSS backup info for this wallet.
2082
+ */
2083
+ async vssBackupInfo(config) {
2084
+ this.ensureNotDisposed();
2085
+ return this.client.vssBackupInfo(config);
2086
+ }
1658
2087
  /**
1659
2088
  * Sign a PSBT using the wallet's mnemonic or a provided mnemonic
1660
2089
  * @param psbt - Base64 encoded PSBT
@@ -1680,16 +2109,15 @@ var WalletManager = class {
1680
2109
  this.ensureNotDisposed();
1681
2110
  const psbt = await this.sendBegin(invoiceTransfer);
1682
2111
  const signedPsbt = await this.signPsbt(psbt, mnemonic);
1683
- console.log("send signedPsbt", signedPsbt);
1684
2112
  return await this.sendEnd({ signedPsbt });
1685
2113
  }
1686
2114
  async createUtxos({ upTo, num, size, feeRate }) {
1687
2115
  this.ensureNotDisposed();
1688
- const psbt = this.createUtxosBegin({ upTo, num, size, feeRate });
2116
+ const psbt = await this.createUtxosBegin({ upTo, num, size, feeRate });
1689
2117
  const signedPsbt = await this.signPsbt(psbt);
1690
2118
  return this.createUtxosEnd({ signedPsbt });
1691
2119
  }
1692
- syncWallet() {
2120
+ async syncWallet() {
1693
2121
  this.client.syncWallet();
1694
2122
  }
1695
2123
  async signMessage(message) {
@@ -1734,33 +2162,1081 @@ var wallet = new Proxy({}, {
1734
2162
  }
1735
2163
  });
1736
2164
 
1737
- // src/types/rgb-model.ts
1738
- var TransactionType = /* @__PURE__ */ ((TransactionType2) => {
1739
- TransactionType2[TransactionType2["RGB_SEND"] = 0] = "RGB_SEND";
1740
- TransactionType2[TransactionType2["DRAIN"] = 1] = "DRAIN";
1741
- TransactionType2[TransactionType2["CREATE_UTXOS"] = 2] = "CREATE_UTXOS";
1742
- TransactionType2[TransactionType2["USER"] = 3] = "USER";
1743
- return TransactionType2;
1744
- })(TransactionType || {});
1745
- var TransferStatus = /* @__PURE__ */ ((TransferStatus2) => {
1746
- TransferStatus2[TransferStatus2["WAITING_COUNTERPARTY"] = 0] = "WAITING_COUNTERPARTY";
1747
- TransferStatus2[TransferStatus2["WAITING_CONFIRMATIONS"] = 1] = "WAITING_CONFIRMATIONS";
1748
- TransferStatus2[TransferStatus2["SETTLED"] = 2] = "SETTLED";
1749
- TransferStatus2[TransferStatus2["FAILED"] = 3] = "FAILED";
1750
- return TransferStatus2;
1751
- })(TransferStatus || {});
1752
- var AssetIface = /* @__PURE__ */ ((AssetIface2) => {
1753
- AssetIface2["RGB20"] = "RGB20";
1754
- AssetIface2["RGB21"] = "RGB21";
1755
- AssetIface2["RGB25"] = "RGB25";
1756
- return AssetIface2;
1757
- })(AssetIface || {});
1758
- var AssetSchema = /* @__PURE__ */ ((AssetSchema2) => {
1759
- AssetSchema2["Nia"] = "Nia";
1760
- AssetSchema2["Uda"] = "Uda";
1761
- AssetSchema2["Cfa"] = "Cfa";
1762
- return AssetSchema2;
1763
- })(AssetSchema || {});
2165
+ // src/utexo/utexo-protocol.ts
2166
+ var LightningProtocol = class {
2167
+ async createLightningInvoice(params) {
2168
+ throw new Error("createLightningInvoice not implemented");
2169
+ }
2170
+ async getLightningReceiveRequest(id) {
2171
+ throw new Error("getLightningReceiveRequest not implemented");
2172
+ }
2173
+ async getLightningSendRequest(id) {
2174
+ throw new Error("getLightningSendRequest not implemented");
2175
+ }
2176
+ async getLightningSendFeeEstimate(params) {
2177
+ throw new Error("getLightningSendFeeEstimate not implemented");
2178
+ }
2179
+ async payLightningInvoiceBegin(params) {
2180
+ throw new Error("payLightningInvoiceBegin not implemented");
2181
+ }
2182
+ async payLightningInvoiceEnd(params) {
2183
+ throw new Error("payLightningInvoiceEnd not implemented");
2184
+ }
2185
+ async payLightningInvoice(params, mnemonic) {
2186
+ throw new Error("payLightningInvoice not implemented");
2187
+ }
2188
+ async listLightningPayments() {
2189
+ throw new Error("listLightningPayments not implemented");
2190
+ }
2191
+ };
2192
+ var OnchainProtocol = class {
2193
+ async onchainReceive(params) {
2194
+ throw new Error("onchainReceive not implemented");
2195
+ }
2196
+ async onchainSendBegin(params) {
2197
+ throw new Error("onchainSendBegin not implemented");
2198
+ }
2199
+ async onchainSendEnd(params) {
2200
+ throw new Error("onchainSendEnd not implemented");
2201
+ }
2202
+ async onchainSend(params, mnemonic) {
2203
+ throw new Error("onchainSend not implemented");
2204
+ }
2205
+ async getOnchainSendStatus(send_id) {
2206
+ throw new Error("getOnchainSendStatus not implemented");
2207
+ }
2208
+ async listOnchainTransfers(asset_id) {
2209
+ throw new Error("listOnchainTransfers not implemented");
2210
+ }
2211
+ };
2212
+ var UTEXOProtocol = class extends LightningProtocol {
2213
+ constructor() {
2214
+ super(...arguments);
2215
+ this.onchainProtocol = new OnchainProtocol();
2216
+ }
2217
+ async onchainReceive(params) {
2218
+ return this.onchainProtocol.onchainReceive(params);
2219
+ }
2220
+ async onchainSendBegin(params) {
2221
+ return this.onchainProtocol.onchainSendBegin(params);
2222
+ }
2223
+ async onchainSendEnd(params) {
2224
+ return this.onchainProtocol.onchainSendEnd(params);
2225
+ }
2226
+ async onchainSend(params, mnemonic) {
2227
+ return this.onchainProtocol.onchainSend(params, mnemonic);
2228
+ }
2229
+ async getOnchainSendStatus(send_id) {
2230
+ return this.onchainProtocol.getOnchainSendStatus(send_id);
2231
+ }
2232
+ async listOnchainTransfers(asset_id) {
2233
+ return this.onchainProtocol.listOnchainTransfers(asset_id);
2234
+ }
2235
+ };
2236
+
2237
+ // src/utexo/config/gateway.ts
2238
+ var DEFAULT_GATEWAY_BASE_URLS = {
2239
+ mainnet: "https://gateway.utexo.tricorn.network/",
2240
+ testnet: "https://dev.gateway.utexo.tricorn.network/"
2241
+ };
2242
+
2243
+ // src/utexo/bridge/types.ts
2244
+ var TransferStatuses = /* @__PURE__ */ ((TransferStatuses2) => {
2245
+ TransferStatuses2[TransferStatuses2["Unspecified"] = 0] = "Unspecified";
2246
+ TransferStatuses2[TransferStatuses2["Confirming"] = 1] = "Confirming";
2247
+ TransferStatuses2[TransferStatuses2["Canceled"] = 2] = "Canceled";
2248
+ TransferStatuses2[TransferStatuses2["Finished"] = 3] = "Finished";
2249
+ TransferStatuses2[TransferStatuses2["Waiting"] = 4] = "Waiting";
2250
+ TransferStatuses2[TransferStatuses2["Cancelling"] = 5] = "Cancelling";
2251
+ TransferStatuses2[TransferStatuses2["Failed"] = 6] = "Failed";
2252
+ TransferStatuses2[TransferStatuses2["Fetching"] = 7] = "Fetching";
2253
+ return TransferStatuses2;
2254
+ })(TransferStatuses || {});
2255
+
2256
+ // src/utexo/bridge/api.ts
2257
+ var encodeTransferStatus = (transferStatus) => {
2258
+ const textEncoder = new TextEncoder();
2259
+ return textEncoder.encode(transferStatus.toString())[0];
2260
+ };
2261
+ var UtexoBridgeApiClient = class {
2262
+ /**
2263
+ * Creates a new UtexoBridgeApiClient instance
2264
+ *
2265
+ * @param axiosInstance - Axios instance to use for HTTP requests (required)
2266
+ * @param basePath - Base path for API endpoints (defaults to '/v1/utexo/bridge')
2267
+ *
2268
+ * @example
2269
+ * ```typescript
2270
+ * import axios from 'axios';
2271
+ * import { UtexoBridgeApiClient } from './utexoBridge';
2272
+ *
2273
+ * const axiosInstance = axios.create({
2274
+ * baseURL: 'https://api.example.com'
2275
+ * });
2276
+ *
2277
+ * const client = new UtexoBridgeApiClient(axiosInstance);
2278
+ * ```
2279
+ */
2280
+ constructor(axiosInstance, basePath = "/v1/utexo/bridge") {
2281
+ this.axios = axiosInstance;
2282
+ this.basePath = basePath;
2283
+ }
2284
+ /**
2285
+ * Gets bridge-in signature for a transfer
2286
+ *
2287
+ * @param request - Bridge-in signature request data
2288
+ * @returns Promise resolving to bridge-in signature response
2289
+ * @throws {ApiError} If the request fails
2290
+ */
2291
+ async getBridgeInSignature(request) {
2292
+ try {
2293
+ const { data } = await this.axios.post(
2294
+ `${this.basePath}/bridge-in-signature`,
2295
+ request
2296
+ );
2297
+ return data;
2298
+ } catch (error) {
2299
+ const responseData = error.response?.data;
2300
+ if (responseData !== void 0) {
2301
+ const message = typeof responseData === "string" ? responseData : JSON.stringify(responseData);
2302
+ throw new Error(message);
2303
+ }
2304
+ throw error;
2305
+ }
2306
+ }
2307
+ /**
2308
+ * Submits a signed transaction to the blockchain
2309
+ *
2310
+ * @param request - Submit transaction request data
2311
+ * @returns Promise resolving to transaction hash
2312
+ * @throws {ApiError} If the request fails
2313
+ */
2314
+ async submitTransaction(request) {
2315
+ const { data } = await this.axios.post(
2316
+ `${this.basePath}/submit-transaction`,
2317
+ request
2318
+ );
2319
+ return data.txHash;
2320
+ }
2321
+ /**
2322
+ * Verifies a bridge-in transaction after it has been sent
2323
+ *
2324
+ * @param request - Verify bridge-in request data
2325
+ * @returns Promise that resolves when verification is complete
2326
+ * @throws {ApiError} If the request fails
2327
+ */
2328
+ async verifyBridgeIn(request) {
2329
+ await this.axios.post(`${this.basePath}/verify-bridge-in`, request);
2330
+ }
2331
+ /**
2332
+ * Gets receiver invoice by transfer ID and network ID
2333
+ *
2334
+ * @param transferId - Transfer ID
2335
+ * @param networkId - Network ID
2336
+ * @returns Promise resolving to invoice string
2337
+ * @throws {ApiError} If the request fails
2338
+ */
2339
+ async getReceiverInvoice(transferId, networkId) {
2340
+ const { data } = await this.axios.get(
2341
+ `${this.basePath}/receiver-invoice/${transferId}/${networkId}`
2342
+ );
2343
+ return data.invoice;
2344
+ }
2345
+ async getWithdrawTransfer(invoice, networkId) {
2346
+ const { data } = await this.axios.get(
2347
+ `${this.basePath}/transfers/history`,
2348
+ {
2349
+ params: {
2350
+ "network_id": String(networkId),
2351
+ "offset": String(0),
2352
+ "limit": String(10),
2353
+ "address": "rgb-address"
2354
+ }
2355
+ }
2356
+ );
2357
+ if (data.transfers.length === 0) {
2358
+ return null;
2359
+ }
2360
+ const withdrawTransfer = data.transfers.map((transfer) => ({ ...transfer, status: TransferStatuses[encodeTransferStatus(transfer.status)] })).find((transfer) => transfer.recipient.address === invoice);
2361
+ if (!withdrawTransfer) {
2362
+ return null;
2363
+ }
2364
+ return withdrawTransfer;
2365
+ }
2366
+ /**
2367
+ * Gets transfer information by mainnet invoice
2368
+ *
2369
+ * @param mainnetInvoice - Mainnet invoice string
2370
+ * @param networkId - Network ID
2371
+ * @returns Promise resolving to transfer information
2372
+ * @throws {ApiError} If the request fails
2373
+ */
2374
+ async getTransferByMainnetInvoice(mainnetInvoice, networkId) {
2375
+ try {
2376
+ const { data } = await this.axios.get(
2377
+ `${this.basePath}/transfer-by-mainnet-invoice`,
2378
+ {
2379
+ params: {
2380
+ mainnet_invoice: mainnetInvoice,
2381
+ network_id: networkId
2382
+ }
2383
+ }
2384
+ );
2385
+ if (data) {
2386
+ return { ...data, status: TransferStatuses[encodeTransferStatus(data.status)] };
2387
+ }
2388
+ return data;
2389
+ } catch (error) {
2390
+ console.log("Mainnet invoice not found");
2391
+ return null;
2392
+ }
2393
+ }
2394
+ };
2395
+ function getBridgeAPI(network = "mainnet") {
2396
+ const axiosInstance = axios.create({
2397
+ baseURL: DEFAULT_GATEWAY_BASE_URLS[network]
2398
+ });
2399
+ return new UtexoBridgeApiClient(axiosInstance);
2400
+ }
2401
+
2402
+ // src/utexo/utils/helpers.ts
2403
+ var UTXO_PATH_INDEX = 2;
2404
+ function toUnitsNumber(value, precision) {
2405
+ const s = String(value).trim();
2406
+ const neg = s.startsWith("-");
2407
+ const [iRaw, fRaw = ""] = (neg ? s.slice(1) : s).split(".");
2408
+ const frac = (fRaw + "0".repeat(precision)).slice(0, precision);
2409
+ const unitsStr = (iRaw || "0") + frac;
2410
+ const units = Number(unitsStr);
2411
+ if (!Number.isSafeInteger(units)) {
2412
+ throw new Error(
2413
+ `Amount exceeds MAX_SAFE_INTEGER. Use BigInt instead. got=${unitsStr}`
2414
+ );
2415
+ }
2416
+ return neg ? -units : units;
2417
+ }
2418
+ function fromUnitsNumber(units, precision) {
2419
+ const neg = units < 0;
2420
+ const base = 10 ** precision;
2421
+ const value = Math.abs(units) / base;
2422
+ return neg ? -value : value;
2423
+ }
2424
+ function decodeBridgeInvoice(hexInvoice) {
2425
+ const hex = hexInvoice.startsWith("0x") ? hexInvoice.slice(UTXO_PATH_INDEX) : hexInvoice;
2426
+ return Buffer.from(hex, "hex").toString("utf-8");
2427
+ }
2428
+
2429
+ // src/utexo/config/vss.ts
2430
+ var DEFAULT_VSS_SERVER_URL = "https://vss-server.utexo.com/vss";
2431
+ function getVssConfigs(config) {
2432
+ const base = { ...config };
2433
+ return {
2434
+ layer1: { ...base, storeId: `${config.storeId}_layer1` },
2435
+ utexo: { ...base, storeId: `${config.storeId}_utexo` }
2436
+ };
2437
+ }
2438
+ var BACKUP_FILE_SUFFIX = ".backup";
2439
+ var LAYER1_BACKUP_SUFFIX = "_layer1.backup";
2440
+ var UTEXO_BACKUP_SUFFIX = "_utexo.backup";
2441
+ var UTEXO_BACKUP_TMP_LAYER1 = ".layer1";
2442
+ var UTEXO_BACKUP_TMP_UTEXO = ".utexo";
2443
+ function getBackupStoreId(masterFingerprint) {
2444
+ return `wallet_${masterFingerprint}`;
2445
+ }
2446
+ function prepareUtxoBackupDirs(backupPath, masterFingerprint) {
2447
+ const storeId = getBackupStoreId(masterFingerprint);
2448
+ if (!fs2__default.existsSync(backupPath)) {
2449
+ fs2__default.mkdirSync(backupPath, { recursive: true });
2450
+ }
2451
+ const layer1TmpDir = path3__default.join(backupPath, UTEXO_BACKUP_TMP_LAYER1);
2452
+ const utexoTmpDir = path3__default.join(backupPath, UTEXO_BACKUP_TMP_UTEXO);
2453
+ fs2__default.mkdirSync(layer1TmpDir, { recursive: true });
2454
+ fs2__default.mkdirSync(utexoTmpDir, { recursive: true });
2455
+ return {
2456
+ storeId,
2457
+ layer1TmpDir,
2458
+ utexoTmpDir,
2459
+ layer1FinalPath: path3__default.join(backupPath, `${storeId}_layer1${BACKUP_FILE_SUFFIX}`),
2460
+ utexoFinalPath: path3__default.join(backupPath, `${storeId}_utexo${BACKUP_FILE_SUFFIX}`)
2461
+ };
2462
+ }
2463
+ function finalizeUtxoBackupPaths(params) {
2464
+ const { layer1BackupPath, utexoBackupPath, layer1FinalPath, utexoFinalPath, layer1TmpDir, utexoTmpDir } = params;
2465
+ fs2__default.renameSync(layer1BackupPath, layer1FinalPath);
2466
+ fs2__default.renameSync(utexoBackupPath, utexoFinalPath);
2467
+ fs2__default.rmdirSync(layer1TmpDir);
2468
+ fs2__default.rmdirSync(utexoTmpDir);
2469
+ }
2470
+ async function buildVssConfigFromMnemonic(mnemonic, serverUrl, networkPreset = "testnet") {
2471
+ const keys = await deriveKeysFromMnemonic(networkPreset, mnemonic.trim());
2472
+ return {
2473
+ serverUrl,
2474
+ storeId: `wallet_${keys.masterFingerprint}`,
2475
+ signingKey: deriveVssSigningKeyFromMnemonic(mnemonic.trim()),
2476
+ backupMode: "Blocking"
2477
+ };
2478
+ }
2479
+ async function restoreUtxoWalletFromVss(params) {
2480
+ const { mnemonic, targetDir, config: providedConfig, networkPreset = "testnet", vssServerUrl } = params;
2481
+ if (!mnemonic || !mnemonic.trim()) {
2482
+ throw new ValidationError("mnemonic is required", "mnemonic");
2483
+ }
2484
+ if (!targetDir) {
2485
+ throw new ValidationError("targetDir is required", "targetDir");
2486
+ }
2487
+ const serverUrl = vssServerUrl ?? DEFAULT_VSS_SERVER_URL;
2488
+ const config = providedConfig ?? await buildVssConfigFromMnemonic(mnemonic.trim(), serverUrl, networkPreset);
2489
+ const presetConfig = getUtxoNetworkConfig(networkPreset);
2490
+ const layer1Network = String(presetConfig.networkMap.mainnet);
2491
+ const utexoNetwork = String(presetConfig.networkMap.utexo);
2492
+ const masterFingerprint = config.storeId.replace(/^wallet_/, "") || config.storeId;
2493
+ const layer1Config = { ...config, storeId: `${config.storeId}_layer1` };
2494
+ const utexoConfig = { ...config, storeId: `${config.storeId}_utexo` };
2495
+ const { walletPath: layer1Path } = restoreFromVss({
2496
+ config: layer1Config,
2497
+ targetDir: path3__default.join(targetDir, layer1Network, masterFingerprint)
2498
+ });
2499
+ const { walletPath: utexoPath } = restoreFromVss({
2500
+ config: utexoConfig,
2501
+ targetDir: path3__default.join(targetDir, utexoNetwork, masterFingerprint)
2502
+ });
2503
+ return { layer1Path, utexoPath, targetDir };
2504
+ }
2505
+ function restoreUtxoWalletFromBackup(params) {
2506
+ const { backupPath, password, targetDir, networkPreset = "testnet" } = params;
2507
+ if (!backupPath || !password || !targetDir) {
2508
+ throw new ValidationError("backupPath, password, and targetDir are required", "restoreUtxoWalletFromBackup");
2509
+ }
2510
+ if (!fs2__default.existsSync(backupPath) || !fs2__default.statSync(backupPath).isDirectory()) {
2511
+ throw new ValidationError("backupPath must be an existing directory", "backupPath");
2512
+ }
2513
+ const files = fs2__default.readdirSync(backupPath);
2514
+ const layer1File = files.find((f) => f.endsWith(LAYER1_BACKUP_SUFFIX));
2515
+ const utexoFile = files.find((f) => f.endsWith(UTEXO_BACKUP_SUFFIX));
2516
+ if (!layer1File || !utexoFile) {
2517
+ throw new ValidationError(
2518
+ `backupPath must contain wallet_<fp>_layer1.backup and wallet_<fp>_utexo.backup (from createBackup)`,
2519
+ "backupPath"
2520
+ );
2521
+ }
2522
+ const masterFingerprint = layer1File.slice(0, -LAYER1_BACKUP_SUFFIX.length).replace(/^wallet_/, "");
2523
+ const expectedUtexoFile = `wallet_${masterFingerprint}${UTEXO_BACKUP_SUFFIX}`;
2524
+ if (utexoFile !== expectedUtexoFile) {
2525
+ throw new ValidationError(
2526
+ `Layer1 and utexo backup filenames must share the same wallet id (expected ${expectedUtexoFile})`,
2527
+ "backupPath"
2528
+ );
2529
+ }
2530
+ const layer1BackupFile = path3__default.join(backupPath, layer1File);
2531
+ const utexoBackupFile = path3__default.join(backupPath, utexoFile);
2532
+ if (!fs2__default.existsSync(layer1BackupFile) || !fs2__default.existsSync(utexoBackupFile)) {
2533
+ throw new ValidationError("Backup files not found", "backupPath");
2534
+ }
2535
+ const presetConfig = getUtxoNetworkConfig(networkPreset);
2536
+ const layer1Network = String(presetConfig.networkMap.mainnet);
2537
+ const utexoNetwork = String(presetConfig.networkMap.utexo);
2538
+ const layer1DataDir = path3__default.join(targetDir, layer1Network, masterFingerprint);
2539
+ const utexoDataDir = path3__default.join(targetDir, utexoNetwork, masterFingerprint);
2540
+ for (const dir of [layer1DataDir, utexoDataDir]) {
2541
+ if (!fs2__default.existsSync(path3__default.dirname(dir))) {
2542
+ fs2__default.mkdirSync(path3__default.dirname(dir), { recursive: true });
2543
+ }
2544
+ if (!fs2__default.existsSync(dir)) {
2545
+ fs2__default.mkdirSync(dir, { recursive: true });
2546
+ }
2547
+ }
2548
+ restoreWallet({ backupFilePath: layer1BackupFile, password, dataDir: layer1DataDir });
2549
+ restoreWallet({ backupFilePath: utexoBackupFile, password, dataDir: utexoDataDir });
2550
+ return {
2551
+ layer1Path: layer1DataDir,
2552
+ utexoPath: utexoDataDir,
2553
+ targetDir
2554
+ };
2555
+ }
2556
+
2557
+ // src/utexo/utexo-wallet.ts
2558
+ var UTEXOWallet = class extends UTEXOProtocol {
2559
+ /**
2560
+ * Creates a new UTEXOWallet instance
2561
+ * @param mnemonicOrSeed - Either a mnemonic phrase (string) or seed (Uint8Array)
2562
+ * @param options - Optional configuration options (defaults to { network: 'mainnet' })
2563
+ */
2564
+ constructor(mnemonicOrSeed, options = {}) {
2565
+ super();
2566
+ this.layer1Keys = null;
2567
+ this.utexoKeys = null;
2568
+ this.layer1RGBWallet = null;
2569
+ this.utexoRGBWallet = null;
2570
+ this.mnemonicOrSeed = mnemonicOrSeed;
2571
+ this.options = options;
2572
+ const preset = options.network ?? "testnet";
2573
+ const networkConfig = getUtxoNetworkConfig(preset);
2574
+ this.networkMap = networkConfig.networkMap;
2575
+ this.networkIdMap = networkConfig.networkIdMap;
2576
+ this.bridge = getBridgeAPI(preset);
2577
+ }
2578
+ async initialize() {
2579
+ this.layer1Keys = await this.derivePublicKeys(this.networkMap.mainnet);
2580
+ this.utexoKeys = await this.derivePublicKeys(this.networkMap.utexo);
2581
+ const fp = this.utexoKeys.masterFingerprint;
2582
+ const dataDir = this.options.dataDir;
2583
+ this.utexoRGBWallet = new WalletManager({
2584
+ xpubVan: this.utexoKeys.accountXpubVanilla,
2585
+ xpubCol: this.utexoKeys.accountXpubColored,
2586
+ masterFingerprint: this.utexoKeys.masterFingerprint,
2587
+ network: this.networkMap.utexo,
2588
+ mnemonic: this.mnemonicOrSeed,
2589
+ dataDir: dataDir ? path3__default.join(dataDir, String(this.networkMap.utexo), fp) : void 0
2590
+ });
2591
+ this.layer1RGBWallet = new WalletManager({
2592
+ xpubVan: this.layer1Keys.accountXpubVanilla,
2593
+ xpubCol: this.layer1Keys.accountXpubVanilla,
2594
+ masterFingerprint: this.layer1Keys.masterFingerprint,
2595
+ network: this.networkMap.mainnet,
2596
+ mnemonic: this.mnemonicOrSeed,
2597
+ dataDir: dataDir ? path3__default.join(dataDir, String(this.networkMap.mainnet), fp) : void 0
2598
+ });
2599
+ }
2600
+ /**
2601
+ * Derive public keys from mnemonic or seed
2602
+ * @param network - BitcoinNetwork identifier
2603
+ * @returns Promise resolving to PublicKeys containing xpub, accountXpubVanilla, accountXpubColored, and masterFingerprint
2604
+ * @throws {ValidationError} If mnemonic is invalid
2605
+ */
2606
+ async derivePublicKeys(network) {
2607
+ const generatedKeys = await deriveKeysFromMnemonicOrSeed(network, this.mnemonicOrSeed);
2608
+ const { xpub, accountXpubVanilla, accountXpubColored, masterFingerprint } = generatedKeys;
2609
+ return { xpub, accountXpubVanilla, accountXpubColored, masterFingerprint };
2610
+ }
2611
+ async getPubKeys() {
2612
+ if (!this.layer1Keys) {
2613
+ throw new ValidationError("Public keys are not set", "publicKeys");
2614
+ }
2615
+ return this.layer1Keys;
2616
+ }
2617
+ /**
2618
+ * Guard method to ensure wallet is initialized
2619
+ * @throws {WalletError} if wallet is not initialized
2620
+ */
2621
+ ensureInitialized() {
2622
+ if (!this.utexoRGBWallet) {
2623
+ throw new WalletError("Wallet not initialized. Call initialize() first.");
2624
+ }
2625
+ }
2626
+ // ==========================================
2627
+ // IWalletManager Implementation
2628
+ // ==========================================
2629
+ async goOnline(indexerUrl, skipConsistencyCheck) {
2630
+ this.ensureInitialized();
2631
+ throw new Error("goOnline not implemented");
2632
+ }
2633
+ getXpub() {
2634
+ this.ensureInitialized();
2635
+ return this.utexoRGBWallet.getXpub();
2636
+ }
2637
+ getNetwork() {
2638
+ this.ensureInitialized();
2639
+ return this.utexoRGBWallet.getNetwork();
2640
+ }
2641
+ async dispose() {
2642
+ if (this.layer1RGBWallet) {
2643
+ await this.layer1RGBWallet.dispose();
2644
+ }
2645
+ if (this.utexoRGBWallet) {
2646
+ await this.utexoRGBWallet.dispose();
2647
+ }
2648
+ }
2649
+ isDisposed() {
2650
+ if (!this.utexoRGBWallet) {
2651
+ return false;
2652
+ }
2653
+ return this.utexoRGBWallet.isDisposed();
2654
+ }
2655
+ async getBtcBalance() {
2656
+ this.ensureInitialized();
2657
+ return this.utexoRGBWallet.getBtcBalance();
2658
+ }
2659
+ async getAddress() {
2660
+ this.ensureInitialized();
2661
+ return this.utexoRGBWallet.getAddress();
2662
+ }
2663
+ async listUnspents() {
2664
+ this.ensureInitialized();
2665
+ return this.utexoRGBWallet.listUnspents();
2666
+ }
2667
+ async createUtxosBegin(params) {
2668
+ this.ensureInitialized();
2669
+ return this.utexoRGBWallet.createUtxosBegin(params);
2670
+ }
2671
+ async createUtxosEnd(params) {
2672
+ this.ensureInitialized();
2673
+ return this.utexoRGBWallet.createUtxosEnd(params);
2674
+ }
2675
+ async createUtxos(params) {
2676
+ this.ensureInitialized();
2677
+ return this.utexoRGBWallet.createUtxos(params);
2678
+ }
2679
+ async listAssets() {
2680
+ this.ensureInitialized();
2681
+ return this.utexoRGBWallet.listAssets();
2682
+ }
2683
+ async getAssetBalance(asset_id) {
2684
+ this.ensureInitialized();
2685
+ return this.utexoRGBWallet.getAssetBalance(asset_id);
2686
+ }
2687
+ async issueAssetNia(params) {
2688
+ this.ensureInitialized();
2689
+ return this.utexoRGBWallet.issueAssetNia(params);
2690
+ }
2691
+ async issueAssetIfa(params) {
2692
+ this.ensureInitialized();
2693
+ return this.utexoRGBWallet.issueAssetIfa(params);
2694
+ }
2695
+ async inflateBegin(params) {
2696
+ this.ensureInitialized();
2697
+ return this.utexoRGBWallet.inflateBegin(params);
2698
+ }
2699
+ async inflateEnd(params) {
2700
+ this.ensureInitialized();
2701
+ return this.utexoRGBWallet.inflateEnd(params);
2702
+ }
2703
+ async inflate(params, mnemonic) {
2704
+ this.ensureInitialized();
2705
+ return this.utexoRGBWallet.inflate(params, mnemonic);
2706
+ }
2707
+ async sendBegin(params) {
2708
+ this.ensureInitialized();
2709
+ return this.utexoRGBWallet.sendBegin(params);
2710
+ }
2711
+ async sendEnd(params) {
2712
+ this.ensureInitialized();
2713
+ return this.utexoRGBWallet.sendEnd(params);
2714
+ }
2715
+ async send(invoiceTransfer, mnemonic) {
2716
+ this.ensureInitialized();
2717
+ return this.utexoRGBWallet.send(invoiceTransfer, mnemonic);
2718
+ }
2719
+ async sendBtcBegin(params) {
2720
+ this.ensureInitialized();
2721
+ return this.utexoRGBWallet.sendBtcBegin(params);
2722
+ }
2723
+ async sendBtcEnd(params) {
2724
+ this.ensureInitialized();
2725
+ return this.utexoRGBWallet.sendBtcEnd(params);
2726
+ }
2727
+ async sendBtc(params) {
2728
+ this.ensureInitialized();
2729
+ return this.utexoRGBWallet.sendBtc(params);
2730
+ }
2731
+ async blindReceive(params) {
2732
+ this.ensureInitialized();
2733
+ return this.utexoRGBWallet.blindReceive(params);
2734
+ }
2735
+ async witnessReceive(params) {
2736
+ this.ensureInitialized();
2737
+ return this.utexoRGBWallet.witnessReceive(params);
2738
+ }
2739
+ async decodeRGBInvoice(params) {
2740
+ this.ensureInitialized();
2741
+ return this.utexoRGBWallet.decodeRGBInvoice(params);
2742
+ }
2743
+ async listTransactions() {
2744
+ this.ensureInitialized();
2745
+ return this.utexoRGBWallet.listTransactions();
2746
+ }
2747
+ async listTransfers(asset_id) {
2748
+ this.ensureInitialized();
2749
+ return this.utexoRGBWallet.listTransfers(asset_id);
2750
+ }
2751
+ async failTransfers(params) {
2752
+ this.ensureInitialized();
2753
+ return this.utexoRGBWallet.failTransfers(params);
2754
+ }
2755
+ async refreshWallet() {
2756
+ this.ensureInitialized();
2757
+ this.utexoRGBWallet.refreshWallet();
2758
+ }
2759
+ async syncWallet() {
2760
+ this.ensureInitialized();
2761
+ this.utexoRGBWallet.syncWallet();
2762
+ }
2763
+ async estimateFeeRate(blocks) {
2764
+ this.ensureInitialized();
2765
+ return this.utexoRGBWallet.estimateFeeRate(blocks);
2766
+ }
2767
+ async estimateFee(psbtBase64) {
2768
+ this.ensureInitialized();
2769
+ return this.utexoRGBWallet.estimateFee(psbtBase64);
2770
+ }
2771
+ /**
2772
+ * Create backup for both layer1 and utexo stores in one folder.
2773
+ * Writes backupPath/wallet_{masterFingerprint}_layer1.backup and backupPath/wallet_{masterFingerprint}_utexo.backup
2774
+ * (same naming convention as VSS: storeId_layer1, storeId_utexo with storeId = wallet_<fp>).
2775
+ * Use restoreUtxoWalletFromBackup with the same backupPath to restore both.
2776
+ */
2777
+ async createBackup(params) {
2778
+ this.ensureInitialized();
2779
+ const { backupPath, password } = params;
2780
+ if (!backupPath || !password) {
2781
+ throw new ValidationError("backupPath and password are required", "createBackup");
2782
+ }
2783
+ const fp = this.utexoKeys.masterFingerprint;
2784
+ const { layer1TmpDir, utexoTmpDir, layer1FinalPath, utexoFinalPath } = prepareUtxoBackupDirs(backupPath, fp);
2785
+ const layer1Result = await this.layer1RGBWallet.createBackup({ backupPath: layer1TmpDir, password });
2786
+ const utexoResult = await this.utexoRGBWallet.createBackup({ backupPath: utexoTmpDir, password });
2787
+ finalizeUtxoBackupPaths({
2788
+ layer1BackupPath: layer1Result.backupPath,
2789
+ utexoBackupPath: utexoResult.backupPath,
2790
+ layer1FinalPath,
2791
+ utexoFinalPath,
2792
+ layer1TmpDir,
2793
+ utexoTmpDir
2794
+ });
2795
+ return {
2796
+ message: "Backup created successfully (layer1 + utexo)",
2797
+ backupPath,
2798
+ layer1BackupPath: layer1FinalPath,
2799
+ utexoBackupPath: utexoFinalPath
2800
+ };
2801
+ }
2802
+ async configureVssBackup(config) {
2803
+ this.ensureInitialized();
2804
+ const { layer1, utexo } = getVssConfigs(config);
2805
+ await this.layer1RGBWallet.configureVssBackup(layer1);
2806
+ await this.utexoRGBWallet.configureVssBackup(utexo);
2807
+ }
2808
+ async disableVssAutoBackup() {
2809
+ this.ensureInitialized();
2810
+ await this.layer1RGBWallet.disableVssAutoBackup();
2811
+ await this.utexoRGBWallet.disableVssAutoBackup();
2812
+ }
2813
+ /**
2814
+ * Run VSS backup for both layer1 and utexo stores.
2815
+ * Config is optional: when omitted, builds config from mnemonic (option param or wallet mnemonic)
2816
+ * and options.vssServerUrl (or DEFAULT_VSS_SERVER_URL if not set).
2817
+ *
2818
+ * @param config - Optional; when omitted, built from mnemonic and vssServerUrl
2819
+ * @param mnemonic - Optional; when omitted, uses wallet mnemonic (only if wallet was created with mnemonic string)
2820
+ */
2821
+ async vssBackup(config, mnemonic) {
2822
+ this.ensureInitialized();
2823
+ let vssConfig;
2824
+ if (config) {
2825
+ vssConfig = config;
2826
+ } else {
2827
+ const mnemonicToUse = mnemonic ?? (typeof this.mnemonicOrSeed === "string" ? this.mnemonicOrSeed : null);
2828
+ if (!mnemonicToUse) {
2829
+ throw new ValidationError(
2830
+ "mnemonic is required for VSS backup when config is not passed (wallet was created with seed)",
2831
+ "mnemonic"
2832
+ );
2833
+ }
2834
+ const serverUrl = this.options.vssServerUrl ?? DEFAULT_VSS_SERVER_URL;
2835
+ const preset = this.options.network ?? "mainnet";
2836
+ vssConfig = await buildVssConfigFromMnemonic(mnemonicToUse.trim(), serverUrl, preset);
2837
+ }
2838
+ const { layer1, utexo } = getVssConfigs(vssConfig);
2839
+ await this.layer1RGBWallet.vssBackup(layer1);
2840
+ const version = await this.utexoRGBWallet.vssBackup(utexo);
2841
+ return version;
2842
+ }
2843
+ /**
2844
+ * Get VSS backup info. Config is optional; when omitted, built from mnemonic (param or wallet)
2845
+ * and options.vssServerUrl (or DEFAULT_VSS_SERVER_URL if not set).
2846
+ */
2847
+ async vssBackupInfo(config, mnemonic) {
2848
+ this.ensureInitialized();
2849
+ let vssConfig;
2850
+ if (config) {
2851
+ vssConfig = config;
2852
+ } else {
2853
+ const mnemonicToUse = mnemonic ?? (typeof this.mnemonicOrSeed === "string" ? this.mnemonicOrSeed : null);
2854
+ if (!mnemonicToUse) {
2855
+ throw new ValidationError("config or mnemonic required for vssBackupInfo", "config");
2856
+ }
2857
+ const serverUrl = this.options.vssServerUrl ?? DEFAULT_VSS_SERVER_URL;
2858
+ const preset = this.options.network ?? "mainnet";
2859
+ vssConfig = await buildVssConfigFromMnemonic(mnemonicToUse.trim(), serverUrl, preset);
2860
+ }
2861
+ const { utexo } = getVssConfigs(vssConfig);
2862
+ return this.utexoRGBWallet.vssBackupInfo(utexo);
2863
+ }
2864
+ async signPsbt(psbt, mnemonic) {
2865
+ this.ensureInitialized();
2866
+ return this.utexoRGBWallet.signPsbt(psbt, mnemonic);
2867
+ }
2868
+ async signMessage(message) {
2869
+ this.ensureInitialized();
2870
+ return this.utexoRGBWallet.signMessage(message);
2871
+ }
2872
+ async verifyMessage(message, signature, accountXpub) {
2873
+ this.ensureInitialized();
2874
+ return this.utexoRGBWallet.verifyMessage(message, signature, accountXpub);
2875
+ }
2876
+ /**
2877
+ * Validates that the wallet has sufficient spendable balance for the given asset and amount.
2878
+ * @param assetId - Asset ID to check balance for
2879
+ * @param amount - Required amount (in asset units)
2880
+ * @throws {ValidationError} If balance is not found or insufficient
2881
+ */
2882
+ async validateBalance(assetId, amount) {
2883
+ const assetBalance = await this.getAssetBalance(assetId);
2884
+ if (!assetBalance || !assetBalance.spendable) {
2885
+ throw new ValidationError("Asset balance is not found", "assetBalance");
2886
+ }
2887
+ if (assetBalance.spendable < amount) {
2888
+ throw new ValidationError(`Insufficient balance ${assetBalance.spendable} < ${amount}`, "amount");
2889
+ }
2890
+ }
2891
+ /**
2892
+ * Extracts invoice data and destination asset from a bridge transfer.
2893
+ *
2894
+ * @param bridgeTransfer - Bridge transfer response containing recipient invoice and token info
2895
+ * @returns Object containing invoice string, decoded invoice data, and destination asset
2896
+ * @throws {ValidationError} If destination asset is not supported
2897
+ */
2898
+ async extractInvoiceAndAsset(bridgeTransfer) {
2899
+ const utexoInvoice = bridgeTransfer.recipient.address;
2900
+ const invoiceData = await this.decodeRGBInvoice({ invoice: utexoInvoice });
2901
+ const destinationAsset = this.networkIdMap.utexo.getAssetById(bridgeTransfer.recipientToken.id);
2902
+ if (!destinationAsset) {
2903
+ throw new ValidationError("Destination asset is not supported", "assetId");
2904
+ }
2905
+ return { utexoInvoice, invoiceData, destinationAsset };
2906
+ }
2907
+ /**
2908
+ * IUTEXOProtocol Implementation
2909
+ */
2910
+ async onchainReceive(params) {
2911
+ this.ensureInitialized();
2912
+ const destinationAsset = getDestinationAsset("mainnet", "utexo", params.assetId ?? null);
2913
+ if (!destinationAsset) {
2914
+ throw new ValidationError("Destination asset is not supported", "assetId");
2915
+ }
2916
+ if (!params.amount) {
2917
+ throw new ValidationError("Amount is required", "amount");
2918
+ }
2919
+ const destinationInvoice = await this.utexoRGBWallet.witnessReceive({
2920
+ assetId: "",
2921
+ //invoice can receive any asset
2922
+ amount: params.amount,
2923
+ minConfirmations: params.minConfirmations,
2924
+ durationSeconds: params.durationSeconds
2925
+ });
2926
+ const bridgeTransfer = await this.bridge.getBridgeInSignature({
2927
+ sender: {
2928
+ address: "rgb-address",
2929
+ networkName: this.networkIdMap.mainnet.networkName,
2930
+ networkId: this.networkIdMap.mainnet.networkId
2931
+ },
2932
+ tokenId: destinationAsset.tokenId,
2933
+ amount: params.amount.toString(),
2934
+ destination: {
2935
+ address: destinationInvoice.invoice,
2936
+ networkName: this.networkIdMap.utexo.networkName,
2937
+ networkId: this.networkIdMap.utexo.networkId
2938
+ },
2939
+ additionalAddresses: []
2940
+ });
2941
+ const decodedInvoice = decodeBridgeInvoice(bridgeTransfer.signature);
2942
+ return {
2943
+ invoice: decodedInvoice
2944
+ };
2945
+ }
2946
+ async onchainSendBegin(params) {
2947
+ this.ensureInitialized();
2948
+ const bridgeTransfer = await this.bridge.getTransferByMainnetInvoice(params.invoice, this.networkIdMap.mainnet.networkId);
2949
+ if (!bridgeTransfer) {
2950
+ console.log("External invoice UTEXO -> Mainnet initiated");
2951
+ return this.UTEXOToMainnetRGB(params);
2952
+ }
2953
+ const utexoInvoice = bridgeTransfer.recipient.address;
2954
+ const invoiceData = await this.decodeRGBInvoice({ invoice: utexoInvoice });
2955
+ const bridgeAmount = bridgeTransfer.recipientAmount;
2956
+ const destinationAsset = this.networkIdMap.utexo.getAssetById(bridgeTransfer.recipientToken.id);
2957
+ if (!destinationAsset) {
2958
+ throw new ValidationError("Destination asset is not supported", "assetId");
2959
+ }
2960
+ const amount = toUnitsNumber(bridgeAmount, destinationAsset.precision);
2961
+ const isWitness = invoiceData.recipientId.includes("wvout:");
2962
+ await this.validateBalance(destinationAsset.assetId, amount);
2963
+ const psbt = await this.utexoRGBWallet.sendBegin({
2964
+ invoice: utexoInvoice,
2965
+ amount,
2966
+ assetId: destinationAsset.assetId,
2967
+ donation: true,
2968
+ ...isWitness && {
2969
+ witnessData: {
2970
+ amountSat: 1e3,
2971
+ blinding: 0
2972
+ }
2973
+ }
2974
+ });
2975
+ return psbt;
2976
+ }
2977
+ async onchainSendEnd(params) {
2978
+ this.ensureInitialized();
2979
+ const sendResult = await this.utexoRGBWallet.sendEnd({ signedPsbt: params.signedPsbt });
2980
+ return sendResult;
2981
+ }
2982
+ async onchainSend(params, mnemonic) {
2983
+ this.ensureInitialized();
2984
+ const psbt = await this.onchainSendBegin(params);
2985
+ const signed_psbt = await this.utexoRGBWallet.signPsbt(psbt, mnemonic);
2986
+ return await this.onchainSendEnd({ signedPsbt: signed_psbt, invoice: params.invoice });
2987
+ }
2988
+ async getOnchainSendStatus(invoice) {
2989
+ const bridgeTransfer = await this.bridge.getTransferByMainnetInvoice(invoice, this.networkIdMap.mainnet.networkId);
2990
+ if (!bridgeTransfer) {
2991
+ const withdrawTransfer = await this.bridge.getWithdrawTransfer(invoice, this.networkIdMap.utexo.networkId);
2992
+ if (!withdrawTransfer) {
2993
+ return null;
2994
+ }
2995
+ return withdrawTransfer.status;
2996
+ }
2997
+ const { invoiceData, destinationAsset } = await this.extractInvoiceAndAsset(bridgeTransfer);
2998
+ const transfers = await this.utexoRGBWallet.listTransfers(destinationAsset.assetId);
2999
+ const transfer = transfers.find((transfer2) => transfer2.recipientId === invoiceData.recipientId);
3000
+ if (transfer) {
3001
+ return transfer.status;
3002
+ }
3003
+ if (bridgeTransfer) {
3004
+ return bridgeTransfer.status;
3005
+ }
3006
+ return null;
3007
+ }
3008
+ async listOnchainTransfers(asset_id) {
3009
+ this.ensureInitialized();
3010
+ return this.utexoRGBWallet.listTransfers(asset_id);
3011
+ }
3012
+ async createLightningInvoice(params) {
3013
+ this.ensureInitialized();
3014
+ const asset = params.asset;
3015
+ if (!asset) {
3016
+ throw new ValidationError("Asset is required", "asset");
3017
+ }
3018
+ if (!asset.assetId) {
3019
+ throw new ValidationError("Asset ID is required", "assetId");
3020
+ }
3021
+ if (!asset.amount) {
3022
+ throw new ValidationError("Amount is required", "amount");
3023
+ }
3024
+ const destinationAsset = getDestinationAsset("mainnet", "utexo", asset.assetId);
3025
+ if (!destinationAsset) {
3026
+ throw new ValidationError("Destination asset is not supported", "assetId");
3027
+ }
3028
+ const destinationInvoice = await this.utexoRGBWallet.witnessReceive({
3029
+ assetId: "",
3030
+ //invoice can receive any asset
3031
+ amount: asset.amount
3032
+ });
3033
+ const bridgeTransfer = await this.bridge.getBridgeInSignature({
3034
+ sender: {
3035
+ address: "rgb-address",
3036
+ networkName: this.networkIdMap.mainnetLightning.networkName,
3037
+ networkId: this.networkIdMap.mainnetLightning.networkId
3038
+ },
3039
+ tokenId: destinationAsset.tokenId,
3040
+ amount: asset.amount.toString(),
3041
+ destination: {
3042
+ address: destinationInvoice.invoice,
3043
+ networkName: this.networkIdMap.utexo.networkName,
3044
+ networkId: this.networkIdMap.utexo.networkId
3045
+ },
3046
+ additionalAddresses: []
3047
+ });
3048
+ const decodedLnInvoice = decodeBridgeInvoice(bridgeTransfer.signature);
3049
+ return {
3050
+ lnInvoice: decodedLnInvoice
3051
+ };
3052
+ }
3053
+ async payLightningInvoiceBegin(params) {
3054
+ this.ensureInitialized();
3055
+ const bridgeTransfer = await this.bridge.getTransferByMainnetInvoice(params.lnInvoice, this.networkIdMap.mainnetLightning.networkId);
3056
+ if (!bridgeTransfer) {
3057
+ console.log("External invoice UTEXO -> Mainnet Lightning initiated");
3058
+ return this.UtexoToMainnetLightning(params);
3059
+ }
3060
+ const bridgeAmount = bridgeTransfer.recipientAmount;
3061
+ const { utexoInvoice, invoiceData, destinationAsset } = await this.extractInvoiceAndAsset(bridgeTransfer);
3062
+ const amount = toUnitsNumber(bridgeAmount, destinationAsset.precision);
3063
+ const isWitness = invoiceData.recipientId.includes("wvout:");
3064
+ const psbt = await this.utexoRGBWallet.sendBegin({
3065
+ invoice: utexoInvoice,
3066
+ amount,
3067
+ assetId: destinationAsset.assetId,
3068
+ donation: true,
3069
+ ...isWitness && {
3070
+ witnessData: {
3071
+ amountSat: 1e3,
3072
+ blinding: 0
3073
+ }
3074
+ }
3075
+ });
3076
+ return psbt;
3077
+ }
3078
+ async payLightningInvoiceEnd(params) {
3079
+ this.ensureInitialized();
3080
+ const sendResult = await this.utexoRGBWallet.sendEnd({ signedPsbt: params.signedPsbt });
3081
+ return sendResult;
3082
+ }
3083
+ async payLightningInvoice(params, mnemonic) {
3084
+ this.ensureInitialized();
3085
+ const psbt = await this.payLightningInvoiceBegin(params);
3086
+ const signed_psbt = await this.utexoRGBWallet.signPsbt(psbt, mnemonic);
3087
+ return await this.payLightningInvoiceEnd({ signedPsbt: signed_psbt, lnInvoice: params.lnInvoice });
3088
+ }
3089
+ async getLightningSendRequest(lnInvoice) {
3090
+ this.ensureInitialized();
3091
+ const bridgeTransfer = await this.bridge.getTransferByMainnetInvoice(lnInvoice, this.networkIdMap.mainnetLightning.networkId);
3092
+ if (!bridgeTransfer) {
3093
+ const withdrawTransfer = await this.bridge.getWithdrawTransfer(lnInvoice, this.networkIdMap.utexo.networkId);
3094
+ if (!withdrawTransfer) {
3095
+ return null;
3096
+ }
3097
+ return withdrawTransfer.status;
3098
+ }
3099
+ const { invoiceData, destinationAsset } = await this.extractInvoiceAndAsset(bridgeTransfer);
3100
+ const transfers = await this.utexoRGBWallet.listTransfers(destinationAsset.assetId);
3101
+ return transfers.length > 0 ? transfers.find((transfer) => transfer.recipientId === invoiceData.recipientId)?.status ?? null : null;
3102
+ }
3103
+ async getLightningReceiveRequest(lnInvoice) {
3104
+ this.ensureInitialized();
3105
+ const bridgeTransfer = await this.bridge.getTransferByMainnetInvoice(lnInvoice, this.networkIdMap.mainnetLightning.networkId);
3106
+ if (!bridgeTransfer) {
3107
+ const withdrawTransfer = await this.bridge.getWithdrawTransfer(lnInvoice, this.networkIdMap.utexo.networkId);
3108
+ if (!withdrawTransfer) {
3109
+ return null;
3110
+ }
3111
+ return withdrawTransfer.status;
3112
+ }
3113
+ const { invoiceData, destinationAsset } = await this.extractInvoiceAndAsset(bridgeTransfer);
3114
+ const transfers = await this.utexoRGBWallet.listTransfers(destinationAsset.assetId);
3115
+ return transfers.length > 0 ? transfers.find((transfer) => transfer.recipientId === invoiceData.recipientId)?.status ?? null : null;
3116
+ }
3117
+ async UTEXOToMainnetRGB(params) {
3118
+ this.ensureInitialized();
3119
+ const invoiceData = await this.decodeRGBInvoice({ invoice: params.invoice });
3120
+ if (!params.assetId && !invoiceData.assetId) {
3121
+ throw new ValidationError("Asset ID is required for external invoice", "assetId");
3122
+ }
3123
+ const assetId = params.assetId ?? invoiceData.assetId;
3124
+ const utexoAsset = getDestinationAsset("mainnet", "utexo", assetId ?? null);
3125
+ if (!utexoAsset) {
3126
+ throw new ValidationError("UTEXO asset is not supported", "assetId");
3127
+ }
3128
+ const destinationAsset = this.networkIdMap.mainnet.getAssetById(utexoAsset?.tokenId ?? 0);
3129
+ if (!destinationAsset) {
3130
+ throw new ValidationError("Destination asset is not supported", "assetId");
3131
+ }
3132
+ if (!params.amount && !invoiceData.assignment.amount) {
3133
+ throw new ValidationError("Amount is required for external invoice", "amount");
3134
+ }
3135
+ let amount;
3136
+ if (params.amount) {
3137
+ amount = params.amount;
3138
+ } else if (invoiceData.assignment.amount) {
3139
+ amount = fromUnitsNumber(invoiceData.assignment.amount, destinationAsset.precision);
3140
+ } else {
3141
+ throw new ValidationError("Amount is required", "amount");
3142
+ }
3143
+ await this.validateBalance(utexoAsset.assetId, toUnitsNumber(amount.toString(), utexoAsset.precision));
3144
+ const payload = {
3145
+ sender: {
3146
+ address: "rgb-address",
3147
+ networkName: this.networkIdMap.utexo.networkName,
3148
+ networkId: this.networkIdMap.utexo.networkId
3149
+ },
3150
+ tokenId: destinationAsset.tokenId,
3151
+ amount: amount.toString(),
3152
+ destination: {
3153
+ address: params.invoice,
3154
+ networkName: this.networkIdMap.mainnet.networkName,
3155
+ networkId: this.networkIdMap.mainnet.networkId
3156
+ },
3157
+ additionalAddresses: []
3158
+ };
3159
+ console.log("payload", payload);
3160
+ const bridgeOutTransfer = await this.bridge.getBridgeInSignature(payload);
3161
+ const decodedInvoice = decodeBridgeInvoice(bridgeOutTransfer.signature);
3162
+ const isWitness = decodedInvoice.includes("wvout:");
3163
+ const psbt = await this.utexoRGBWallet.sendBegin({
3164
+ invoice: decodedInvoice,
3165
+ amount: Number(bridgeOutTransfer.amount),
3166
+ assetId: utexoAsset.assetId,
3167
+ donation: true,
3168
+ ...isWitness && {
3169
+ witnessData: {
3170
+ amountSat: 1e3,
3171
+ blinding: 0
3172
+ }
3173
+ }
3174
+ });
3175
+ return psbt;
3176
+ }
3177
+ async UtexoToMainnetLightning(params) {
3178
+ this.ensureInitialized();
3179
+ if (!params.assetId) {
3180
+ throw new ValidationError("Asset ID is required for external invoice", "assetId");
3181
+ }
3182
+ const assetId = params.assetId;
3183
+ const utexoAsset = getDestinationAsset("mainnet", "utexo", assetId ?? null);
3184
+ const destinationAsset = this.networkIdMap.mainnet.getAssetById(utexoAsset?.tokenId ?? 0);
3185
+ if (!destinationAsset) {
3186
+ throw new ValidationError("Destination asset is not supported", "assetId");
3187
+ }
3188
+ if (!utexoAsset) {
3189
+ throw new ValidationError("Destination asset is not supported", "assetId");
3190
+ }
3191
+ if (!params.amount) {
3192
+ throw new ValidationError("Amount is required for external invoice", "amount");
3193
+ }
3194
+ const amount = params.amount;
3195
+ await this.validateBalance(utexoAsset.assetId, toUnitsNumber(amount.toString(), utexoAsset.precision));
3196
+ const bridgeOutTransfer = await this.bridge.getBridgeInSignature({
3197
+ sender: {
3198
+ address: "rgb-address",
3199
+ networkName: this.networkIdMap.utexo.networkName,
3200
+ networkId: this.networkIdMap.utexo.networkId
3201
+ },
3202
+ tokenId: destinationAsset.tokenId,
3203
+ amount: amount.toString(),
3204
+ destination: {
3205
+ address: params.lnInvoice,
3206
+ networkName: this.networkIdMap.mainnetLightning.networkName,
3207
+ networkId: this.networkIdMap.mainnetLightning.networkId
3208
+ },
3209
+ additionalAddresses: []
3210
+ });
3211
+ const decodedInvoice = decodeBridgeInvoice(bridgeOutTransfer.signature);
3212
+ const isWitness = decodedInvoice.includes("wvout:");
3213
+ const psbt = await this.utexoRGBWallet.sendBegin({
3214
+ invoice: decodedInvoice,
3215
+ amount: Number(bridgeOutTransfer.amount),
3216
+ assetId: utexoAsset.assetId,
3217
+ donation: true,
3218
+ ...isWitness && {
3219
+ witnessData: {
3220
+ amountSat: 1e3,
3221
+ blinding: 0
3222
+ }
3223
+ }
3224
+ });
3225
+ return psbt;
3226
+ }
3227
+ // TODO: Implement remaining methods as needed:
3228
+ // - createLightningInvoice() - will use utexoRGBWallet
3229
+ // - getLightningReceiveRequest() - will use utexoRGBWallet
3230
+ // - getLightningSendRequest() - will use utexoRGBWallet
3231
+ // - getLightningSendFeeEstimate() - will use utexoRGBWallet
3232
+ // - payLightningInvoiceBegin() - will use utexoRGBWallet
3233
+ // - payLightningInvoiceEnd() - will use utexoRGBWallet
3234
+ // - onchainSendBegin() - will use layer1RGBWallet or utexoRGBWallet
3235
+ // - onchainSendEnd() - will use layer1RGBWallet or utexoRGBWallet
3236
+ // - getOnchainSendStatus() - will use layer1RGBWallet or utexoRGBWallet
3237
+ // - listOnchainTransfers() - will use layer1RGBWallet or utexoRGBWallet
3238
+ // - listLightningPayments() - will use utexoRGBWallet
3239
+ };
1764
3240
 
1765
3241
  // src/utils/logger.ts
1766
3242
  var LogLevel = /* @__PURE__ */ ((LogLevel2) => {
@@ -1825,6 +3301,6 @@ function configureLogging(level) {
1825
3301
  logger.setLevel(level);
1826
3302
  }
1827
3303
 
1828
- export { AssetIface, AssetSchema, BIP32_VERSIONS, BadRequestError, COIN_BITCOIN_MAINNET, COIN_BITCOIN_TESTNET, COIN_RGB_MAINNET, COIN_RGB_TESTNET, ConfigurationError, ConflictError, CryptoError, DEFAULT_API_TIMEOUT, DEFAULT_LOG_LEVEL, DEFAULT_MAX_RETRIES, DEFAULT_NETWORK, DERIVATION_ACCOUNT, DERIVATION_PURPOSE, KEYCHAIN_BTC, KEYCHAIN_RGB, LogLevel, NETWORK_MAP, NetworkError, NotFoundError, RgbNodeError, SDKError, TransactionType, TransferStatus, ValidationError, WalletError, WalletManager, accountXpubsFromMnemonic, configureLogging, createWallet, createWalletManager, deriveKeysFromMnemonic, deriveKeysFromSeed, deriveKeysFromXpriv, generateKeys2 as generateKeys, getEnvironment, getXprivFromMnemonic, getXpubFromXpriv, isBrowser, isNode, logger, normalizeNetwork, restoreFromBackup, restoreKeys, signMessage, signPsbt, signPsbtFromSeed, signPsbtSync, validateBase64, validateHex, validateMnemonic, validateNetwork, validatePsbt, validateRequired, validateString, verifyMessage, wallet };
3304
+ export { BIP32_VERSIONS, BadRequestError, COIN_BITCOIN_MAINNET, COIN_BITCOIN_TESTNET, COIN_RGB_MAINNET, COIN_RGB_TESTNET, ConfigurationError, ConflictError, CryptoError, DEFAULT_API_TIMEOUT, DEFAULT_LOG_LEVEL, DEFAULT_MAX_RETRIES, DEFAULT_NETWORK, DEFAULT_VSS_SERVER_URL, DERIVATION_ACCOUNT, DERIVATION_PURPOSE, KEYCHAIN_BTC, KEYCHAIN_RGB, LightningProtocol, LogLevel, NETWORK_MAP, NetworkError, NotFoundError, OnchainProtocol, RgbNodeError, SDKError, UTEXOProtocol, UTEXOWallet, ValidationError, WalletError, WalletManager, accountXpubsFromMnemonic, configureLogging, createWallet, createWalletManager, deriveKeysFromMnemonic, deriveKeysFromMnemonicOrSeed, deriveKeysFromSeed, deriveKeysFromXpriv, deriveVssSigningKeyFromMnemonic, generateKeys2 as generateKeys, getDestinationAsset, getEnvironment, getUtxoNetworkConfig, getXprivFromMnemonic, getXpubFromXpriv, isBrowser, isNode, logger, normalizeNetwork, restoreFromBackup, restoreFromVss, restoreKeys, restoreUtxoWalletFromBackup, restoreUtxoWalletFromVss, signMessage, signPsbt, signPsbtFromSeed, signPsbtSync, utexoNetworkIdMap, utexoNetworkMap, validateBase64, validateHex, validateMnemonic, validateNetwork, validatePsbt, validateRequired, validateString, verifyMessage, wallet };
1829
3305
  //# sourceMappingURL=index.mjs.map
1830
3306
  //# sourceMappingURL=index.mjs.map