@stellar/typescript-wallet-sdk 1.7.0 → 1.8.0-beta.1731096658096

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 (39) hide show
  1. package/CHANGELOG.MD +8 -0
  2. package/examples/helpers/ask-question.ts +15 -0
  3. package/examples/sep10/.env.example +2 -0
  4. package/examples/sep10/README.md +34 -0
  5. package/examples/sep10/sep10Server.ts +53 -0
  6. package/examples/sep10/sep10Wallet.ts +45 -0
  7. package/examples/sep10/well_known/stellar.toml +18 -0
  8. package/examples/sep12/.env.example +2 -0
  9. package/examples/sep12/README.md +25 -0
  10. package/examples/sep12/sep12.ts +38 -0
  11. package/examples/sep24/sep24.ts +1 -15
  12. package/lib/bundle.js +3277 -1898
  13. package/lib/bundle.js.map +1 -1
  14. package/lib/bundle_browser.js +117 -48
  15. package/lib/bundle_browser.js.map +1 -1
  16. package/lib/walletSdk/Anchor/Sep24.d.ts +19 -7
  17. package/lib/walletSdk/Anchor/Sep38.d.ts +1 -0
  18. package/lib/walletSdk/Anchor/Sep6.d.ts +3 -1
  19. package/lib/walletSdk/Anchor/index.d.ts +5 -3
  20. package/lib/walletSdk/Customer/index.d.ts +12 -6
  21. package/lib/walletSdk/Exceptions/index.d.ts +3 -0
  22. package/lib/walletSdk/Horizon/Transaction/TransactionBuilder.d.ts +2 -1
  23. package/lib/walletSdk/Types/anchor.d.ts +14 -22
  24. package/lib/walletSdk/Types/sep12.d.ts +7 -1
  25. package/lib/walletSdk/Types/sep24.d.ts +21 -0
  26. package/package.json +8 -4
  27. package/src/walletSdk/Anchor/Sep24.ts +44 -12
  28. package/src/walletSdk/Anchor/Sep38.ts +1 -1
  29. package/src/walletSdk/Anchor/Sep6.ts +9 -2
  30. package/src/walletSdk/Anchor/index.ts +5 -10
  31. package/src/walletSdk/Customer/index.ts +33 -14
  32. package/src/walletSdk/Exceptions/index.ts +9 -0
  33. package/src/walletSdk/Horizon/Transaction/TransactionBuilder.ts +8 -1
  34. package/src/walletSdk/Types/anchor.ts +15 -20
  35. package/src/walletSdk/Types/sep12.ts +7 -1
  36. package/src/walletSdk/Types/sep24.ts +19 -0
  37. package/test/customer.test.ts +25 -15
  38. package/test/stellar.test.ts +155 -31
  39. package/test/wallet.test.ts +18 -1
@@ -15,6 +15,7 @@ import {
15
15
  WithdrawalTxMissingMemoError,
16
16
  WithdrawalTxNotPendingUserTransferStartError,
17
17
  WithdrawalTxMemoError,
18
+ WithdrawalTxMissingDestinationError,
18
19
  } from "../../Exceptions";
19
20
  import { StellarAssetId } from "../../Asset";
