@subwallet/extension-base 1.0.7-2 → 1.0.9-0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (57) hide show
  1. package/background/KoniTypes.d.ts +3 -1
  2. package/background/KoniTypes.js +1 -0
  3. package/background/errors/TransactionError.js +5 -1
  4. package/cjs/background/KoniTypes.js +1 -0
  5. package/cjs/background/errors/TransactionError.js +4 -0
  6. package/cjs/constants/index.js +6 -3
  7. package/cjs/koni/api/dotsama/balance.js +5 -2
  8. package/cjs/koni/api/dotsama/crowdloan.js +1 -1
  9. package/cjs/koni/api/dotsama/transfer.js +19 -5
  10. package/cjs/koni/api/tokens/wasm/index.js +7 -0
  11. package/cjs/koni/api/xcm/polkadotXcm.js +18 -37
  12. package/cjs/koni/api/xcm/utils.js +78 -11
  13. package/cjs/koni/api/xcm/xTokens.js +4 -33
  14. package/cjs/koni/api/xcm/xcmPallet.js +4 -36
  15. package/cjs/koni/background/handlers/Extension.js +83 -25
  16. package/cjs/koni/background/handlers/State.js +1 -1
  17. package/cjs/packageInfo.js +1 -1
  18. package/cjs/services/chain-service/constants.js +9 -7
  19. package/cjs/services/chain-service/index.js +19 -15
  20. package/cjs/services/chain-service/utils.js +1 -5
  21. package/cjs/services/history-service/constants/index.js +13 -0
  22. package/cjs/services/history-service/subsquid-multi-chain-history.js +38 -3
  23. package/cjs/services/transaction-service/helpers/index.js +45 -2
  24. package/cjs/services/transaction-service/index.js +58 -24
  25. package/cjs/utils/eth/parseTransaction/index.js +69 -59
  26. package/cjs/utils/number.js +112 -0
  27. package/constants/index.d.ts +1 -0
  28. package/constants/index.js +1 -0
  29. package/koni/api/dotsama/balance.js +4 -2
  30. package/koni/api/dotsama/crowdloan.js +2 -2
  31. package/koni/api/dotsama/transfer.js +19 -5
  32. package/koni/api/tokens/wasm/index.js +7 -0
  33. package/koni/api/xcm/polkadotXcm.js +20 -39
  34. package/koni/api/xcm/utils.d.ts +36 -3
  35. package/koni/api/xcm/utils.js +72 -11
  36. package/koni/api/xcm/xTokens.js +6 -35
  37. package/koni/api/xcm/xcmPallet.js +5 -35
  38. package/koni/background/handlers/Extension.js +82 -24
  39. package/koni/background/handlers/State.js +2 -2
  40. package/package.json +18 -8
  41. package/packageInfo.js +1 -1
  42. package/services/chain-service/constants.d.ts +2 -0
  43. package/services/chain-service/constants.js +9 -7
  44. package/services/chain-service/index.js +13 -8
  45. package/services/chain-service/utils.d.ts +0 -1
  46. package/services/chain-service/utils.js +1 -4
  47. package/services/history-service/constants/index.d.ts +2 -0
  48. package/services/history-service/constants/index.js +5 -0
  49. package/services/history-service/subsquid-multi-chain-history.d.ts +1 -1
  50. package/services/history-service/subsquid-multi-chain-history.js +36 -3
  51. package/services/transaction-service/helpers/index.d.ts +2 -0
  52. package/services/transaction-service/helpers/index.js +42 -0
  53. package/services/transaction-service/index.js +54 -20
  54. package/services/transaction-service/types.d.ts +2 -2
  55. package/utils/eth/parseTransaction/index.js +69 -59
  56. package/utils/number.d.ts +9 -0
  57. package/utils/number.js +100 -0
@@ -10,9 +10,10 @@ var _TransactionError = require("@subwallet/extension-base/background/errors/Tra
10
10
  var _KoniTypes = require("@subwallet/extension-base/background/KoniTypes");
11
11
  var _TransactionWarning = require("@subwallet/extension-base/background/warnings/TransactionWarning");
12
12
  var _constants = require("@subwallet/extension-base/constants");
13
+ var _constants2 = require("@subwallet/extension-base/services/chain-service/constants");
13
14
  var _utils = require("@subwallet/extension-base/services/chain-service/utils");
14
- var _constants2 = require("@subwallet/extension-base/services/request-service/constants");
15
- var _constants3 = require("@subwallet/extension-base/services/transaction-service/constants");
15
+ var _constants3 = require("@subwallet/extension-base/services/request-service/constants");
16
+ var _constants4 = require("@subwallet/extension-base/services/transaction-service/constants");
16
17
  var _eventParser = require("@subwallet/extension-base/services/transaction-service/event-parser");
17
18
  var _helpers = require("@subwallet/extension-base/services/transaction-service/helpers");
18
19
  var _utils2 = require("@subwallet/extension-base/services/transaction-service/utils");
@@ -116,6 +117,10 @@ class TransactionService {
116
117
  }
117
118
  }
