@stellar/typescript-wallet-sdk 1.1.2 → 1.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/examples/sep24/README.md +22 -0
- package/examples/sep24/sep24.ts +199 -0
- package/lib/bundle.js +42285 -45231
- package/lib/bundle.js.map +1 -1
- package/lib/bundle_browser.js +55838 -51560
- package/lib/bundle_browser.js.map +1 -1
- package/lib/walletSdk/Exceptions/index.d.ts +3 -0
- package/package.json +6 -4
- package/src/index.ts +1 -0
- package/src/walletSdk/Anchor/Sep24.ts +2 -0
- package/src/walletSdk/Auth/WalletSigner.ts +64 -1
- package/src/walletSdk/Auth/index.ts +1 -1
- package/src/walletSdk/Exceptions/index.ts +13 -0
- package/src/walletSdk/Horizon/Transaction/CommonTransactionBuilder.ts +75 -0
- package/src/walletSdk/Horizon/Transaction/SponsoringBuilder.ts +58 -0
- package/src/walletSdk/Horizon/Transaction/TransactionBuilder.ts +132 -37
- package/src/walletSdk/Horizon/index.ts +1 -0
- package/src/walletSdk/Types/auth.ts +4 -0
- package/src/walletSdk/Types/horizon.ts +12 -1
- package/src/walletSdk/index.ts +7 -1
- package/test/stellar.test.ts +237 -19
- package/test/transaction.test.ts +325 -0
- package/test/wallet.test.ts +24 -0
package/test/stellar.test.ts
CHANGED
|
@@ -36,14 +36,13 @@ describe("Stellar", () => {
|
|
|
36
36
|
} catch (e) {
|
|
37
37
|
await axios.get("https://friendbot.stellar.org/?addr=" + kp.publicKey);
|
|
38
38
|
}
|
|
39
|
-
});
|
|
39
|
+
}, 10000);
|
|
40
40
|
it("should create and submit a transaction", async () => {
|
|
41
41
|
const now = Math.floor(Date.now() / 1000) - 5;
|
|
42
42
|
|
|
43
43
|
const txBuilderParams = [
|
|
44
44
|
{
|
|
45
45
|
sourceAddress: kp,
|
|
46
|
-
baseFee: 100,
|
|
47
46
|
startingBalance: 2,
|
|
48
47
|
},
|
|
49
48
|
{
|
|
@@ -198,32 +197,174 @@ describe("Stellar", () => {
|
|
|
198
197
|
kp.sign(tx);
|
|
199
198
|
});
|
|
200
199
|
it("should transfer withdrawal transaction", async () => {
|
|
201
|
-
const
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
200
|
+
const memoExamples = [
|
|
201
|
+
{
|
|
202
|
+
type: "text",
|
|
203
|
+
value: "example text",
|
|
204
|
+
},
|
|
205
|
+
{
|
|
206
|
+
type: "id",
|
|
207
|
+
value: "12345",
|
|
208
|
+
},
|
|
209
|
+
{
|
|
210
|
+
type: "hash",
|
|
211
|
+
value: "AAAAAAAAAAAAAAAAAAAAAMAP+8deo0TViBD09TfOBY0=",
|
|
212
|
+
},
|
|
213
|
+
{
|
|
214
|
+
type: "hash",
|
|
215
|
+
value: "MV9b23bQeMQ7isAGTkoBZGErH853yGk0W/yUx1iU7dM=",
|
|
216
|
+
},
|
|
217
|
+
];
|
|
211
218
|
|
|
212
|
-
const
|
|
213
|
-
|
|
214
|
-
|
|
219
|
+
for (const memoExample of memoExamples) {
|
|
220
|
+
const walletTransaction = {
|
|
221
|
+
id: "db15d166-5a5e-4d5c-ba5d-271c32cd8cf0",
|
|
222
|
+
kind: "withdrawal",
|
|
223
|
+
status: TransactionStatus.pending_user_transfer_start,
|
|
224
|
+
amount_in: "50.55",
|
|
225
|
+
withdraw_memo_type: memoExample.type,
|
|
226
|
+
withdraw_memo: memoExample.value,
|
|
227
|
+
withdraw_anchor_account:
|
|
228
|
+
"GCSGSR6KQQ5BP2FXVPWRL6SWPUSFWLVONLIBJZUKTVQB5FYJFVL6XOXE",
|
|
229
|
+
} as WithdrawTransaction;
|
|
230
|
+
|
|
231
|
+
const asset = new IssuedAssetId(
|
|
232
|
+
"USDC",
|
|
233
|
+
"GBBD47IF6LWK7P7MDEVSCWR7DPUWV3NY3DTQEVFL4NAT4AQH3ZLLFLA5",
|
|
234
|
+
);
|
|
235
|
+
|
|
236
|
+
const txBuilder = await stellar.transaction({
|
|
237
|
+
sourceAddress: kp,
|
|
238
|
+
baseFee: 100,
|
|
239
|
+
});
|
|
240
|
+
|
|
241
|
+
const txn = txBuilder
|
|
242
|
+
.transferWithdrawalTransaction(walletTransaction, asset)
|
|
243
|
+
.build();
|
|
244
|
+
expect(txn).toBeTruthy();
|
|
245
|
+
}
|
|
246
|
+
}, 20000);
|
|
247
|
+
});
|
|
248
|
+
|
|
249
|
+
let txnSourceKp;
|
|
250
|
+
let sponsorKp;
|
|
251
|
+
let newKp;
|
|
252
|
+
describe("SponsoringBuilder", () => {
|
|
253
|
+
beforeAll(async () => {
|
|
254
|
+
wal = Wallet.TestNet();
|
|
255
|
+
stellar = wal.stellar();
|
|
256
|
+
|
|
257
|
+
txnSourceKp = new SigningKeypair(Keypair.random());
|
|
258
|
+
sponsorKp = new SigningKeypair(Keypair.random());
|
|
259
|
+
newKp = new SigningKeypair(Keypair.random());
|
|
260
|
+
await axios.get(
|
|
261
|
+
"https://friendbot.stellar.org/?addr=" + sponsorKp.publicKey,
|
|
215
262
|
);
|
|
263
|
+
await axios.get(
|
|
264
|
+
"https://friendbot.stellar.org/?addr=" + txnSourceKp.publicKey,
|
|
265
|
+
);
|
|
266
|
+
}, 15000);
|
|
267
|
+
|
|
268
|
+
it("should sponsor creating an account", async () => {
|
|
269
|
+
const wal = Wallet.TestNet();
|
|
270
|
+
const stellar = wal.stellar();
|
|
216
271
|
|
|
217
272
|
const txBuilder = await stellar.transaction({
|
|
218
|
-
sourceAddress:
|
|
273
|
+
sourceAddress: txnSourceKp,
|
|
274
|
+
baseFee: 100,
|
|
275
|
+
});
|
|
276
|
+
const buildingFunction = (bldr) => bldr.createAccount(newKp, 0);
|
|
277
|
+
// scenario of different txn source account from sponsor account
|
|
278
|
+
const txn = txBuilder
|
|
279
|
+
.sponsoring(sponsorKp, buildingFunction, newKp)
|
|
280
|
+
.build();
|
|
281
|
+
newKp.sign(txn);
|
|
282
|
+
txnSourceKp.sign(txn);
|
|
283
|
+
sponsorKp.sign(txn);
|
|
284
|
+
|
|
285
|
+
const res = await stellar.submitTransaction(txn);
|
|
286
|
+
expect(res).toBe(true);
|
|
287
|
+
|
|
288
|
+
const sponsoredLoaded = (await stellar.server.loadAccount(
|
|
289
|
+
newKp.publicKey,
|
|
290
|
+
)) as any;
|
|
291
|
+
expect(sponsoredLoaded.num_sponsored).toBe(2);
|
|
292
|
+
}, 15000);
|
|
293
|
+
|
|
294
|
+
it("should sponsor adding trustlines", async () => {
|
|
295
|
+
const txBuilder = await stellar.transaction({
|
|
296
|
+
sourceAddress: txnSourceKp,
|
|
219
297
|
baseFee: 100,
|
|
220
298
|
});
|
|
299
|
+
const buildingFunction = (bldr) =>
|
|
300
|
+
bldr.addAssetSupport(
|
|
301
|
+
new IssuedAssetId(
|
|
302
|
+
"USDC",
|
|
303
|
+
"GBBD47IF6LWK7P7MDEVSCWR7DPUWV3NY3DTQEVFL4NAT4AQH3ZLLFLA5",
|
|
304
|
+
),
|
|
305
|
+
);
|
|
306
|
+
const txn = txBuilder.sponsoring(sponsorKp, buildingFunction).build();
|
|
307
|
+
sponsorKp.sign(txn);
|
|
308
|
+
txnSourceKp.sign(txn);
|
|
221
309
|
|
|
310
|
+
const res = await stellar.submitTransaction(txn);
|
|
311
|
+
expect(res).toBe(true);
|
|
312
|
+
|
|
313
|
+
const sponsorLoaded = (await stellar.server.loadAccount(
|
|
314
|
+
sponsorKp.publicKey,
|
|
315
|
+
)) as any;
|
|
316
|
+
expect(sponsorLoaded.num_sponsoring).toBe(3);
|
|
317
|
+
}, 15000);
|
|
318
|
+
|
|
319
|
+
it("should allow sponsoring and regular operations in same transaction", async () => {
|
|
320
|
+
const txBuilder = await stellar.transaction({
|
|
321
|
+
sourceAddress: txnSourceKp,
|
|
322
|
+
baseFee: 100,
|
|
323
|
+
});
|
|
324
|
+
const buildingFunction = (bldr) =>
|
|
325
|
+
bldr.addAssetSupport(
|
|
326
|
+
new IssuedAssetId(
|
|
327
|
+
"USDC",
|
|
328
|
+
"GBBD47IF6LWK7P7MDEVSCWR7DPUWV3NY3DTQEVFL4NAT4AQH3ZLLFLA5",
|
|
329
|
+
),
|
|
330
|
+
);
|
|
222
331
|
const txn = txBuilder
|
|
223
|
-
.
|
|
332
|
+
.sponsoring(sponsorKp, buildingFunction)
|
|
333
|
+
.transfer(sponsorKp.publicKey, new NativeAssetId(), "5")
|
|
224
334
|
.build();
|
|
225
|
-
|
|
226
|
-
|
|
335
|
+
sponsorKp.sign(txn);
|
|
336
|
+
txnSourceKp.sign(txn);
|
|
337
|
+
|
|
338
|
+
const res = await stellar.submitTransaction(txn);
|
|
339
|
+
expect(res).toBe(true);
|
|
340
|
+
|
|
341
|
+
const sponsorLoaded = (await stellar.server.loadAccount(
|
|
342
|
+
sponsorKp.publicKey,
|
|
343
|
+
)) as any;
|
|
344
|
+
expect(sponsorLoaded.num_sponsoring).toBe(3);
|
|
345
|
+
}, 15000);
|
|
346
|
+
it("should sponsor account modification", async () => {
|
|
347
|
+
const txBuilder = await stellar.transaction({
|
|
348
|
+
sourceAddress: txnSourceKp,
|
|
349
|
+
baseFee: 100,
|
|
350
|
+
});
|
|
351
|
+
const otherKp = new SigningKeypair(Keypair.random());
|
|
352
|
+
|
|
353
|
+
const txn = txBuilder
|
|
354
|
+
.sponsoring(sponsorKp, (bldr) => bldr.addAccountSigner(otherKp, 2))
|
|
355
|
+
.build();
|
|
356
|
+
sponsorKp.sign(txn);
|
|
357
|
+
txnSourceKp.sign(txn);
|
|
358
|
+
|
|
359
|
+
await stellar.submitTransaction(txn);
|
|
360
|
+
const sourceLoaded = (await stellar.server.loadAccount(
|
|
361
|
+
txnSourceKp.publicKey,
|
|
362
|
+
)) as any;
|
|
363
|
+
expect(
|
|
364
|
+
sourceLoaded.signers.find((signer) => signer.key === otherKp.publicKey)
|
|
365
|
+
.weight,
|
|
366
|
+
).toBe(2);
|
|
367
|
+
}, 15000);
|
|
227
368
|
});
|
|
228
369
|
|
|
229
370
|
describe("Asset", () => {
|
|
@@ -245,3 +386,80 @@ describe("Asset", () => {
|
|
|
245
386
|
expect(fiat.sep38).toBe("iso4217:USD");
|
|
246
387
|
});
|
|
247
388
|
});
|
|
389
|
+
|
|
390
|
+
describe("Account Modifying", () => {
|
|
391
|
+
it("should modify account ", async () => {
|
|
392
|
+
const wallet = Wallet.TestNet();
|
|
393
|
+
const stellar = wallet.stellar();
|
|
394
|
+
|
|
395
|
+
const sourceKp = new SigningKeypair(Keypair.random());
|
|
396
|
+
const otherKp = new SigningKeypair(Keypair.random());
|
|
397
|
+
await axios.get(
|
|
398
|
+
"https://friendbot.stellar.org/?addr=" + sourceKp.publicKey,
|
|
399
|
+
);
|
|
400
|
+
await axios.get("https://friendbot.stellar.org/?addr=" + otherKp.publicKey);
|
|
401
|
+
|
|
402
|
+
// Add account signer
|
|
403
|
+
let txBuilder = await stellar.transaction({
|
|
404
|
+
sourceAddress: sourceKp,
|
|
405
|
+
baseFee: 1000,
|
|
406
|
+
});
|
|
407
|
+
const tx = txBuilder.addAccountSigner(otherKp, 1).build();
|
|
408
|
+
tx.sign(sourceKp.keypair);
|
|
409
|
+
await stellar.submitTransaction(tx);
|
|
410
|
+
|
|
411
|
+
let resp = await stellar.server.loadAccount(sourceKp.publicKey);
|
|
412
|
+
|
|
413
|
+
expect(
|
|
414
|
+
resp.signers.find((signer) => signer.key === sourceKp.publicKey),
|
|
415
|
+
).toBeTruthy();
|
|
416
|
+
expect(
|
|
417
|
+
resp.signers.find((signer) => signer.key === otherKp.publicKey),
|
|
418
|
+
).toBeTruthy();
|
|
419
|
+
|
|
420
|
+
// Remove account signer
|
|
421
|
+
txBuilder = await stellar.transaction({
|
|
422
|
+
sourceAddress: sourceKp,
|
|
423
|
+
baseFee: 1000,
|
|
424
|
+
});
|
|
425
|
+
const removeTx = txBuilder.removeAccountSigner(otherKp).build();
|
|
426
|
+
removeTx.sign(sourceKp.keypair);
|
|
427
|
+
await stellar.submitTransaction(removeTx);
|
|
428
|
+
|
|
429
|
+
resp = await stellar.server.loadAccount(sourceKp.publicKey);
|
|
430
|
+
expect(
|
|
431
|
+
resp.signers.find((signer) => signer.key === sourceKp.publicKey),
|
|
432
|
+
).toBeTruthy();
|
|
433
|
+
expect(
|
|
434
|
+
resp.signers.find((signer) => signer.key === otherKp.publicKey),
|
|
435
|
+
).toBeFalsy();
|
|
436
|
+
|
|
437
|
+
// Change account thresholds
|
|
438
|
+
txBuilder = await stellar.transaction({
|
|
439
|
+
sourceAddress: sourceKp,
|
|
440
|
+
baseFee: 1000,
|
|
441
|
+
});
|
|
442
|
+
const thresholdTx = txBuilder.setThreshold({ low: 0, high: 1 }).build();
|
|
443
|
+
thresholdTx.sign(sourceKp.keypair);
|
|
444
|
+
await stellar.submitTransaction(thresholdTx);
|
|
445
|
+
|
|
446
|
+
resp = await stellar.server.loadAccount(sourceKp.publicKey);
|
|
447
|
+
expect(resp.thresholds).toEqual({
|
|
448
|
+
low_threshold: 0,
|
|
449
|
+
med_threshold: 0,
|
|
450
|
+
high_threshold: 1,
|
|
451
|
+
});
|
|
452
|
+
|
|
453
|
+
// Lock master account
|
|
454
|
+
txBuilder = await stellar.transaction({
|
|
455
|
+
sourceAddress: sourceKp,
|
|
456
|
+
baseFee: 1000,
|
|
457
|
+
});
|
|
458
|
+
const lockTx = txBuilder.lockAccountMasterKey().build();
|
|
459
|
+
lockTx.sign(sourceKp.keypair);
|
|
460
|
+
await stellar.submitTransaction(lockTx);
|
|
461
|
+
|
|
462
|
+
resp = await stellar.server.loadAccount(sourceKp.publicKey);
|
|
463
|
+
expect(resp.signers[0].weight).toBe(0);
|
|
464
|
+
}, 45000);
|
|
465
|
+
});
|
|
@@ -0,0 +1,325 @@
|
|
|
1
|
+
import axios from "axios";
|
|
2
|
+
import { Horizon, MuxedAccount } from "stellar-sdk";
|
|
3
|
+
|
|
4
|
+
import { AccountService, SigningKeypair, Stellar, Wallet } from "../src";
|
|
5
|
+
import { IssuedAssetId, NativeAssetId } from "../src/walletSdk/Asset";
|
|
6
|
+
|
|
7
|
+
describe("Muxed Transactions", () => {
|
|
8
|
+
let wallet: Wallet;
|
|
9
|
+
let stellar: Stellar;
|
|
10
|
+
let accountService: AccountService;
|
|
11
|
+
let testingDistributionKp: SigningKeypair;
|
|
12
|
+
let testingAsset: IssuedAssetId;
|
|
13
|
+
|
|
14
|
+
// Creates testing stellar account with testing TSWT asset
|
|
15
|
+
// in case it doesn't exist just yet
|
|
16
|
+
beforeAll(async () => {
|
|
17
|
+
wallet = Wallet.TestNet();
|
|
18
|
+
stellar = wallet.stellar();
|
|
19
|
+
accountService = stellar.account();
|
|
20
|
+
|
|
21
|
+
// Keys for accounts to issue and receive the new TSWT asset
|
|
22
|
+
var issuingKeys = SigningKeypair.fromSecret(
|
|
23
|
+
"SAJMJSEC44DWU22TJF6RWYLRPPXLY4G3L5PVGC7D2QDUCPJIFCOISNQE",
|
|
24
|
+
);
|
|
25
|
+
var receivingKeys = SigningKeypair.fromSecret(
|
|
26
|
+
"SAOQQ76UQFEYN4QAAAOIO45KNZZNQKSXAUB5GXKI6YOFLEDCWPWTCDM3",
|
|
27
|
+
);
|
|
28
|
+
|
|
29
|
+
// The "receiving" account is the distribution account
|
|
30
|
+
testingDistributionKp = receivingKeys;
|
|
31
|
+
|
|
32
|
+
// This is the testing asset we'll use to test sending non-native payments
|
|
33
|
+
testingAsset = new IssuedAssetId("TSWT", issuingKeys.publicKey);
|
|
34
|
+
|
|
35
|
+
let assetAlreadyCreated = false;
|
|
36
|
+
try {
|
|
37
|
+
const receivingAccountInfo = await accountService.getInfo({
|
|
38
|
+
accountAddress: receivingKeys.publicKey,
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
const tswtAssetBalance = receivingAccountInfo.balances.find(
|
|
42
|
+
(balanceLine) => {
|
|
43
|
+
const { asset_code, balance } =
|
|
44
|
+
balanceLine as Horizon.BalanceLineAsset;
|
|
45
|
+
return asset_code === testingAsset.code && Number(balance) > 1000;
|
|
46
|
+
},
|
|
47
|
+
);
|
|
48
|
+
|
|
49
|
+
if (tswtAssetBalance) {
|
|
50
|
+
assetAlreadyCreated = true;
|
|
51
|
+
}
|
|
52
|
+
} catch {}
|
|
53
|
+
|
|
54
|
+
if (assetAlreadyCreated) {
|
|
55
|
+
return;
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
// If the TSWT asset is not there yet, let's issue and distribute it!
|
|
59
|
+
try {
|
|
60
|
+
// First make sure both issuing and receiving(distribution) accounts
|
|
61
|
+
// are funded
|
|
62
|
+
await axios.get(
|
|
63
|
+
"https://friendbot.stellar.org/?addr=" + issuingKeys.publicKey,
|
|
64
|
+
);
|
|
65
|
+
|
|
66
|
+
await axios.get(
|
|
67
|
+
"https://friendbot.stellar.org/?addr=" + receivingKeys.publicKey,
|
|
68
|
+
);
|
|
69
|
+
} catch {}
|
|
70
|
+
|
|
71
|
+
let didFail = false;
|
|
72
|
+
try {
|
|
73
|
+
// Then, the receiving(distribution) account must trust the asset
|
|
74
|
+
const txBuilder = await stellar.transaction({
|
|
75
|
+
sourceAddress: receivingKeys,
|
|
76
|
+
baseFee: 100,
|
|
77
|
+
});
|
|
78
|
+
const addTswtTx = txBuilder.addAssetSupport(testingAsset).build();
|
|
79
|
+
addTswtTx.sign(receivingKeys.keypair);
|
|
80
|
+
await stellar.submitTransaction(addTswtTx);
|
|
81
|
+
|
|
82
|
+
// Finally, the issuing account actually sends a payment using the asset
|
|
83
|
+
// to fund the receiving(distribution) account
|
|
84
|
+
const txBuilder2 = await stellar.transaction({
|
|
85
|
+
sourceAddress: issuingKeys,
|
|
86
|
+
baseFee: 100,
|
|
87
|
+
});
|
|
88
|
+
const fundingPaymentTx = txBuilder2
|
|
89
|
+
.transfer(receivingKeys.publicKey, testingAsset, "100000000")
|
|
90
|
+
.build();
|
|
91
|
+
fundingPaymentTx.sign(issuingKeys.keypair);
|
|
92
|
+
await stellar.submitTransaction(fundingPaymentTx);
|
|
93
|
+
} catch {
|
|
94
|
+
didFail = true;
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
expect(didFail).toBeFalsy();
|
|
98
|
+
}, 60000);
|
|
99
|
+
|
|
100
|
+
it("should send 'native' payment to valid Muxed account", async () => {
|
|
101
|
+
const baseAccoutKp = SigningKeypair.fromSecret(
|
|
102
|
+
"SDC4SZWQDELBKWPBPBLZSKMWAIPNE27OF6BPJV7F7FCXTKHBACN3KWRO",
|
|
103
|
+
);
|
|
104
|
+
|
|
105
|
+
try {
|
|
106
|
+
await axios.get(
|
|
107
|
+
"https://friendbot.stellar.org/?addr=" + baseAccoutKp.publicKey,
|
|
108
|
+
);
|
|
109
|
+
} catch {}
|
|
110
|
+
|
|
111
|
+
const baseAccount = await stellar.server.loadAccount(
|
|
112
|
+
baseAccoutKp.publicKey,
|
|
113
|
+
);
|
|
114
|
+
const muxedAccount = new MuxedAccount(baseAccount, "123");
|
|
115
|
+
|
|
116
|
+
const txBuilder = await stellar.transaction({
|
|
117
|
+
sourceAddress: testingDistributionKp,
|
|
118
|
+
baseFee: 100,
|
|
119
|
+
});
|
|
120
|
+
|
|
121
|
+
const sendNativePaymentTx = txBuilder
|
|
122
|
+
.transfer(muxedAccount.accountId(), new NativeAssetId(), "1")
|
|
123
|
+
.build();
|
|
124
|
+
sendNativePaymentTx.sign(testingDistributionKp.keypair);
|
|
125
|
+
|
|
126
|
+
const response = await stellar.submitTransaction(sendNativePaymentTx);
|
|
127
|
+
|
|
128
|
+
expect(response).toBeTruthy();
|
|
129
|
+
}, 30000);
|
|
130
|
+
|
|
131
|
+
it("should send non-native payment to valid Muxed account", async () => {
|
|
132
|
+
const baseAccoutKp = SigningKeypair.fromSecret(
|
|
133
|
+
"SDFK2E4LSVZJGEWKFIX4SXOLDXQQWMDGNONERVBNFXDVWE2PTEKY6ZSI",
|
|
134
|
+
);
|
|
135
|
+
|
|
136
|
+
try {
|
|
137
|
+
await axios.get(
|
|
138
|
+
"https://friendbot.stellar.org/?addr=" + baseAccoutKp.publicKey,
|
|
139
|
+
);
|
|
140
|
+
} catch {}
|
|
141
|
+
|
|
142
|
+
const baseAccount = await stellar.server.loadAccount(
|
|
143
|
+
baseAccoutKp.publicKey,
|
|
144
|
+
);
|
|
145
|
+
const muxedAccount = new MuxedAccount(baseAccount, "456");
|
|
146
|
+
|
|
147
|
+
// First add support for the non-native asset
|
|
148
|
+
const txBuilder1 = await stellar.transaction({
|
|
149
|
+
sourceAddress: baseAccoutKp,
|
|
150
|
+
baseFee: 100,
|
|
151
|
+
});
|
|
152
|
+
const addTswtTx = txBuilder1.addAssetSupport(testingAsset).build();
|
|
153
|
+
addTswtTx.sign(baseAccoutKp.keypair);
|
|
154
|
+
await stellar.submitTransaction(addTswtTx);
|
|
155
|
+
|
|
156
|
+
// Then submit the non-native payment!
|
|
157
|
+
const txBuilder2 = await stellar.transaction({
|
|
158
|
+
sourceAddress: testingDistributionKp,
|
|
159
|
+
baseFee: 100,
|
|
160
|
+
});
|
|
161
|
+
|
|
162
|
+
const sendNonNativePaymentTx = txBuilder2
|
|
163
|
+
.transfer(muxedAccount.accountId(), testingAsset, "1")
|
|
164
|
+
.build();
|
|
165
|
+
sendNonNativePaymentTx.sign(testingDistributionKp.keypair);
|
|
166
|
+
|
|
167
|
+
const response = await stellar.submitTransaction(sendNonNativePaymentTx);
|
|
168
|
+
|
|
169
|
+
expect(response).toBeTruthy();
|
|
170
|
+
}, 30000);
|
|
171
|
+
|
|
172
|
+
it("should return 'op_no_trust' error for sending unsupported Asset to valid Muxed account", async () => {
|
|
173
|
+
const baseAccoutKp = SigningKeypair.fromSecret(
|
|
174
|
+
"SD4UETXJ2MJCIPSU72DAJDPL2YGDHF2FEIJVNARUGE6MFDPXNS5YHNGK",
|
|
175
|
+
);
|
|
176
|
+
|
|
177
|
+
try {
|
|
178
|
+
await axios.get(
|
|
179
|
+
"https://friendbot.stellar.org/?addr=" + baseAccoutKp.publicKey,
|
|
180
|
+
);
|
|
181
|
+
} catch {}
|
|
182
|
+
|
|
183
|
+
const baseAccount = await stellar.server.loadAccount(
|
|
184
|
+
baseAccoutKp.publicKey,
|
|
185
|
+
);
|
|
186
|
+
const muxedAccount = new MuxedAccount(baseAccount, "789");
|
|
187
|
+
|
|
188
|
+
// Try submitting the non-native payment without adding the trustline
|
|
189
|
+
const txBuilder = await stellar.transaction({
|
|
190
|
+
sourceAddress: testingDistributionKp,
|
|
191
|
+
baseFee: 100,
|
|
192
|
+
});
|
|
193
|
+
|
|
194
|
+
const sendNonNativePaymentTx = txBuilder
|
|
195
|
+
.transfer(muxedAccount.accountId(), testingAsset, "1")
|
|
196
|
+
.build();
|
|
197
|
+
sendNonNativePaymentTx.sign(testingDistributionKp.keypair);
|
|
198
|
+
|
|
199
|
+
try {
|
|
200
|
+
await stellar.submitTransaction(sendNonNativePaymentTx);
|
|
201
|
+
} catch (error) {
|
|
202
|
+
expect(error?.response?.status === 400).toBeTruthy();
|
|
203
|
+
|
|
204
|
+
const resultCodeOperations: Array<string> =
|
|
205
|
+
error?.response?.data?.extras?.result_codes?.operations || [];
|
|
206
|
+
|
|
207
|
+
expect(resultCodeOperations).toContain("op_no_trust");
|
|
208
|
+
}
|
|
209
|
+
}, 30000);
|
|
210
|
+
|
|
211
|
+
it("should return error for sending payment to invalid Muxed address", async () => {
|
|
212
|
+
const txBuilder = await stellar.transaction({
|
|
213
|
+
sourceAddress: testingDistributionKp,
|
|
214
|
+
baseFee: 100,
|
|
215
|
+
});
|
|
216
|
+
|
|
217
|
+
try {
|
|
218
|
+
txBuilder
|
|
219
|
+
.transfer(
|
|
220
|
+
// Invalid Muxed address ending in "XXXXXX"
|
|
221
|
+
"MBE3SABPOQFUSVCNDO5WNSS4N2KD7ZUFIYDRBP6Q3UBXBMYZFYWLSAAAAAAAAAAXXXXXX",
|
|
222
|
+
new NativeAssetId(),
|
|
223
|
+
"1",
|
|
224
|
+
)
|
|
225
|
+
.build();
|
|
226
|
+
} catch (error) {
|
|
227
|
+
const lowercaseError = error.toString().toLowerCase();
|
|
228
|
+
// Catches "Error: destination is invalid" error message
|
|
229
|
+
expect(lowercaseError.match(/destination.*invalid/)).toBeTruthy();
|
|
230
|
+
}
|
|
231
|
+
});
|
|
232
|
+
});
|
|
233
|
+
|
|
234
|
+
describe("Path Payment", () => {
|
|
235
|
+
let wallet: Wallet;
|
|
236
|
+
let stellar: Stellar;
|
|
237
|
+
let sourceKp;
|
|
238
|
+
let receivingKp;
|
|
239
|
+
const usdcAsset = new IssuedAssetId(
|
|
240
|
+
"USDC",
|
|
241
|
+
"GBBD47IF6LWK7P7MDEVSCWR7DPUWV3NY3DTQEVFL4NAT4AQH3ZLLFLA5",
|
|
242
|
+
);
|
|
243
|
+
beforeAll(async () => {
|
|
244
|
+
wallet = Wallet.TestNet();
|
|
245
|
+
stellar = wallet.stellar();
|
|
246
|
+
|
|
247
|
+
// set up accounts
|
|
248
|
+
sourceKp = SigningKeypair.fromSecret(
|
|
249
|
+
"SBTMCNDNPMJFEYUHLCAMFM5C2PWI7ZUI7PFMLI53O62CSSXFSAXEDTS6",
|
|
250
|
+
);
|
|
251
|
+
receivingKp = SigningKeypair.fromSecret(
|
|
252
|
+
"SDU4Z54AAFF3Y3GA6U27QSSYYX5FLDV6KWGFCCWSMSOSFWHSABJFBFOD",
|
|
253
|
+
);
|
|
254
|
+
try {
|
|
255
|
+
await stellar.server.loadAccount(sourceKp.publicKey);
|
|
256
|
+
await stellar.server.loadAccount(receivingKp.publicKey);
|
|
257
|
+
} catch (e) {
|
|
258
|
+
await axios.get(
|
|
259
|
+
"https://friendbot.stellar.org/?addr=" + sourceKp.publicKey,
|
|
260
|
+
);
|
|
261
|
+
await axios.get(
|
|
262
|
+
"https://friendbot.stellar.org/?addr=" + receivingKp.publicKey,
|
|
263
|
+
);
|
|
264
|
+
|
|
265
|
+
// add trustlines if new accounts
|
|
266
|
+
let txBuilder = await stellar.transaction({
|
|
267
|
+
sourceAddress: receivingKp,
|
|
268
|
+
});
|
|
269
|
+
let txn = txBuilder.addAssetSupport(usdcAsset).build();
|
|
270
|
+
receivingKp.sign(txn);
|
|
271
|
+
await stellar.submitTransaction(txn);
|
|
272
|
+
|
|
273
|
+
txBuilder = await stellar.transaction({
|
|
274
|
+
sourceAddress: sourceKp,
|
|
275
|
+
});
|
|
276
|
+
txn = txBuilder.addAssetSupport(usdcAsset).build();
|
|
277
|
+
sourceKp.sign(txn);
|
|
278
|
+
await stellar.submitTransaction(txn);
|
|
279
|
+
}
|
|
280
|
+
}, 20000);
|
|
281
|
+
|
|
282
|
+
it("should use path payment send", async () => {
|
|
283
|
+
const txBuilder = await stellar.transaction({
|
|
284
|
+
sourceAddress: sourceKp,
|
|
285
|
+
});
|
|
286
|
+
const txn = txBuilder
|
|
287
|
+
.pathPay({
|
|
288
|
+
destinationAddress: receivingKp.publicKey,
|
|
289
|
+
sendAsset: new NativeAssetId(),
|
|
290
|
+
destAsset: usdcAsset,
|
|
291
|
+
sendAmount: "5",
|
|
292
|
+
})
|
|
293
|
+
.build();
|
|
294
|
+
sourceKp.sign(txn);
|
|
295
|
+
const success = await stellar.submitTransaction(txn);
|
|
296
|
+
expect(success).toBe(true);
|
|
297
|
+
}, 15000);
|
|
298
|
+
|
|
299
|
+
it("should use path payment receive", async () => {
|
|
300
|
+
const txBuilder = await stellar.transaction({
|
|
301
|
+
sourceAddress: sourceKp,
|
|
302
|
+
});
|
|
303
|
+
const txn = txBuilder
|
|
304
|
+
.pathPay({
|
|
305
|
+
destinationAddress: receivingKp.publicKey,
|
|
306
|
+
sendAsset: new NativeAssetId(),
|
|
307
|
+
destAsset: usdcAsset,
|
|
308
|
+
destAmount: "5",
|
|
309
|
+
})
|
|
310
|
+
.build();
|
|
311
|
+
sourceKp.sign(txn);
|
|
312
|
+
const success = await stellar.submitTransaction(txn);
|
|
313
|
+
expect(success).toBe(true);
|
|
314
|
+
}, 15000);
|
|
315
|
+
|
|
316
|
+
it("should swap", async () => {
|
|
317
|
+
const txBuilder = await stellar.transaction({
|
|
318
|
+
sourceAddress: sourceKp,
|
|
319
|
+
});
|
|
320
|
+
const txn = txBuilder.swap(new NativeAssetId(), usdcAsset, "1").build();
|
|
321
|
+
sourceKp.sign(txn);
|
|
322
|
+
const success = await stellar.submitTransaction(txn);
|
|
323
|
+
expect(success).toBe(true);
|
|
324
|
+
}, 15000);
|
|
325
|
+
});
|
package/test/wallet.test.ts
CHANGED
|
@@ -18,6 +18,7 @@ import {
|
|
|
18
18
|
} from "../src/walletSdk/Auth/WalletSigner";
|
|
19
19
|
import { SigningKeypair } from "../src/walletSdk/Horizon/Account";
|
|
20
20
|
import { Sep24 } from "../src/walletSdk/Anchor/Sep24";
|
|
21
|
+
import { DomainSigner } from "../src/walletSdk/Auth/WalletSigner";
|
|
21
22
|
|
|
22
23
|
import { TransactionsResponse } from "../test/fixtures/TransactionsResponse";
|
|
23
24
|
|
|
@@ -1804,6 +1805,29 @@ describe("Anchor", () => {
|
|
|
1804
1805
|
});
|
|
1805
1806
|
});
|
|
1806
1807
|
|
|
1808
|
+
describe("DomainSigner", () => {
|
|
1809
|
+
it("should work", async () => {
|
|
1810
|
+
jest.spyOn(DefaultClient, "post").mockResolvedValue({
|
|
1811
|
+
data: {
|
|
1812
|
+
transaction:
|
|
1813
|
+
"AAAAAgAAAADVJRbxdB+qXZjUMLcrL/VVoS6megW1ReSxIO33pvO61AAAB9AAAAAAAAAAAQAAAAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEAAAAAAAAACwAAAAAAAAACAAAAAAAAAAA=",
|
|
1814
|
+
},
|
|
1815
|
+
});
|
|
1816
|
+
const signer = new DomainSigner("example url", {
|
|
1817
|
+
SampleHeader: "sample-header",
|
|
1818
|
+
});
|
|
1819
|
+
|
|
1820
|
+
const txn = await signer.signWithDomainAccount({
|
|
1821
|
+
transactionXDR: "test-xdr",
|
|
1822
|
+
networkPassphrase: "Test SDF Network ; September 2015",
|
|
1823
|
+
accountKp: SigningKeypair.fromSecret(
|
|
1824
|
+
"SBYAW5H46NNDGCECWMWWM32DE4DPNN3RHVMNTR3BXXZX2DJF6LZWBMWZ",
|
|
1825
|
+
),
|
|
1826
|
+
});
|
|
1827
|
+
expect(txn).toBeTruthy();
|
|
1828
|
+
});
|
|
1829
|
+
});
|
|
1830
|
+
|
|
1807
1831
|
describe("Http client", () => {
|
|
1808
1832
|
it("should work with http", async () => {
|
|
1809
1833
|
const accountKp = Keypair.fromSecret(
|