@buildonspark/issuer-sdk 0.0.92 → 0.0.93
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.
- package/CHANGELOG.md +7 -0
- package/README.md +2 -1
- package/package.json +5 -5
- package/src/tests/integration/spark.test.ts +174 -24
package/CHANGELOG.md
CHANGED
package/README.md
CHANGED
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@buildonspark/issuer-sdk",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.93",
|
|
4
4
|
"description": "Spark Issuer SDK for token issuance",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"module": "./dist/index.js",
|
|
@@ -56,8 +56,8 @@
|
|
|
56
56
|
"depcheck": "depcheck --ignores=buffer,ts-proto,jest,ts-jest,publint",
|
|
57
57
|
"dev": "yarn build -- --watch",
|
|
58
58
|
"docs": "typedoc src",
|
|
59
|
-
"format:fix": "prettier
|
|
60
|
-
"format": "prettier
|
|
59
|
+
"format:fix": "prettier . --write",
|
|
60
|
+
"format": "prettier . --check",
|
|
61
61
|
"lint:fix": "eslint --fix .",
|
|
62
62
|
"lint:fix:continue": "eslint --fix . || exit 0",
|
|
63
63
|
"lint:watch": "esw ./src -w --ext .ts,.tsx,.js --color",
|
|
@@ -72,7 +72,7 @@
|
|
|
72
72
|
"types": "tsc"
|
|
73
73
|
},
|
|
74
74
|
"dependencies": {
|
|
75
|
-
"@buildonspark/spark-sdk": "0.
|
|
75
|
+
"@buildonspark/spark-sdk": "0.3.0",
|
|
76
76
|
"@noble/curves": "^1.8.0",
|
|
77
77
|
"@scure/btc-signer": "^1.5.0",
|
|
78
78
|
"buffer": "^6.0.3"
|
|
@@ -86,7 +86,7 @@
|
|
|
86
86
|
"jest": "^29.7.0",
|
|
87
87
|
"madge": "^8.0.0",
|
|
88
88
|
"node-fetch": "^3.3.2",
|
|
89
|
-
"prettier": "^3.
|
|
89
|
+
"prettier": "^3.6.2",
|
|
90
90
|
"publint": "^0.3.9",
|
|
91
91
|
"ts-jest": "^29.2.5",
|
|
92
92
|
"tsup": "^8.4.0",
|
|
@@ -1,12 +1,14 @@
|
|
|
1
1
|
import {
|
|
2
2
|
ConfigOptions,
|
|
3
3
|
filterTokenBalanceForTokenIdentifier,
|
|
4
|
+
RPCError,
|
|
4
5
|
WalletConfig,
|
|
5
6
|
} from "@buildonspark/spark-sdk";
|
|
6
7
|
import { jest } from "@jest/globals";
|
|
7
|
-
import { bytesToHex } from "@noble/curves/utils";
|
|
8
|
+
import { hexToBytes, bytesToHex } from "@noble/curves/utils";
|
|
8
9
|
import { IssuerSparkWalletTesting } from "../utils/issuer-test-wallet.js";
|
|
9
10
|
import { SparkWalletTesting } from "../utils/spark-testing-wallet.js";
|
|
11
|
+
import { BitcoinFaucet } from "@buildonspark/spark-sdk/test-utils";
|
|
10
12
|
|
|
11
13
|
export const TOKENS_V0_SCHNORR_CONFIG: Required<ConfigOptions> = {
|
|
12
14
|
...WalletConfig.LOCAL,
|
|
@@ -232,9 +234,12 @@ describe.each(TEST_CONFIGS)(
|
|
|
232
234
|
expiryTime: new Date(Date.now() + 1000 * 60 * 60 * 24),
|
|
233
235
|
});
|
|
234
236
|
|
|
235
|
-
const
|
|
236
|
-
|
|
237
|
-
expect(
|
|
237
|
+
const { tokenTransactionSuccess, tokenTransactionErrors } =
|
|
238
|
+
await issuerWallet.fulfillSparkInvoice([{ invoice }]);
|
|
239
|
+
expect(tokenTransactionErrors.length).toBe(0);
|
|
240
|
+
expect(tokenTransactionSuccess.length).toBe(1);
|
|
241
|
+
expect(tokenTransactionSuccess[0].txid).toBeDefined();
|
|
242
|
+
expect(tokenTransactionSuccess[0].txid.length).toBeGreaterThan(0);
|
|
238
243
|
|
|
239
244
|
const issuerBalanceAfter = (await issuerWallet.getIssuerTokenBalance())
|
|
240
245
|
.balance;
|
|
@@ -305,13 +310,16 @@ describe.each(TEST_CONFIGS)(
|
|
|
305
310
|
expiryTime: new Date(Date.now() + 1000 * 60 * 60 * 24),
|
|
306
311
|
});
|
|
307
312
|
|
|
308
|
-
const
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
expect(
|
|
313
|
+
const { tokenTransactionSuccess, tokenTransactionErrors } =
|
|
314
|
+
await issuerWallet.fulfillSparkInvoice([
|
|
315
|
+
{ invoice: invoice1 },
|
|
316
|
+
{ invoice: invoice2 },
|
|
317
|
+
{ invoice: invoice3 },
|
|
318
|
+
]);
|
|
319
|
+
expect(tokenTransactionErrors.length).toBe(0);
|
|
320
|
+
expect(tokenTransactionSuccess.length).toBe(1);
|
|
321
|
+
expect(tokenTransactionSuccess[0].txid).toBeDefined();
|
|
322
|
+
expect(tokenTransactionSuccess[0].txid.length).toBeGreaterThan(0);
|
|
315
323
|
|
|
316
324
|
const issuerBalanceAfter = (await issuerWallet.getIssuerTokenBalance())
|
|
317
325
|
.balance;
|
|
@@ -369,9 +377,11 @@ describe.each(TEST_CONFIGS)(
|
|
|
369
377
|
expiryTime: new Date(Date.now() - 60_000),
|
|
370
378
|
});
|
|
371
379
|
|
|
372
|
-
await
|
|
373
|
-
|
|
374
|
-
)
|
|
380
|
+
const { invalidInvoices } = await issuerWallet.fulfillSparkInvoice([
|
|
381
|
+
{ invoice: expiredInvoice },
|
|
382
|
+
]);
|
|
383
|
+
expect(invalidInvoices.length).toBe(1);
|
|
384
|
+
expect(invalidInvoices[0].invoice).toBe(expiredInvoice);
|
|
375
385
|
|
|
376
386
|
const issuerBalanceAfter = (await issuerWallet.getIssuerTokenBalance())
|
|
377
387
|
.balance;
|
|
@@ -420,11 +430,14 @@ describe.each(TEST_CONFIGS)(
|
|
|
420
430
|
expiryTime: null as unknown as Date,
|
|
421
431
|
});
|
|
422
432
|
|
|
423
|
-
const
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
expect(
|
|
433
|
+
const { tokenTransactionSuccess, tokenTransactionErrors } =
|
|
434
|
+
await issuerWallet.fulfillSparkInvoice([
|
|
435
|
+
{ invoice: nullExpiryInvoice },
|
|
436
|
+
]);
|
|
437
|
+
expect(tokenTransactionErrors.length).toBe(0);
|
|
438
|
+
expect(tokenTransactionSuccess.length).toBe(1);
|
|
439
|
+
expect(tokenTransactionSuccess[0].txid).toBeDefined();
|
|
440
|
+
expect(tokenTransactionSuccess[0].txid.length).toBeGreaterThan(0);
|
|
428
441
|
|
|
429
442
|
const issuerBalanceAfter = (await issuerWallet.getIssuerTokenBalance())
|
|
430
443
|
.balance;
|
|
@@ -475,11 +488,14 @@ describe.each(TEST_CONFIGS)(
|
|
|
475
488
|
expiryTime: new Date(Date.now() + 1000 * 60 * 60 * 24),
|
|
476
489
|
});
|
|
477
490
|
|
|
478
|
-
const
|
|
479
|
-
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
expect(
|
|
491
|
+
const { tokenTransactionSuccess, tokenTransactionErrors } =
|
|
492
|
+
await issuerWallet.fulfillSparkInvoice([
|
|
493
|
+
{ invoice: invoiceWithoutAmount, amount: tokenAmount },
|
|
494
|
+
]);
|
|
495
|
+
expect(tokenTransactionErrors.length).toBe(0);
|
|
496
|
+
expect(tokenTransactionSuccess.length).toBe(1);
|
|
497
|
+
expect(tokenTransactionSuccess[0].txid).toBeDefined();
|
|
498
|
+
expect(tokenTransactionSuccess[0].txid.length).toBeGreaterThan(0);
|
|
483
499
|
|
|
484
500
|
const issuerBalanceAfter = (await issuerWallet.getIssuerTokenBalance())
|
|
485
501
|
.balance;
|
|
@@ -496,6 +512,140 @@ describe.each(TEST_CONFIGS)(
|
|
|
496
512
|
},
|
|
497
513
|
);
|
|
498
514
|
|
|
515
|
+
tv1It(
|
|
516
|
+
`fulfillSparkInvoice successfully handles multiple mixed tokens and sats invoices`,
|
|
517
|
+
async () => {
|
|
518
|
+
const faucet = BitcoinFaucet.getInstance();
|
|
519
|
+
const { wallet: sdk } = await IssuerSparkWalletTesting.initialize({
|
|
520
|
+
options: config,
|
|
521
|
+
});
|
|
522
|
+
await sdk.createToken({
|
|
523
|
+
tokenName: `SDKONE`,
|
|
524
|
+
tokenTicker: "SDK1",
|
|
525
|
+
decimals: 0,
|
|
526
|
+
isFreezable: false,
|
|
527
|
+
maxSupply: 1_000_000n,
|
|
528
|
+
});
|
|
529
|
+
const { wallet: sdk2 } = await IssuerSparkWalletTesting.initialize({
|
|
530
|
+
options: config,
|
|
531
|
+
});
|
|
532
|
+
await sdk2.createToken({
|
|
533
|
+
tokenName: `SDKTWO`,
|
|
534
|
+
tokenTicker: "SDK2",
|
|
535
|
+
decimals: 0,
|
|
536
|
+
isFreezable: false,
|
|
537
|
+
maxSupply: 1_000_000n,
|
|
538
|
+
});
|
|
539
|
+
|
|
540
|
+
await sdk.mintTokens(1_000_000n);
|
|
541
|
+
await sdk2.mintTokens(1_000_000n);
|
|
542
|
+
|
|
543
|
+
const sdkOneTokenIdentifier = await sdk.getIssuerTokenIdentifier();
|
|
544
|
+
const sdkTwoTokenIdentifier = await sdk2.getIssuerTokenIdentifier();
|
|
545
|
+
|
|
546
|
+
await sdk2.transferTokens({
|
|
547
|
+
tokenAmount: 1_000_000n,
|
|
548
|
+
tokenIdentifier: sdkTwoTokenIdentifier,
|
|
549
|
+
receiverSparkAddress: await sdk.getSparkAddress(),
|
|
550
|
+
});
|
|
551
|
+
|
|
552
|
+
const depositAddrOne = await sdk.getSingleUseDepositAddress();
|
|
553
|
+
if (!depositAddrOne) {
|
|
554
|
+
throw new RPCError("Deposit address not found", {
|
|
555
|
+
method: "getDepositAddress",
|
|
556
|
+
});
|
|
557
|
+
}
|
|
558
|
+
const depositAddrTwo = await sdk.getSingleUseDepositAddress();
|
|
559
|
+
if (!depositAddrTwo) {
|
|
560
|
+
throw new RPCError("Deposit address not found", {
|
|
561
|
+
method: "getDepositAddress",
|
|
562
|
+
});
|
|
563
|
+
}
|
|
564
|
+
const depositAddrThree = await sdk.getSingleUseDepositAddress();
|
|
565
|
+
if (!depositAddrThree) {
|
|
566
|
+
throw new RPCError("Deposit address not found", {
|
|
567
|
+
method: "getDepositAddress",
|
|
568
|
+
});
|
|
569
|
+
}
|
|
570
|
+
|
|
571
|
+
const oneThousand = await faucet.sendToAddress(depositAddrOne, 1_000n);
|
|
572
|
+
const twoThousand = await faucet.sendToAddress(depositAddrTwo, 2_000n);
|
|
573
|
+
const threeThousand = await faucet.sendToAddress(
|
|
574
|
+
depositAddrThree,
|
|
575
|
+
3_000n,
|
|
576
|
+
);
|
|
577
|
+
|
|
578
|
+
await sdk.claimDeposit(oneThousand.id);
|
|
579
|
+
await sdk.claimDeposit(twoThousand.id);
|
|
580
|
+
await sdk.claimDeposit(threeThousand.id);
|
|
581
|
+
|
|
582
|
+
const balance = await sdk.getBalance();
|
|
583
|
+
expect(balance.balance).toBe(6_000n);
|
|
584
|
+
|
|
585
|
+
const tomorrow = new Date(Date.now() + 1000 * 60 * 60 * 24);
|
|
586
|
+
const invoice1000 = await sdk2.createSatsInvoice({
|
|
587
|
+
amount: 1_000,
|
|
588
|
+
memo: "Test invoice",
|
|
589
|
+
expiryTime: tomorrow,
|
|
590
|
+
});
|
|
591
|
+
const invoice2000 = await sdk2.createSatsInvoice({
|
|
592
|
+
amount: 2_000,
|
|
593
|
+
memo: "Test invoice",
|
|
594
|
+
expiryTime: tomorrow,
|
|
595
|
+
});
|
|
596
|
+
const invoiceNilAmount = await sdk2.createSatsInvoice({
|
|
597
|
+
memo: "Test invoice",
|
|
598
|
+
expiryTime: tomorrow,
|
|
599
|
+
});
|
|
600
|
+
const sdkOneTokenInvoiceA = await sdk2.createTokensInvoice({
|
|
601
|
+
amount: 1_000n,
|
|
602
|
+
tokenIdentifier: sdkOneTokenIdentifier,
|
|
603
|
+
memo: "Test invoice",
|
|
604
|
+
expiryTime: tomorrow,
|
|
605
|
+
});
|
|
606
|
+
const sdkOneTokenInvoiceB = await sdk2.createTokensInvoice({
|
|
607
|
+
amount: 2_000n,
|
|
608
|
+
tokenIdentifier: sdkOneTokenIdentifier,
|
|
609
|
+
memo: "Test invoice",
|
|
610
|
+
expiryTime: tomorrow,
|
|
611
|
+
});
|
|
612
|
+
const sdkTwoTokenInvoiceA = await sdk2.createTokensInvoice({
|
|
613
|
+
amount: 1_000n,
|
|
614
|
+
tokenIdentifier: sdkTwoTokenIdentifier,
|
|
615
|
+
memo: "Test invoice",
|
|
616
|
+
expiryTime: tomorrow,
|
|
617
|
+
});
|
|
618
|
+
const sdkTwoTokenNilAmountInvoiceB = await sdk2.createTokensInvoice({
|
|
619
|
+
tokenIdentifier: sdkTwoTokenIdentifier,
|
|
620
|
+
memo: "Test invoice",
|
|
621
|
+
expiryTime: tomorrow,
|
|
622
|
+
});
|
|
623
|
+
|
|
624
|
+
const transferResults = await sdk.fulfillSparkInvoice([
|
|
625
|
+
{ invoice: invoice1000 },
|
|
626
|
+
{ invoice: invoice2000 },
|
|
627
|
+
{ invoice: invoiceNilAmount, amount: 3_000n },
|
|
628
|
+
{ invoice: sdkOneTokenInvoiceA },
|
|
629
|
+
{ invoice: sdkOneTokenInvoiceB },
|
|
630
|
+
{ invoice: sdkTwoTokenInvoiceA },
|
|
631
|
+
{ invoice: sdkTwoTokenNilAmountInvoiceB, amount: 3_000n },
|
|
632
|
+
]);
|
|
633
|
+
|
|
634
|
+
const {
|
|
635
|
+
satsTransactionSuccess,
|
|
636
|
+
satsTransactionErrors,
|
|
637
|
+
tokenTransactionSuccess,
|
|
638
|
+
tokenTransactionErrors,
|
|
639
|
+
invalidInvoices,
|
|
640
|
+
} = transferResults;
|
|
641
|
+
expect(satsTransactionErrors.length).toBe(0);
|
|
642
|
+
expect(tokenTransactionErrors.length).toBe(0);
|
|
643
|
+
expect(satsTransactionSuccess.length).toBe(3); // one sats success per invoice
|
|
644
|
+
expect(tokenTransactionSuccess.length).toBe(2); // two token assets - divided into two token transactions
|
|
645
|
+
expect(invalidInvoices.length).toBe(0);
|
|
646
|
+
},
|
|
647
|
+
);
|
|
648
|
+
|
|
499
649
|
it("should create, mint, and batchtransfer tokens", async () => {
|
|
500
650
|
const tokenAmount: bigint = 999n;
|
|
501
651
|
|