20
21
  import {
@@ -193,7 +194,7 @@ export class TransactionBuilder extends CommonTransactionBuilder<TransactionBuil
193
194
 
194
195
  /**
195
196
  * Swap assets using the Stellar network. This swaps using the
196
- * pathPaymentStrictReceive operation.
197
+ * pathPaymentStrictSend operation.
197
198
  * @param {StellarAssetId} fromAsset - The source asset to be sent.
198
199
  * @param {StellarAssetId} toAsset - The destination asset to receive.
199
200
  * @param {string} amount - The amount of the source asset to be sent.
@@ -241,6 +242,7 @@ export class TransactionBuilder extends CommonTransactionBuilder<TransactionBuil
241
242
  * @param {WithdrawTransaction} transaction - The withdrawal transaction.
242
243
  * @param {StellarAssetId} assetId - The asset ID to transfer.
243
244
  * @throws {WithdrawalTxNotPendingUserTransferStartError} If the withdrawal transaction status is not pending_user_transfer_start.
245
+ * @throws {WithdrawalTxMissingDestinationError} If the withdrawal transaction is missing withdraw_anchor_account field.
244
246
  * @throws {WithdrawalTxMissingMemoError} If the withdrawal transaction is missing a memo.
245
247
  * @throws {WithdrawalTxMemoError} If there is an issue with the withdrawal transaction memo.
246
248
  * @returns {TransactionBuilder} The TransactionBuilder instance.
@@ -255,6 +257,11 @@ export class TransactionBuilder extends CommonTransactionBuilder<TransactionBuil
255
257
  );
256
258
  }
257
259
 
260
+ // We can't send a payment if we don't know the destination address
261
+ if (!transaction.withdraw_anchor_account) {
262
+ throw new WithdrawalTxMissingDestinationError();
263
+ }
264
+
258
265
  if (!(transaction.withdraw_memo_type && transaction.withdraw_memo)) {
259
266
  throw new WithdrawalTxMissingMemoError();
260
267
  }
@@ -2,25 +2,20 @@ import { MemoType } from "@stellar/stellar-sdk";
2
2
  import { Optional } from "utility-types";
3
3
 
4
4
  import { AuthToken } from "./auth";
5
-
6
- export interface AnchorServiceInfo {
7
- deposit: AssetInfoMap;
8
- withdraw: AssetInfoMap;
9
- fee: { enabled: boolean };
10
- features: { account_creation: boolean; claimable_balances: boolean };
11
- }
12
-
13
- export interface AssetInfoMap {
14
- [asset_code: string]: AnchorServiceAsset;
15
- }
16
-
17
- export interface AnchorServiceAsset {
18
- enabled: boolean;
19
- min_amount: number;
20
- max_amount: number;
21
- fee_fixed: number;
22
- fee_percent: number;
23
- }
5
+ import { Sep24AssetInfo, Sep24AssetInfoMap, Sep24Info } from "./sep24";
6
+
7
+ /**
8
+ * @deprecated Please use Sep24Info interface instead.
9
+ */
10
+ export type AnchorServiceInfo = Sep24Info;
11
+ /**
12
+ * @deprecated Please use Sep24AssetInfoMap interface instead.
13
+ */
14
+ export type AssetInfoMap = Sep24AssetInfoMap;
15
+ /**
16
+ * @deprecated Please use Sep24AssetInfo interface instead.
17
+ */
18
+ export type AnchorServiceAsset = Sep24AssetInfo;
24
19
 
25
20
  export interface BaseTransaction {
26
21
  id: string;
@@ -60,7 +55,7 @@ export interface WithdrawTransaction extends ProcessingAnchorTransaction {
60
55
  to?: string;
61
56
  withdraw_memo?: string;
62
57
  withdraw_memo_type: MemoType;
63
- withdraw_anchor_account: string;
58
+ withdraw_anchor_account?: string;
64
59
  }
65
60
 
66
61
  export type Sep6Transaction = DepositTransaction &
@@ -2,6 +2,10 @@ export type CustomerInfoMap = {
2
2
  [key: string]: string;
3
3
  };
4
4
 
5
+ export type CustomerBinaryInfoMap = {
6
+ [key: string]: Buffer;
7
+ };
8
+
5
9
  export enum Sep12Status {
6
10
  ACCEPTED = "ACCEPTED",
7
11
  PROCESSING = "PROCESSING",
@@ -38,6 +42,7 @@ export type GetCustomerParams = {
38
42
  type?: string;
39
43
  memo?: string;
40
44
  lang?: string;
45
+ transactionId?: string;
41
46
  };
42
47
 
43
48
  export type GetCustomerResponse = {
@@ -50,10 +55,11 @@ export type GetCustomerResponse = {
50
55
 
51
56
  export type AddCustomerParams = {
52
57
  sep9Info?: CustomerInfoMap;
53
- sep9BinaryInfo?: CustomerInfoMap;
58
+ sep9BinaryInfo?: CustomerBinaryInfoMap;
54
59
  id?: string;
55
60
  memo?: string;
56
61
  type?: string;
62
+ transactionId?: string;
57
63
  };
58
64
 
59
65
  export type AddCustomerResponse = {
@@ -2,6 +2,25 @@ import { Memo } from "@stellar/stellar-sdk";
2
2
 
3
3
  import { AuthToken } from "./auth";
4
4
 
5
+ export interface Sep24Info {
6
+ deposit: Sep24AssetInfoMap;
7
+ withdraw: Sep24AssetInfoMap;
8
+ fee: { enabled: boolean };
9
+ features: { account_creation: boolean; claimable_balances: boolean };
10
+ }
11
+
12
+ export interface Sep24AssetInfoMap {
13
+ [asset_code: string]: Sep24AssetInfo;
14
+ }
15
+
16
+ export interface Sep24AssetInfo {
17
+ enabled: boolean;
18
+ min_amount: number;
19
+ max_amount: number;
20
+ fee_fixed: number;
21
+ fee_percent: number;
22
+ }
23
+
5
24
  export enum FLOW_TYPE {
6
25
  DEPOSIT = "deposit",
7
26
  WITHDRAW = "withdraw",
@@ -1,9 +1,9 @@
1
- import { Wallet } from "../src";
1
+ import { Sep12, SigningKeypair, Wallet } from "../src";
2
2
  import axios from "axios";
3
3
  import { getRandomString } from "./utils";
4
4
 
5
- let wallet;
6
- let accountKp;
5
+ let wallet: Wallet;
6
+ let accountKp: SigningKeypair;
7
7
 
8
8
  describe("Customer", () => {
9
9
  beforeAll(async () => {
@@ -22,31 +22,36 @@ describe("Customer", () => {
22
22
  const auth = await anchor.sep10();
23
23
  const authToken = await auth.authenticate({ accountKp });
24
24
 
25
- const sep12 = await anchor.sep12(authToken);
25
+ const sep12: Sep12 = await anchor.sep12(authToken);
26
26
  const customerType = "sep31-receiver";
27
27
  const customerEmail = `${getRandomString(6)}@gmail.com`;
28
28
 
29
29
  // Add
30
- let resp = await sep12.add({
30
+ const addResp = await sep12.add({
31
31
  sep9Info: {
32
32
  first_name: "john",
33
33
  last_name: "smith",
34
34
  email_address: customerEmail,
35
35
  type: customerType,
36
36
  },
37
+ transactionId: "abcd1234",
37
38
  });
38
- expect(resp.id).toBeTruthy();
39
- const { id } = resp;
39
+ expect(addResp.id).toBeTruthy();
40
+ const { id } = addResp;
40
41
 
41
42
  // Get
42
- resp = await sep12.getCustomer({ id, type: customerType });
43
- expect(Object.keys(resp).sort()).toEqual(
43
+ const getResp = await sep12.getCustomer({
44
+ id,
45
+ type: customerType,
46
+ transactionId: "abcd1234",
47
+ });
48
+ expect(Object.keys(getResp).sort()).toEqual(
44
49
  ["id", "provided_fields", "fields", "status"].sort(),
45
50
  );
46
- expect(Object.keys(resp?.provided_fields).sort()).toEqual(
51
+ expect(Object.keys(getResp?.provided_fields).sort()).toEqual(
47
52
  ["first_name", "last_name", "email_address"].sort(),
48
53
  );
49
- expect(Object.keys(resp?.fields).sort()).toEqual(
54
+ expect(Object.keys(getResp?.fields).sort()).toEqual(
50
55
  [
51
56
  "bank_account_number",
52
57
  "bank_number",
@@ -56,7 +61,7 @@ describe("Customer", () => {
56
61
  );
57
62
 
58
63
  // Update
59
- resp = await sep12.update({
64
+ const updateResp = await sep12.update({
60
65
  sep9Info: {
61
66
  first_name: "j",
62
67
  last_name: "s",
@@ -69,12 +74,17 @@ describe("Customer", () => {
69
74
  photo_id_back: Buffer.from("test-back-image"),
70
75
  },
71
76
  id,
77
+ transactionId: "abcd1234",
72
78
  });
73
- expect(resp.id).toBeTruthy();
79
+ expect(updateResp.id).toBeTruthy();
74
80
 
75
81
  // Get again, check that the provided fields updated
76
- resp = await sep12.getCustomer({ id, type: customerType });
77
- expect(Object.keys(resp.fields).length).toBe(0);
82
+ const getResp2 = await sep12.getCustomer({
83
+ id,
84
+ type: customerType,
85
+ transactionId: "abcd1234",
86
+ });
87
+ expect(Object.keys(getResp2.fields).length).toBe(0);
78
88
 
79
89
  // Delete
80
90
  await sep12.delete();
@@ -13,6 +13,11 @@ import {
13
13
  Assets,
14
14
  } from "../src/walletSdk/Asset";
15
15
  import { TransactionStatus, WithdrawTransaction } from "../src/walletSdk/Types";
16
+ import {
17
+ WithdrawalTxMissingDestinationError,
18
+ WithdrawalTxMissingMemoError,
19
+ WithdrawalTxNotPendingUserTransferStartError,
20
+ } from "../src/walletSdk/Exceptions";
16
21
 
17
22
  let wal: Wallet;
18
23
  let stellar: Stellar;
@@ -31,6 +36,7 @@ describe("Stellar", () => {
31
36
  await stellar.fundTestnetAccount(kp.publicKey);
32
37
  }
33
38
  }, 10000);
39
+
34
40
  it("should create and submit a transaction", async () => {
35
41
  const now = Math.floor(Date.now() / 1000) - 5;
36
42
 
@@ -190,34 +196,127 @@ describe("Stellar", () => {
190
196
  const tx = stellar.decodeTransaction(txnXdr);
191
197
  kp.sign(tx);
192
198
  });
193
- it("should transfer withdrawal transaction", async () => {
194
- const memoExamples = [
195
- {
196
- type: "text",
197
- value: "example text",
198
- },
199
- {
200
- type: "id",
201
- value: "12345",
202
- },
203
- {
204
- type: "hash",
205
- value: "AAAAAAAAAAAAAAAAAAAAAMAP+8deo0TViBD09TfOBY0=",
206
- },
207
- {
208
- type: "hash",
209
- value: "MV9b23bQeMQ7isAGTkoBZGErH853yGk0W/yUx1iU7dM=",
210
- },
211
- ];
212
199
 
213
- for (const memoExample of memoExamples) {
200
+ it("should return recommended fee", async () => {
201
+ const fee = await stellar.getRecommendedFee();
202
+ expect(fee).toBeTruthy();
203
+ });
204
+
205
+ describe("TransactionBuilder/transferWithdrawalTransaction", () => {
206
+ it("should transfer withdrawal transaction", async () => {
207
+ const memoExamples = [
208
+ {
209
+ type: "text",
210
+ value: "example text",
211
+ },
212
+ {
213
+ type: "id",
214
+ value: "12345",
215
+ },
216
+ {
217
+ type: "hash",
218
+ value: "AAAAAAAAAAAAAAAAAAAAAMAP+8deo0TViBD09TfOBY0=",
219
+ },
220
+ {
221
+ type: "hash",
222
+ value: "MV9b23bQeMQ7isAGTkoBZGErH853yGk0W/yUx1iU7dM=",
223
+ },
224
+ ];
225
+
226
+ for (const memoExample of memoExamples) {
227
+ const walletTransaction = {
228
+ id: "db15d166-5a5e-4d5c-ba5d-271c32cd8cf0",
229
+ kind: "withdrawal",
230
+ status: TransactionStatus.pending_user_transfer_start,
231
+ amount_in: "50.55",
232
+ withdraw_memo_type: memoExample.type,
233
+ withdraw_memo: memoExample.value,
234
+ withdraw_anchor_account:
235
+ "GCSGSR6KQQ5BP2FXVPWRL6SWPUSFWLVONLIBJZUKTVQB5FYJFVL6XOXE",
236
+ } as WithdrawTransaction;
237
+
238
+ const asset = new IssuedAssetId(
239
+ "USDC",
240
+ "GBBD47IF6LWK7P7MDEVSCWR7DPUWV3NY3DTQEVFL4NAT4AQH3ZLLFLA5",
241
+ );
242
+
243
+ const txBuilder = await stellar.transaction({
244
+ sourceAddress: kp,
245
+ baseFee: 100,
246
+ });
247
+
248
+ const txn = txBuilder
249
+ .transferWithdrawalTransaction(walletTransaction, asset)
250
+ .build();
251
+ expect(txn).toBeTruthy();
252
+ }
253
+ }, 20000);
254
+
255
+ it("should throw if tx not in pending_user_transfer_start status", async () => {
256
+ const walletTransaction = {
257
+ id: "db15d166-5a5e-4d5c-ba5d-271c32cd8cf0",
258
+ kind: "withdrawal",
259
+ status: TransactionStatus.pending_anchor,
260
+ amount_in: "50.55",
261
+ withdraw_memo_type: "text",
262
+ withdraw_memo: "example text",
263
+ withdraw_anchor_account:
264
+ "GCSGSR6KQQ5BP2FXVPWRL6SWPUSFWLVONLIBJZUKTVQB5FYJFVL6XOXE",
265
+ } as WithdrawTransaction;
266
+
267
+ const asset = new IssuedAssetId(
268
+ "USDC",
269
+ "GBBD47IF6LWK7P7MDEVSCWR7DPUWV3NY3DTQEVFL4NAT4AQH3ZLLFLA5",
270
+ );
271
+
272
+ const txBuilder = await stellar.transaction({
273
+ sourceAddress: kp,
274
+ baseFee: 100,
275
+ });
276
+
277
+ expect(() => {
278
+ txBuilder
279
+ .transferWithdrawalTransaction(walletTransaction, asset)
280
+ .build();
281
+ }).toThrowError(WithdrawalTxNotPendingUserTransferStartError);
282
+ }, 5000);
283
+
284
+ it("should throw if tx is missing withdraw_anchor_account", async () => {
285
+ const walletTransaction = {
286
+ id: "db15d166-5a5e-4d5c-ba5d-271c32cd8cf0",
287
+ kind: "withdrawal",
288
+ status: TransactionStatus.pending_user_transfer_start,
289
+ amount_in: "50.55",
290
+ withdraw_memo_type: "text",
291
+ withdraw_memo: "example text",
292
+ withdraw_anchor_account: null,
293
+ } as WithdrawTransaction;
294
+
295
+ const asset = new IssuedAssetId(
296
+ "USDC",
297
+ "GBBD47IF6LWK7P7MDEVSCWR7DPUWV3NY3DTQEVFL4NAT4AQH3ZLLFLA5",
298
+ );
299
+
300
+ const txBuilder = await stellar.transaction({
301
+ sourceAddress: kp,
302
+ baseFee: 100,
303
+ });
304
+
305
+ expect(() => {
306
+ txBuilder
307
+ .transferWithdrawalTransaction(walletTransaction, asset)
308
+ .build();
309
+ }).toThrowError(WithdrawalTxMissingDestinationError);
310
+ }, 5000);
311
+
312
+ it("should throw if tx is missing withdraw_memo_type", async () => {
214
313
  const walletTransaction = {
215
314
  id: "db15d166-5a5e-4d5c-ba5d-271c32cd8cf0",
216
315
  kind: "withdrawal",
217
316
  status: TransactionStatus.pending_user_transfer_start,
218
317
  amount_in: "50.55",
219
- withdraw_memo_type: memoExample.type,
220
- withdraw_memo: memoExample.value,
318
+ withdraw_memo_type: null,
319
+ withdraw_memo: "example text",
221
320
  withdraw_anchor_account:
222
321
  "GCSGSR6KQQ5BP2FXVPWRL6SWPUSFWLVONLIBJZUKTVQB5FYJFVL6XOXE",
223
322
  } as WithdrawTransaction;
@@ -232,16 +331,41 @@ describe("Stellar", () => {
232
331
  baseFee: 100,
233
332
  });
234
333
 
235
- const txn = txBuilder
236
- .transferWithdrawalTransaction(walletTransaction, asset)
237
- .build();
238
- expect(txn).toBeTruthy();
239
- }
240
- }, 20000);
334
+ expect(() => {
335
+ txBuilder
336
+ .transferWithdrawalTransaction(walletTransaction, asset)
337
+ .build();
338
+ }).toThrowError(WithdrawalTxMissingMemoError);
339
+ }, 5000);
241
340
 
242
- it("should return recommended fee", async () => {
243
- const fee = await stellar.getRecommendedFee();
244
- expect(fee).toBeTruthy();
341
+ it("should throw if tx is missing withdraw_memo", async () => {
342
+ const walletTransaction = {
343
+ id: "db15d166-5a5e-4d5c-ba5d-271c32cd8cf0",
344
+ kind: "withdrawal",
345
+ status: TransactionStatus.pending_user_transfer_start,
346
+ amount_in: "50.55",
347
+ withdraw_memo_type: "text",
348
+ withdraw_memo: null,
349
+ withdraw_anchor_account:
350
+ "GCSGSR6KQQ5BP2FXVPWRL6SWPUSFWLVONLIBJZUKTVQB5FYJFVL6XOXE",
351
+ } as WithdrawTransaction;
352
+
353
+ const asset = new IssuedAssetId(
354
+ "USDC",
355
+ "GBBD47IF6LWK7P7MDEVSCWR7DPUWV3NY3DTQEVFL4NAT4AQH3ZLLFLA5",
356
+ );
357
+
358
+ const txBuilder = await stellar.transaction({
359
+ sourceAddress: kp,
360
+ baseFee: 100,
361
+ });
362
+
363
+ expect(() => {
364
+ txBuilder
365
+ .transferWithdrawalTransaction(walletTransaction, asset)
366
+ .build();
367
+ }).toThrowError(WithdrawalTxMissingMemoError);
368
+ }, 5000);
245
369
  });
246
370
  });
247
371
 
@@ -156,7 +156,7 @@ describe("Anchor", () => {
156
156
  expect(signedByClient).toBe(true);
157
157
  expect(signedByDomain).toBe(true);
158
158
  });
159
- it("should get anchor services info", async () => {
159
+ it("(deprecated) should get anchor services info", async () => {
160
160
  let serviceInfo = await anchor.sep24().getServicesInfo();
161
161
  expect(serviceInfo.deposit).toBeTruthy();
162
162
  expect(serviceInfo.withdraw).toBeTruthy();
@@ -167,6 +167,23 @@ describe("Anchor", () => {
167
167
  expect(serviceInfo.withdraw).toBeTruthy();
168
168
  });
169
169
 
170
+ it("should get anchor Sep-24 info", async () => {
171
+ const sep24Info = await anchor.sep24().info();
172
+ expect(sep24Info.deposit).toBeTruthy();
173
+ expect(sep24Info.withdraw).toBeTruthy();
174
+ });
175
+
176
+ it("should get anchor Sep-6 info", async () => {
177
+ const sep6Info = await anchor.sep6().info();
178
+ expect(sep6Info["deposit-exchange"]).toBeTruthy();
179
+ expect(sep6Info["withdraw-exchange"]).toBeTruthy();
180
+ });
181
+
182
+ it("should get anchor Sep-38 info", async () => {
183
+ const sep38Info = await anchor.sep38().info();
184
+ expect(sep38Info.assets).toBeTruthy();
185
+ });
186
+
170
187
  it("should give interactive deposit url", async () => {
171
188
  const assetCode = "SRT";
172
189
  const resp = await anchor.sep24().deposit({