118
119
  } catch (e) {
120
+ const error = e;
121
+ if (error.message.includes('gas required exceeds allowance')) {
122
+ validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.NOT_ENOUGH_BALANCE));
123
+ }
119
124
  estimateFee.value = '0';
120
125
  }
121
126
  }
@@ -142,16 +147,22 @@ class TransactionService {
142
147
  const balanceNum = parseInt(balance.value);
143
148
  const edNum = parseInt(existentialDeposit);
144
149
  const transferNativeNum = parseInt(transferNative);
145
- if (!isTransferAll) {
146
- if (transferNativeNum + feeNum > balanceNum) {
150
+ if (transferNativeNum + feeNum > balanceNum) {
151
+ if (!isTransferAll) {
147
152
  validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.NOT_ENOUGH_BALANCE));
148
153
  } else {
149
- if (balanceNum - (transferNativeNum + feeNum) <= edNum) {
150
- if (edAsWarning) {
151
- validationResponse.warnings.push(new _TransactionWarning.TransactionWarning(_KoniTypes.BasicTxWarningCode.NOT_ENOUGH_EXISTENTIAL_DEPOSIT, ''));
152
- } else {
153
- validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.NOT_ENOUGH_EXISTENTIAL_DEPOSIT, ''));
154
- }
154
+ if ([..._constants2._TRANSFER_CHAIN_GROUP.acala, ..._constants2._TRANSFER_CHAIN_GROUP.genshiro, ..._constants2._TRANSFER_CHAIN_GROUP.bitcountry, ..._constants2._TRANSFER_CHAIN_GROUP.statemine].includes(chain)) {
155
+ // Chain not have transfer all function
156
+ validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.NOT_ENOUGH_BALANCE));
157
+ }
158
+ }
159
+ }
160
+ if (!isTransferAll) {
161
+ if (balanceNum - (transferNativeNum + feeNum) < edNum) {
162
+ if (edAsWarning) {
163
+ validationResponse.warnings.push(new _TransactionWarning.TransactionWarning(_KoniTypes.BasicTxWarningCode.NOT_ENOUGH_EXISTENTIAL_DEPOSIT, ''));
164
+ } else {
165
+ validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.NOT_ENOUGH_EXISTENTIAL_DEPOSIT, ''));
155
166
  }
156
167
  }
157
168
  }
@@ -172,7 +183,7 @@ class TransactionService {
172
183
  updatedAt: new Date().getTime(),
173
184
  errors: transaction.errors || [],
174
185
  warnings: transaction.warnings || [],
175
- url: transaction.url || _constants2.EXTENSION_REQUEST_URL,
186
+ url: transaction.url || _constants3.EXTENSION_REQUEST_URL,
176
187
  status: _KoniTypes.ExtrinsicStatus.QUEUED,
177
188
  isInternal,
178
189
  id: transactionId,
@@ -213,6 +224,7 @@ class TransactionService {
213
224
  // @ts-ignore
214
225
  'transaction' in validatedTransaction && delete validatedTransaction.transaction;
215
226
  'additionalValidator' in validatedTransaction && delete validatedTransaction.additionalValidator;
227
+ 'eventsHandler' in validatedTransaction && delete validatedTransaction.eventsHandler;
216
228
  return validatedTransaction;
217
229
  }
218
230
  validatedTransaction.warnings = [];
@@ -234,11 +246,15 @@ class TransactionService {
234
246
  // @ts-ignore
235
247
  'transaction' in validatedTransaction && delete validatedTransaction.transaction;
236
248
  'additionalValidator' in validatedTransaction && delete validatedTransaction.additionalValidator;
249
+ 'eventsHandler' in validatedTransaction && delete validatedTransaction.eventsHandler;
237
250
  return validatedTransaction;
238
251
  }
239
252
  async sendTransaction(transaction) {
240
253
  // Send Transaction
241
254
  const emitter = transaction.chainType === 'substrate' ? this.signAndSendSubstrateTransaction(transaction) : await this.signAndSendEvmTransaction(transaction);
255
+ const {
256
+ eventsHandler
257
+ } = transaction;
242
258
  emitter.on('signed', data => {
243
259
  this.onSigned(data);
244
260
  });
@@ -262,6 +278,7 @@ class TransactionService {
262
278
 
263
279
  // Todo: handle any event with transaction.eventsHandler
264
280
 
281
+ eventsHandler === null || eventsHandler === void 0 ? void 0 : eventsHandler(emitter);
265
282
  return emitter;
266
283
  }
267
284
  removeTransaction(id) {
@@ -288,6 +305,7 @@ class TransactionService {
288
305
  }
289
306
  transactionToHistories(id, startBlock, nonce, eventLogs) {
290
307
  const transaction = this.getTransaction(id);
308
+ const extrinsicType = transaction.extrinsicType;
291
309
  const historyItem = {
292
310
  origin: 'app',
293
311
  chain: transaction.chain,
@@ -318,7 +336,7 @@ class TransactionService {
318
336
  };
319
337
 
320
338
  // Fill data by extrinsicType
321
- switch (transaction.extrinsicType) {
339
+ switch (extrinsicType) {
322
340
  case _KoniTypes.ExtrinsicType.TRANSFER_BALANCE:
323
341
  {
324
342
  const inputData = (0, _utils2.parseTransactionData)(transaction.data);
@@ -357,9 +375,10 @@ class TransactionService {
357
375
  };
358
376
 
359
377
  // @ts-ignore
360
- // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment
361
378
  historyItem.additionalInfo = {
362
- destinationChain: (inputData === null || inputData === void 0 ? void 0 : inputData.destinationNetworkKey) || ''
379
+ destinationChain: (inputData === null || inputData === void 0 ? void 0 : inputData.destinationNetworkKey) || '',
380
+ originalChain: inputData.originNetworkKey || '',
381
+ fee: transaction.estimateFee
363
382
  };
364
383
  eventLogs && (0, _eventParser.parseXcmEventLogs)(historyItem, eventLogs, transaction.chain, sendingTokenInfo, chainInfo);
365
384
  }
@@ -458,11 +477,22 @@ class TransactionService {
458
477
  // Return one more history record if transaction send to account in the wallets
459
478
  const toAccount = (historyItem === null || historyItem === void 0 ? void 0 : historyItem.to) && _uiKeyring.default.getPair(historyItem.to);
460
479
  if (toAccount) {
461
- return [historyItem, {
480
+ const receiverHistory = {
462
481
  ...historyItem,
463
482
  address: toAccount.address,
464
483
  direction: _KoniTypes.TransactionDirection.RECEIVED
465
- }];
484
+ };
485
+ switch (extrinsicType) {
486
+ case _KoniTypes.ExtrinsicType.TRANSFER_XCM:
487
+ {
488
+ const inputData = (0, _utils2.parseTransactionData)(transaction.data);
489
+ receiverHistory.chain = inputData.destinationNetworkKey;
490
+ break;
491
+ }
492
+ default:
493
+ break;
494
+ }
495
+ return [historyItem, receiverHistory];
466
496
  }
467
497
  } catch (e) {
468
498
  console.warn(e);
@@ -554,10 +584,11 @@ class TransactionService {
554
584
  blockNumber: blockNumber || 0,
555
585
  blockHash: blockHash || ''
556
586
  }).catch(console.error);
587
+ const info = (0, _util.isHex)(extrinsicHash) ? extrinsicHash : (0, _helpers.getBaseTransactionInfo)(transaction, this.chainService.getChainInfoMap());
557
588
  this.notificationService.notify({
558
589
  type: _KoniTypes.NotificationType.SUCCESS,
559
590
  title: 'Transaction completed',
560
- message: `Transaction ${transaction === null || transaction === void 0 ? void 0 : transaction.extrinsicHash} completed`,
591
+ message: `Transaction ${info} completed`,
561
592
  action: {
562
593
  url: this.getTransactionLink(id)
563
594
  },
@@ -589,10 +620,11 @@ class TransactionService {
589
620
  blockNumber: blockNumber || 0,
590
621
  blockHash: blockHash || ''
591
622
  }).catch(console.error);
623
+ const info = (0, _util.isHex)(transaction === null || transaction === void 0 ? void 0 : transaction.extrinsicHash) ? transaction === null || transaction === void 0 ? void 0 : transaction.extrinsicHash : (0, _helpers.getBaseTransactionInfo)(transaction, this.chainService.getChainInfoMap());
592
624
  this.notificationService.notify({
593
625
  type: _KoniTypes.NotificationType.ERROR,
594
626
  title: 'Transaction failed',
595
- message: `Transaction ${transaction === null || transaction === void 0 ? void 0 : transaction.extrinsicHash} failed`,
627
+ message: `Transaction ${info} failed`,
596
628
  action: {
597
629
  url: this.getTransactionLink(id)
598
630
  },
@@ -687,9 +719,10 @@ class TransactionService {
687
719
  const eventData = {
688
720
  id,
689
721
  errors: [],
690
- warnings: []
722
+ warnings: [],
723
+ extrinsicHash: id
691
724
  };
692
- this.requestService.addConfirmation(id, url || _constants2.EXTENSION_REQUEST_URL, 'evmSendTransactionRequest', payload, {}).then(async _ref7 => {
725
+ this.requestService.addConfirmation(id, url || _constants3.EXTENSION_REQUEST_URL, 'evmSendTransactionRequest', payload, {}).then(async _ref7 => {
693
726
  let {
694
727
  isApproved,
695
728
  payload
@@ -760,12 +793,13 @@ class TransactionService {
760
793
  const eventData = {
761
794
  id,
762
795
  errors: [],
763
- warnings: []
796
+ warnings: [],
797
+ extrinsicHash: id
764
798
  };
765
799
  transaction.signAsync(address, {
766
800
  signer: {
767
801
  signPayload: async payload => {
768
- const signing = await this.requestService.signInternalTransaction(id, address, url || _constants2.EXTENSION_REQUEST_URL, payload);
802
+ const signing = await this.requestService.signInternalTransaction(id, address, url || _constants3.EXTENSION_REQUEST_URL, payload);
769
803
  return {
770
804
  id: new Date().getTime(),
771
805
  signature: signing.signature
@@ -790,7 +824,7 @@ class TransactionService {
790
824
  }
791
825
  if (txState.status.isInBlock) {
792
826
  eventData.eventLogs = txState.events;
793
- if (!eventData.extrinsicHash || eventData.extrinsicHash === '') {
827
+ if (!eventData.extrinsicHash || eventData.extrinsicHash === '' || !(0, _util.isHex)(eventData.extrinsicHash)) {
794
828
  eventData.extrinsicHash = txState.txHash.toHex();
795
829
  eventData.blockHash = txState.status.asInBlock.toHex();
796
830
  emitter.emit('extrinsicHash', eventData);
@@ -841,7 +875,7 @@ class TransactionService {
841
875
  emitter.emit('error', eventData);
842
876
  clearTimeout(timeout);
843
877
  }
844
- }, _constants3.TRANSACTION_TIMEOUT);
878
+ }, _constants4.TRANSACTION_TIMEOUT);
845
879
  emitter.once('success', () => {
846
880
  clearTimeout(timeout);
847
881
  });
@@ -107,44 +107,59 @@ const isContractAddress = async (address, evmApi) => {
107
107
  }
108
108
  };
109
109
  exports.isContractAddress = isContractAddress;
110
+ const parseInputWithAbi = (input, abi) => {
111
+ const decoder = new _base.InputDataDecoder(abi);
112
+ const raw = decoder.decodeData(input);
113
+ if (raw.method && raw.methodName) {
114
+ const temp = {
115
+ method: raw.method,
116
+ methodName: raw.methodName,
117
+ args: []
118
+ };
119
+ raw.types.forEach((type, index) => {
120
+ temp.args.push(parseResult(type, raw.inputs[index], raw.names[index]));
121
+ });
122
+ return temp;
123
+ } else {
124
+ return null;
125
+ }
126
+ };
110
127
  const parseContractInput = async (input, contractAddress, network) => {
111
- let result = input;
112
-
113
- // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment
114
- const _ABIs = [...ABIs];
128
+ for (const abi of ABIs) {
129
+ const temp = parseInputWithAbi(input, abi);
130
+ if (temp) {
131
+ return {
132
+ result: temp
133
+ };
134
+ }
135
+ }
115
136
  if (contractAddress && network) {
137
+ console.log('parseOnline');
116
138
  if ((0, _utils._getEvmAbiExplorer)(network)) {
117
- const res = await _axios.default.get((0, _utils._getEvmAbiExplorer)(network), {
118
- params: {
119
- address: contractAddress
120
- }
121
- });
139
+ try {
140
+ const res = await _axios.default.get((0, _utils._getEvmAbiExplorer)(network), {
141
+ params: {
142
+ address: contractAddress
143
+ },
144
+ timeout: 3000
145
+ });
122
146
 
123
- // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
124
- if (res.status === 200 && res.data.status === '1') {
125
147
  // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
126
- _ABIs.unshift(res.data.result);
127
- }
128
- }
129
- }
130
- for (const abi of _ABIs) {
131
- const decoder = new _base.InputDataDecoder(abi);
132
- const raw = decoder.decodeData(input);
133
- if (raw.method && raw.methodName) {
134
- const temp = {
135
- method: raw.method,
136
- methodName: raw.methodName,
137
- args: []
138
- };
139
- raw.types.forEach((type, index) => {
140
- temp.args.push(parseResult(type, raw.inputs[index], raw.names[index]));
141
- });
142
- result = temp;
143
- break;
148
+ if (res.status === 200 && res.data.status === '1') {
149
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access,@typescript-eslint/no-unsafe-assignment
150
+ const abi = res.data.result;
151
+ const temp = parseInputWithAbi(input, abi);
152
+ if (temp) {
153
+ return {
154
+ result: temp
155
+ };
156
+ }
157
+ }
158
+ } catch (e) {}
144
159
  }
145
160
  }
146
161
  return {
147
- result
162
+ result: input
148
163
  };
149
164
  };
150
165
  exports.parseContractInput = parseContractInput;
@@ -187,43 +202,38 @@ const parseEvmRlp = async (data, networkMap, evmApiMap) => {
187
202
  nonce: new _bignumber.default(tx.nonce).toNumber()
188
203
  };
189
204
  const network = getChainInfoByChainId(networkMap, parseInt(tx.ethereumChainId));
190
-
191
- // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment
192
- const _ABIs = [...ABIs];
205
+ for (const abi of ABIs) {
206
+ const temp = parseInputWithAbi(tx.data, abi);
207
+ if (temp) {
208
+ result.data = temp;
209
+ return result;
210
+ }
211
+ }
193
212
  if (tx.action && network) {
194
213
  if (await isContractAddress(tx.action, evmApiMap[network.slug])) {
195
214
  if ((0, _utils._getEvmAbiExplorer)(network) !== '') {
196
- const res = await _axios.default.get((0, _utils._getEvmAbiExplorer)(network), {
197
- params: {
198
- address: tx.action
199
- }
200
- });
215
+ try {
216
+ const res = await _axios.default.get((0, _utils._getEvmAbiExplorer)(network), {
217
+ params: {
218
+ address: tx.action
219
+ },
220
+ timeout: 2000
221
+ });
201
222
 
202
- // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
203
- if (res.status === 200 && res.data.status === '1') {
204
223
  // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
205
- _ABIs.unshift(res.data.result);
206
- }
224
+ if (res.status === 200 && res.data.status === '1') {
225
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access,@typescript-eslint/no-unsafe-assignment
226
+ const abi = res.data.result;
227
+ const temp = parseInputWithAbi(tx.data, abi);
228
+ if (temp) {
229
+ result.data = temp;
230
+ return result;
231
+ }
232
+ }
233
+ } catch (e) {}
207
234
  }
208
235
  }
209
236
  }
210
- for (const abi of _ABIs) {
211
- const decoder = new _base.InputDataDecoder(abi);
212
- const raw = decoder.decodeData(tx.data);
213
- if (raw.method && raw.methodName) {
214
- const temp = {
215
- method: raw.method,
216
- methodName: raw.methodName,
217
- args: []
218
- };
219
- raw.types.forEach((type, index) => {
220
- // eslint-disable-next-line @typescript-eslint/no-unsafe-call,@typescript-eslint/no-unsafe-member-access,@typescript-eslint/no-unsafe-assignment
221
- temp.args.push(parseResult(type, raw.inputs[index], raw.names[index]));
222
- });
223
- result.data = temp;
224
- break;
225
- }
226
- }
227
237
  return result;
228
238
  };
229
239
  exports.parseEvmRlp = parseEvmRlp;
@@ -0,0 +1,112 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
4
+ Object.defineProperty(exports, "__esModule", {
5
+ value: true
6
+ });
7
+ exports.toBNString = exports.formatNumber = exports.balanceFormatter = exports.PREDEFINED_FORMATTER = exports.BN_TEN = void 0;
8
+ var _bignumber = _interopRequireDefault(require("bignumber.js"));
9
+ // Copyright 2019-2022 @subwallet/extension-koni authors & contributors
10
+ // SPDX-License-Identifier: Apache-2.0
11
+
12
+ const BN_TEN = new _bignumber.default(10);
13
+ exports.BN_TEN = BN_TEN;
14
+ // Clear zero from end, use with decimal only
15
+ const clearZero = result => {
16
+ let index = result.length - 1;
17
+ while (result[index] === '0') {
18
+ result = result.slice(0, index);
19
+ index--;
20
+ }
21
+ return result;
22
+ };
23
+ const NUM_1T = new _bignumber.default(1e12);
24
+ const TLIM = new _bignumber.default(1e17);
25
+ const NUM_1B = new _bignumber.default(1e9);
26
+ const BLIM = new _bignumber.default(1e14);
27
+ const NUM_1M = new _bignumber.default(1e6);
28
+ const NUM_100M = new _bignumber.default(1e8);
29
+ const balanceFormatter = (input, metadata) => {
30
+ const absGteOne = new _bignumber.default(input).abs().gte(1);
31
+ const minNumberFormat = (metadata === null || metadata === void 0 ? void 0 : metadata.minNumberFormat) || 2;
32
+ const maxNumberFormat = (metadata === null || metadata === void 0 ? void 0 : metadata.maxNumberFormat) || 6;
33
+ const [int, decimal = '0'] = input.split('.');
34
+ let _decimal = '';
35
+ if (absGteOne) {
36
+ const intNumber = new _bignumber.default(int);
37
+ const max = BN_TEN.pow(maxNumberFormat);
38
+
39
+ // If count of number in integer part greater or equal maxNumberFormat, do not show decimal
40
+ if (intNumber.gte(max)) {
41
+ if (intNumber.gte(NUM_100M)) {
42
+ if (intNumber.gte(BLIM)) {
43
+ if (intNumber.gte(TLIM)) {
44
+ return `${intNumber.dividedBy(NUM_1T).toFixed(2)} T`;
45
+ }
46
+ return `${intNumber.dividedBy(NUM_1B).toFixed(2)} B`;
47
+ }
48
+ return `${intNumber.dividedBy(NUM_1M).toFixed(2)} M`;
49
+ }
50
+ return int;
51
+ }
52
+
53
+ // Get only minNumberFormat number at decimal
54
+ if (decimal.length <= minNumberFormat) {
55
+ _decimal = decimal;
56
+ } else {
57
+ _decimal = decimal.slice(0, minNumberFormat);
58
+ }
59
+
60
+ // Clear zero number for decimal
61
+ _decimal = clearZero(_decimal);
62
+ } else {
63
+ // Index of cursor
64
+ let index = 0;
65
+
66
+ // Count of not zero number in decimal
67
+ let current = 0;
68
+
69
+ // Find a not zero number in decimal
70
+ let metNotZero = false;
71
+
72
+ // Get at least minNumberFormat number not 0 from index 0
73
+ // If count of 0 number at prefix greater or equal maxNumberFormat should stop and return 0
74
+
75
+ // current === minNumberFormat: get enough number
76
+ // index === decimal.length: end of decimal
77
+ // index === maxNumberFormat: reach limit of 0 number at prefix
78
+ while (current < minNumberFormat && index < decimal.length && (index < maxNumberFormat || metNotZero)) {
79
+ const _char = decimal[index];
80
+ _decimal += _char;
81
+ index++;
82
+ if (_char !== '0') {
83
+ metNotZero = true;
84
+ }
85
+ if (metNotZero) {
86
+ current++;
87
+ }
88
+ }
89
+
90
+ // Clear zero number for decimal
91
+ _decimal = clearZero(_decimal);
92
+ }
93
+ if (_decimal) {
94
+ return `${int}.${_decimal}`;
95
+ }
96
+ return int;
97
+ };
98
+ exports.balanceFormatter = balanceFormatter;
99
+ const PREDEFINED_FORMATTER = {
100
+ balance: balanceFormatter
101
+ };
102
+ exports.PREDEFINED_FORMATTER = PREDEFINED_FORMATTER;
103
+ const toBNString = (input, decimal) => {
104
+ const raw = new _bignumber.default(input);
105
+ return raw.multipliedBy(BN_TEN.pow(decimal)).toFixed();
106
+ };
107
+ exports.toBNString = toBNString;
108
+ const formatNumber = (input, decimal, formatter, metadata) => {
109
+ const raw = new _bignumber.default(input).dividedBy(BN_TEN.pow(decimal)).toFixed();
110
+ return formatter(raw, metadata);
111
+ };
112
+ exports.formatNumber = formatNumber;
@@ -17,4 +17,5 @@ export declare const ALL_NETWORK_KEY = "all";
17
17
  export declare const ALL_GENESIS_HASH: null;
18
18
  export declare const IGNORE_GET_SUBSTRATE_FEATURES_LIST: string[];
19
19
  export declare const IGNORE_QR_SIGNER: string[];
20
+ export declare const XCM_MIN_AMOUNT_RATIO = 1.2;
20
21
  export * from './staking';
@@ -20,4 +20,5 @@ export const ALL_NETWORK_KEY = 'all';
20
20
  export const ALL_GENESIS_HASH = null;
21
21
  export const IGNORE_GET_SUBSTRATE_FEATURES_LIST = ['astarEvm', 'ethereum', 'ethereum_goerli', 'binance', 'binance_test', 'boba_rinkeby', 'boba', 'bobabase', 'bobabeam'];
22
22
  export const IGNORE_QR_SIGNER = [];
23
+ export const XCM_MIN_AMOUNT_RATIO = 1.2;
23
24
  export * from "./staking.js";
@@ -12,6 +12,7 @@ import { state } from '@subwallet/extension-base/koni/background/handlers';
12
12
  import { _BALANCE_CHAIN_GROUP, _PURE_EVM_CHAINS } from '@subwallet/extension-base/services/chain-service/constants';
13
13
  import { _checkSmartContractSupportByChain, _getChainNativeTokenSlug, _getContractAddressOfToken, _getTokenOnChainAssetId, _getTokenOnChainInfo, _isChainEvmCompatible, _isPureEvmChain, _isSubstrateRelayChain } from '@subwallet/extension-base/services/chain-service/utils';
14
14
  import { categoryAddresses, sumBN } from '@subwallet/extension-base/utils';
15
+ import BigN from 'bignumber.js';
15
16
  import { BN, BN_ZERO } from '@polkadot/util';
16
17
  // main subscription
17
18
  export function subscribeBalance(addresses, chainInfoMap, substrateApiMap, evmApiMap, callback) {
@@ -229,7 +230,7 @@ async function subscribeEquilibriumTokenBalance(addresses, chain, api, callBack,
229
230
 
230
231
  // @ts-ignore
231
232
  const freeTokenBalance = balanceList.find(data => data[0] === parseInt(assetId));
232
- const bnFreeTokenBalance = freeTokenBalance ? new BN(freeTokenBalance[1].positive.toString()) : BN_ZERO;
233
+ const bnFreeTokenBalance = freeTokenBalance ? new BN(new BigN(freeTokenBalance[1].positive).toString()) : BN_ZERO;
233
234
  tokenFreeBalance = tokenFreeBalance.add(bnFreeTokenBalance);
234
235
  }
235
236
  const tokenBalance = {
@@ -284,10 +285,11 @@ async function subscribeTokensAccountsPallet(addresses, chain, api, callBack, in
284
285
  const unsubList = await Promise.all(Object.values(tokenMap).map(async tokenInfo => {
285
286
  try {
286
287
  const onChainInfo = _getTokenOnChainInfo(tokenInfo);
288
+ const assetId = _getTokenOnChainAssetId(tokenInfo);
287
289
 
288
290
  // Get Token Balance
289
291
  // @ts-ignore
290
- return await api.query.tokens.accounts.multi(addresses.map(address => [address, onChainInfo]), balances => {
292
+ return await api.query.tokens.accounts.multi(addresses.map(address => [address, onChainInfo || assetId]), balances => {
291
293
  const tokenBalance = {
292
294
  reserved: sumBN(balances.map(b => b.reserved || new BN(0))),
293
295
  frozen: sumBN(balances.map(b => b.frozen || new BN(0))),
@@ -5,7 +5,7 @@ import { COMMON_CHAIN_SLUGS } from '@subwallet/chain-list';
5
5
  import { APIItemState, CrowdloanParaState } from '@subwallet/extension-base/background/KoniTypes';
6
6
  import { ACALA_REFRESH_CROWDLOAN_INTERVAL } from '@subwallet/extension-base/constants';
7
7
  import registry from '@subwallet/extension-base/koni/api/dotsama/typeRegistry';
8
- import { _getChainSubstrateAddressPrefix, _getSubstrateParaId, _getSubstrateRelayParent, _isChainEvmCompatible, _isSubstrateParachain } from '@subwallet/extension-base/services/chain-service/utils';
8
+ import { _getChainSubstrateAddressPrefix, _getSubstrateParaId, _getSubstrateRelayParent, _isChainEvmCompatible, _isSubstrateParaChain } from '@subwallet/extension-base/services/chain-service/utils';
9
9
  import { categoryAddresses, reformatAddress } from '@subwallet/extension-base/utils';
10
10
  import axios from 'axios';
11
11
  import { BN } from '@polkadot/util';
@@ -97,7 +97,7 @@ export async function subscribeCrowdloan(addresses, substrateApiMap, callback, c
97
97
  return registry.createType('AccountId', address).toHex();
98
98
  });
99
99
  Object.entries(chainInfoMap).forEach(([networkKey, chainInfo]) => {
100
- if (_isSubstrateParachain(chainInfo)) {
100
+ if (_isSubstrateParaChain(chainInfo)) {
101
101
  const parentChain = _getSubstrateRelayParent(chainInfo);
102
102
  const crowdloanCb = rs => {
103
103
  callback(networkKey, rs);
@@ -82,7 +82,14 @@ export async function checkSupportTransfer(networkKey, tokenInfo, substrateApiMa
82
82
  } else if (_TRANSFER_CHAIN_GROUP.statemine.includes(networkKey) && !_isNativeToken(tokenInfo)) {
83
83
  result.supportTransfer = true;
84
84
  result.supportTransferAll = true;
85
+ } else if (_TRANSFER_CHAIN_GROUP.sora_substrate.includes(networkKey)) {
86
+ result.supportTransfer = true;
87
+ result.supportTransferAll = true;
88
+ // } else if (_TRANSFER_CHAIN_GROUP.riochain.includes(networkKey) && _isNativeToken(tokenInfo)) {
89
+ // result.supportTransfer = true;
90
+ // result.supportTransferAll = true;
85
91
  }
92
+
86
93
  return result;
87
94
  }
88
95
  export const createTransferExtrinsic = async ({
@@ -102,6 +109,7 @@ export const createTransferExtrinsic = async ({
102
109
  const isTxBalancesSupported = !!api && !!api.tx && !!api.tx.balances;
103
110
  const isTxTokensSupported = !!api && !!api.tx && !!api.tx.tokens;
104
111
  const isTxEqBalancesSupported = !!api && !!api.tx && !!api.tx.eqBalances;
112
+ const isTxAssetsSupported = !!api && !!api.tx && !!api.tx.assets;
105
113
  let transferAmount; // for PSP-22 tokens, might be deprecated in the future
106
114
 
107
115
  if (_isTokenWasmSmartContract(tokenInfo) && api.query.contracts) {
@@ -116,14 +124,14 @@ export const createTransferExtrinsic = async ({
116
124
  transferAmount = value;
117
125
  } else if (_TRANSFER_CHAIN_GROUP.acala.includes(networkKey) && !_isNativeToken(tokenInfo) && isTxCurrenciesSupported) {
118
126
  transfer = api.tx.currencies.transfer(to, _getTokenOnChainInfo(tokenInfo), value);
119
- } else if (_TRANSFER_CHAIN_GROUP.kintsugi.includes(networkKey) && !_isNativeToken(tokenInfo) && isTxTokensSupported) {
127
+ } else if (_TRANSFER_CHAIN_GROUP.kintsugi.includes(networkKey) && isTxTokensSupported) {
120
128
  if (transferAll) {
121
- transfer = api.tx.tokens.transferAll(to, _getTokenOnChainInfo(tokenInfo), false);
129
+ transfer = api.tx.tokens.transferAll(to, _getTokenOnChainInfo(tokenInfo) || _getTokenOnChainAssetId(tokenInfo), false);
122
130
  } else if (value) {
123
- transfer = api.tx.tokens.transfer(to, _getTokenOnChainInfo(tokenInfo), new BN(value));
131
+ transfer = api.tx.tokens.transfer(to, _getTokenOnChainInfo(tokenInfo) || _getTokenOnChainAssetId(tokenInfo), new BN(value));
124
132
  }
125
- } else if (_TRANSFER_CHAIN_GROUP.genshiro.includes(networkKey) && !_isNativeToken(tokenInfo) && isTxEqBalancesSupported) {
126
- transfer = api.tx.eqBalances.transfer([_getTokenOnChainAssetId(tokenInfo)], to, value);
133
+ } else if (_TRANSFER_CHAIN_GROUP.genshiro.includes(networkKey) && isTxEqBalancesSupported) {
134
+ transfer = api.tx.eqBalances.transfer(_getTokenOnChainAssetId(tokenInfo), to, value);
127
135
  } else if (!_isNativeToken(tokenInfo) && (_TRANSFER_CHAIN_GROUP.crab.includes(networkKey) || _BALANCE_TOKEN_GROUP.crab.includes(tokenInfo.symbol))) {
128
136
  if (transferAll) {
129
137
  transfer = api.tx.kton.transferAll(to, false);
@@ -134,6 +142,12 @@ export const createTransferExtrinsic = async ({
134
142
  transfer = api.tx.currencies.transfer(to, _getTokenOnChainInfo(tokenInfo), value);
135
143
  } else if (_TRANSFER_CHAIN_GROUP.statemine.includes(networkKey) && !_isNativeToken(tokenInfo)) {
136
144
  transfer = api.tx.assets.transfer(_getTokenOnChainAssetId(tokenInfo), to, value);
145
+ // } else if (_TRANSFER_CHAIN_GROUP.riochain.includes(networkKey)) {
146
+ // if (_isNativeToken(tokenInfo)) {
147
+ // transfer = api.tx.currencies.transferNativeCurrency(to, value);
148
+ // }
149
+ } else if (_TRANSFER_CHAIN_GROUP.sora_substrate.includes(networkKey) && isTxAssetsSupported) {
150
+ transfer = api.tx.assets.transfer(_getTokenOnChainAssetId(tokenInfo), to, value);
137
151
  } else if (isTxBalancesSupported && _isNativeToken(tokenInfo)) {
138
152
  if (transferAll) {
139
153
  transfer = api.tx.balances.transferAll(to, false);
@@ -10,9 +10,15 @@ export function getPSP22ContractPromise(apiPromise, contractAddress) {
10
10
  export function getPSP34ContractPromise(apiPromise, contractAddress) {
11
11
  return new ContractPromise(apiPromise, _PSP34_ABI, contractAddress);
12
12
  }
13
+ const mustFormatNumberReg = /^-?[0-9][0-9,.]+$/;
13
14
  export async function getPSP34TransferExtrinsic(networkKey, substrateApi, senderAddress, recipientAddress, params) {
14
15
  const contractAddress = params.contractAddress;
15
16
  const onChainOption = params.onChainOption;
17
+ for (const [key, value] of Object.entries(onChainOption)) {
18
+ if (mustFormatNumberReg.test(value)) {
19
+ onChainOption[key] = value.replaceAll(',', '');
20
+ }
21
+ }
16
22
  try {
17
23
  const contractPromise = getPSP34ContractPromise(substrateApi.api, contractAddress);
18
24
  // @ts-ignore
@@ -23,6 +29,7 @@ export async function getPSP34TransferExtrinsic(networkKey, substrateApi, sender
23
29
  gasLimit
24
30
  }, recipientAddress, onChainOption, {});
25
31
  } catch (e) {
32
+ console.debug(e);
26
33
  return null;
27
34
  }
28
35
  }