@subwallet/extension-base 1.2.3-0 → 1.2.4-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/background/KoniTypes.d.ts +4 -153
- package/background/KoniTypes.js +0 -21
- package/cjs/background/KoniTypes.js +1 -22
- package/cjs/core/logic-validation/earning.js +47 -0
- package/cjs/core/logic-validation/swap.js +99 -0
- package/cjs/core/logic-validation/transfer.js +212 -0
- package/cjs/core/substrate/nominationpools-pallet.js +22 -0
- package/cjs/core/substrate/system-pallet.js +77 -0
- package/cjs/core/substrate/xcm-parser.js +190 -0
- package/cjs/koni/api/dotsama/transfer.js +58 -122
- package/cjs/koni/api/staking/bonding/utils.js +1 -1
- package/cjs/koni/api/xcm/index.js +30 -2
- package/cjs/koni/api/xcm/polkadotXcm.js +12 -20
- package/cjs/koni/api/xcm/utils.js +8 -126
- package/cjs/koni/api/xcm/xTokens.js +10 -8
- package/cjs/koni/api/xcm/xcmPallet.js +6 -6
- package/cjs/koni/background/handlers/Extension.js +223 -356
- package/cjs/packageInfo.js +1 -1
- package/cjs/services/balance-service/helpers/group.js +4 -27
- package/cjs/services/balance-service/helpers/subscribe/index.js +2 -30
- package/cjs/services/balance-service/helpers/subscribe/substrate/index.js +46 -82
- package/cjs/services/balance-service/index.js +11 -9
- package/cjs/services/chain-service/constants.js +2 -2
- package/cjs/services/chain-service/index.js +0 -1
- package/cjs/services/chain-service/utils/index.js +13 -2
- package/cjs/services/earning-service/handlers/base.js +1 -1
- package/cjs/services/earning-service/handlers/special.js +11 -12
- package/cjs/services/migration-service/scripts/MigrateTransactionHistoryBySymbol.js +2 -1
- package/cjs/services/migration-service/scripts/databases/MigrateAssetSetting.js +2 -1
- package/cjs/services/migration-service/scripts/index.js +2 -2
- package/cjs/services/swap-service/handler/base-handler.js +30 -44
- package/cjs/services/swap-service/handler/chainflip-handler.js +23 -21
- package/cjs/services/swap-service/handler/hydradx-handler.js +41 -39
- package/cjs/services/swap-service/index.js +6 -0
- package/cjs/services/swap-service/utils.js +8 -49
- package/cjs/services/transaction-service/index.js +66 -155
- package/core/logic-validation/earning.d.ts +10 -0
- package/core/logic-validation/earning.js +37 -0
- package/core/logic-validation/swap.d.ts +8 -0
- package/core/logic-validation/swap.js +89 -0
- package/core/logic-validation/transfer.d.ts +16 -0
- package/core/logic-validation/transfer.js +199 -0
- package/core/substrate/nominationpools-pallet.d.ts +10 -0
- package/core/substrate/nominationpools-pallet.js +13 -0
- package/core/substrate/system-pallet.d.ts +27 -0
- package/core/substrate/system-pallet.js +70 -0
- package/core/substrate/xcm-parser.d.ts +49 -0
- package/core/substrate/xcm-parser.js +181 -0
- package/koni/api/dotsama/transfer.d.ts +3 -4
- package/koni/api/dotsama/transfer.js +54 -118
- package/koni/api/staking/bonding/relayChain.d.ts +2 -1
- package/koni/api/staking/bonding/utils.js +1 -1
- package/koni/api/xcm/index.d.ts +2 -0
- package/koni/api/xcm/index.js +27 -1
- package/koni/api/xcm/polkadotXcm.js +14 -22
- package/koni/api/xcm/utils.d.ts +3 -48
- package/koni/api/xcm/utils.js +5 -114
- package/koni/api/xcm/xTokens.js +12 -10
- package/koni/api/xcm/xcmPallet.js +7 -7
- package/koni/background/handlers/Extension.d.ts +6 -8
- package/koni/background/handlers/Extension.js +117 -247
- package/package.json +39 -9
- package/packageInfo.js +1 -1
- package/services/balance-service/helpers/group.js +4 -27
- package/services/balance-service/helpers/subscribe/index.d.ts +2 -1
- package/services/balance-service/helpers/subscribe/index.js +2 -30
- package/services/balance-service/helpers/subscribe/substrate/index.d.ts +2 -1
- package/services/balance-service/helpers/subscribe/substrate/index.js +31 -66
- package/services/balance-service/index.d.ts +7 -6
- package/services/balance-service/index.js +12 -10
- package/services/chain-service/constants.js +2 -2
- package/services/chain-service/index.js +0 -1
- package/services/chain-service/utils/index.d.ts +4 -2
- package/services/chain-service/utils/index.js +9 -2
- package/services/earning-service/handlers/base.js +1 -1
- package/services/earning-service/handlers/nomination-pool/index.d.ts +2 -1
- package/services/earning-service/handlers/special.js +11 -12
- package/services/migration-service/scripts/MigrateTransactionHistoryBySymbol.js +2 -1
- package/services/migration-service/scripts/databases/MigrateAssetSetting.js +2 -1
- package/services/migration-service/scripts/index.js +2 -2
- package/services/swap-service/handler/base-handler.d.ts +3 -2
- package/services/swap-service/handler/base-handler.js +28 -42
- package/services/swap-service/handler/chainflip-handler.d.ts +2 -1
- package/services/swap-service/handler/chainflip-handler.js +4 -2
- package/services/swap-service/handler/hydradx-handler.d.ts +2 -1
- package/services/swap-service/handler/hydradx-handler.js +8 -6
- package/services/swap-service/index.js +7 -1
- package/services/swap-service/utils.d.ts +2 -4
- package/services/swap-service/utils.js +7 -47
- package/services/transaction-service/index.d.ts +1 -1
- package/services/transaction-service/index.js +30 -119
- package/services/transaction-service/types.d.ts +1 -0
- package/types/balance/index.d.ts +6 -10
- package/types/yield/info/pallet.d.ts +0 -6
|
@@ -0,0 +1,212 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
4
|
+
Object.defineProperty(exports, "__esModule", {
|
|
5
|
+
value: true
|
|
6
|
+
});
|
|
7
|
+
exports.additionalValidateTransfer = additionalValidateTransfer;
|
|
8
|
+
exports.additionalValidateXcmTransfer = additionalValidateXcmTransfer;
|
|
9
|
+
exports.checkBalanceWithTransactionFee = checkBalanceWithTransactionFee;
|
|
10
|
+
exports.checkSigningAccountForTransaction = checkSigningAccountForTransaction;
|
|
11
|
+
exports.checkSupportForTransaction = checkSupportForTransaction;
|
|
12
|
+
exports.estimateFeeForTransaction = estimateFeeForTransaction;
|
|
13
|
+
exports.validateTransferRequest = validateTransferRequest;
|
|
14
|
+
exports.validateXcmTransferRequest = validateXcmTransferRequest;
|
|
15
|
+
var _TransactionError = require("@subwallet/extension-base/background/errors/TransactionError");
|
|
16
|
+
var _KoniTypes = require("@subwallet/extension-base/background/KoniTypes");
|
|
17
|
+
var _TransactionWarning = require("@subwallet/extension-base/background/warnings/TransactionWarning");
|
|
18
|
+
var _constants = require("@subwallet/extension-base/constants");
|
|
19
|
+
var _systemPallet = require("@subwallet/extension-base/core/substrate/system-pallet");
|
|
20
|
+
var _constants2 = require("@subwallet/extension-base/services/chain-service/constants");
|
|
21
|
+
var _utils = require("@subwallet/extension-base/services/chain-service/utils");
|
|
22
|
+
var _utils2 = require("@subwallet/extension-base/services/fee-service/utils");
|
|
23
|
+
var _helpers = require("@subwallet/extension-base/services/transaction-service/helpers");
|
|
24
|
+
var _utils3 = require("@subwallet/extension-base/utils");
|
|
25
|
+
var _uiKeyring = require("@subwallet/ui-keyring");
|
|
26
|
+
var _bignumber = _interopRequireDefault(require("bignumber.js"));
|
|
27
|
+
var _i18next = require("i18next");
|
|
28
|
+
var _utilCrypto = require("@polkadot/util-crypto");
|
|
29
|
+
// Copyright 2019-2022 @subwallet/extension-base authors & contributors
|
|
30
|
+
// SPDX-License-Identifier: Apache-2.0
|
|
31
|
+
|
|
32
|
+
// normal transfer
|
|
33
|
+
function validateTransferRequest(tokenInfo, from, to, value, transferAll) {
|
|
34
|
+
const errors = [];
|
|
35
|
+
const keypair = _uiKeyring.keyring.getPair(from);
|
|
36
|
+
let transferValue;
|
|
37
|
+
if (!transferAll) {
|
|
38
|
+
if (value === undefined) {
|
|
39
|
+
errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.INVALID_PARAMS, (0, _i18next.t)('Transfer amount is required')));
|
|
40
|
+
}
|
|
41
|
+
if (value) {
|
|
42
|
+
transferValue = new _bignumber.default(value);
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
if (!tokenInfo) {
|
|
46
|
+
errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.INVALID_PARAMS, (0, _i18next.t)('Not found token from registry')));
|
|
47
|
+
}
|
|
48
|
+
if ((0, _utilCrypto.isEthereumAddress)(from) && (0, _utilCrypto.isEthereumAddress)(to) && (0, _utils._isTokenEvmSmartContract)(tokenInfo) && (0, _utils._getContractAddressOfToken)(tokenInfo).length === 0) {
|
|
49
|
+
errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.INVALID_PARAMS, (0, _i18next.t)('Not found ERC20 address for this token')));
|
|
50
|
+
}
|
|
51
|
+
return [errors, keypair, transferValue];
|
|
52
|
+
}
|
|
53
|
+
function additionalValidateTransfer(tokenInfo, extrinsicType, receiverTransferTokenFreeBalance, transferAmount, senderTransferTokenTransferable) {
|
|
54
|
+
const minAmount = (0, _utils._getTokenMinAmount)(tokenInfo);
|
|
55
|
+
let warning;
|
|
56
|
+
let error;
|
|
57
|
+
|
|
58
|
+
// Check ed of not native token for sender
|
|
59
|
+
if (extrinsicType === _KoniTypes.ExtrinsicType.TRANSFER_TOKEN && senderTransferTokenTransferable) {
|
|
60
|
+
if (new _bignumber.default(senderTransferTokenTransferable).minus(transferAmount).lt(minAmount)) {
|
|
61
|
+
warning = new _TransactionWarning.TransactionWarning(_KoniTypes.BasicTxWarningCode.NOT_ENOUGH_EXISTENTIAL_DEPOSIT);
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
// Check ed for receiver
|
|
66
|
+
if (new _bignumber.default(receiverTransferTokenFreeBalance).plus(transferAmount).lt(minAmount)) {
|
|
67
|
+
const atLeast = new _bignumber.default(minAmount).minus(receiverTransferTokenFreeBalance).plus((tokenInfo.decimals || 0) === 0 ? 0 : 1);
|
|
68
|
+
const atLeastStr = (0, _utils3.formatNumber)(atLeast, tokenInfo.decimals || 0, _utils3.balanceFormatter, {
|
|
69
|
+
maxNumberFormat: tokenInfo.decimals || 6
|
|
70
|
+
});
|
|
71
|
+
error = new _TransactionError.TransactionError(_KoniTypes.TransferTxErrorType.RECEIVER_NOT_ENOUGH_EXISTENTIAL_DEPOSIT, (0, _i18next.t)('You must transfer at least {{amount}} {{symbol}} to keep the destination account alive', {
|
|
72
|
+
replace: {
|
|
73
|
+
amount: atLeastStr,
|
|
74
|
+
symbol: tokenInfo.symbol
|
|
75
|
+
}
|
|
76
|
+
}));
|
|
77
|
+
}
|
|
78
|
+
return [warning, error];
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
// xcm transfer
|
|
82
|
+
function validateXcmTransferRequest(destTokenInfo, sender, sendingValue) {
|
|
83
|
+
const errors = [];
|
|
84
|
+
const keypair = _uiKeyring.keyring.getPair(sender);
|
|
85
|
+
const transferValue = new _bignumber.default(sendingValue);
|
|
86
|
+
if (!destTokenInfo) {
|
|
87
|
+
errors.push(new _TransactionError.TransactionError(_KoniTypes.TransferTxErrorType.INVALID_TOKEN, (0, _i18next.t)('Not found token from registry')));
|
|
88
|
+
}
|
|
89
|
+
return [errors, keypair, transferValue];
|
|
90
|
+
}
|
|
91
|
+
function additionalValidateXcmTransfer(originTokenInfo, destinationTokenInfo, sendingAmount, senderTransferable) {
|
|
92
|
+
const destMinAmount = (0, _utils._getTokenMinAmount)(destinationTokenInfo);
|
|
93
|
+
const minSendingRequired = new _bignumber.default(destMinAmount).multipliedBy(_constants.XCM_MIN_AMOUNT_RATIO);
|
|
94
|
+
let error;
|
|
95
|
+
let warning;
|
|
96
|
+
|
|
97
|
+
// Check ed for receiver
|
|
98
|
+
if (new _bignumber.default(sendingAmount).lt(minSendingRequired)) {
|
|
99
|
+
const atLeastStr = (0, _utils3.formatNumber)(minSendingRequired, destinationTokenInfo.decimals || 0, _utils3.balanceFormatter, {
|
|
100
|
+
maxNumberFormat: destinationTokenInfo.decimals || 6
|
|
101
|
+
});
|
|
102
|
+
error = new _TransactionError.TransactionError(_KoniTypes.TransferTxErrorType.RECEIVER_NOT_ENOUGH_EXISTENTIAL_DEPOSIT, (0, _i18next.t)('You must transfer at least {{amount}} {{symbol}} to keep the destination account alive', {
|
|
103
|
+
replace: {
|
|
104
|
+
amount: atLeastStr,
|
|
105
|
+
symbol: originTokenInfo.symbol
|
|
106
|
+
}
|
|
107
|
+
}));
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
// Check ed for sender
|
|
111
|
+
if (!(0, _utils._isNativeToken)(originTokenInfo)) {
|
|
112
|
+
if (new _bignumber.default(senderTransferable).minus(sendingAmount).lt((0, _utils._getTokenMinAmount)(originTokenInfo))) {
|
|
113
|
+
warning = new _TransactionWarning.TransactionWarning(_KoniTypes.BasicTxWarningCode.NOT_ENOUGH_EXISTENTIAL_DEPOSIT);
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
return [warning, error];
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
// general validations
|
|
120
|
+
function checkSupportForTransaction(validationResponse, transaction) {
|
|
121
|
+
const {
|
|
122
|
+
extrinsicType
|
|
123
|
+
} = validationResponse;
|
|
124
|
+
if (!transaction) {
|
|
125
|
+
if (extrinsicType === _KoniTypes.ExtrinsicType.SEND_NFT) {
|
|
126
|
+
validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.UNSUPPORTED, (0, _i18next.t)('This feature is not yet available for this NFT')));
|
|
127
|
+
} else {
|
|
128
|
+
validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.UNSUPPORTED));
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
}
|
|
132
|
+
async function estimateFeeForTransaction(validationResponse, transaction, chainInfo, evmApi) {
|
|
133
|
+
const estimateFee = {
|
|
134
|
+
symbol: '',
|
|
135
|
+
decimals: 0,
|
|
136
|
+
value: '0',
|
|
137
|
+
tooHigh: false
|
|
138
|
+
};
|
|
139
|
+
const {
|
|
140
|
+
decimals,
|
|
141
|
+
symbol
|
|
142
|
+
} = (0, _utils._getChainNativeTokenBasicInfo)(chainInfo);
|
|
143
|
+
estimateFee.decimals = decimals;
|
|
144
|
+
estimateFee.symbol = symbol;
|
|
145
|
+
if (transaction) {
|
|
146
|
+
try {
|
|
147
|
+
if ((0, _helpers.isSubstrateTransaction)(transaction)) {
|
|
148
|
+
estimateFee.value = (await transaction.paymentInfo(validationResponse.address)).partialFee.toString();
|
|
149
|
+
} else {
|
|
150
|
+
const gasLimit = await evmApi.api.eth.estimateGas(transaction);
|
|
151
|
+
const priority = await (0, _utils2.calculateGasFeeParams)(evmApi, chainInfo.slug);
|
|
152
|
+
if (priority.baseGasFee) {
|
|
153
|
+
const maxFee = priority.maxFeePerGas; // TODO: Need review
|
|
154
|
+
|
|
155
|
+
estimateFee.value = maxFee.multipliedBy(gasLimit).toFixed(0);
|
|
156
|
+
} else {
|
|
157
|
+
estimateFee.value = new _bignumber.default(priority.gasPrice).multipliedBy(gasLimit).toFixed(0);
|
|
158
|
+
}
|
|
159
|
+
estimateFee.tooHigh = priority.busyNetwork;
|
|
160
|
+
}
|
|
161
|
+
} catch (e) {
|
|
162
|
+
const error = e;
|
|
163
|
+
if (error.message.includes('gas required exceeds allowance') && error.message.includes('insufficient funds')) {
|
|
164
|
+
validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.NOT_ENOUGH_BALANCE));
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
return estimateFee;
|
|
169
|
+
}
|
|
170
|
+
function checkSigningAccountForTransaction(validationResponse) {
|
|
171
|
+
const pair = _uiKeyring.keyring.getPair(validationResponse.address);
|
|
172
|
+
if (!pair) {
|
|
173
|
+
validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.INTERNAL_ERROR, (0, _i18next.t)('Unable to find account')));
|
|
174
|
+
} else {
|
|
175
|
+
var _pair$meta;
|
|
176
|
+
if ((_pair$meta = pair.meta) !== null && _pair$meta !== void 0 && _pair$meta.isReadOnly) {
|
|
177
|
+
validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.INTERNAL_ERROR, (0, _i18next.t)('This account is watch-only')));
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
function checkBalanceWithTransactionFee(validationResponse, transactionInput, nativeTokenInfo, nativeTokenAvailable) {
|
|
182
|
+
if (!validationResponse.estimateFee) {
|
|
183
|
+
// todo: estimateFee should be must-have, need to refactor interface
|
|
184
|
+
return;
|
|
185
|
+
}
|
|
186
|
+
const {
|
|
187
|
+
edAsWarning,
|
|
188
|
+
extrinsicType,
|
|
189
|
+
isTransferAll,
|
|
190
|
+
skipFeeValidation
|
|
191
|
+
} = transactionInput;
|
|
192
|
+
if (skipFeeValidation) {
|
|
193
|
+
return;
|
|
194
|
+
}
|
|
195
|
+
const bnFee = new _bignumber.default(validationResponse.estimateFee.value);
|
|
196
|
+
const bnNativeTokenAvailable = new _bignumber.default(nativeTokenAvailable.value);
|
|
197
|
+
const bnNativeTokenTransferAmount = new _bignumber.default(validationResponse.transferNativeAmount || '0');
|
|
198
|
+
if (!bnNativeTokenAvailable.gt(0)) {
|
|
199
|
+
validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.NOT_ENOUGH_BALANCE));
|
|
200
|
+
}
|
|
201
|
+
const isChainNotSupportTransferAll = [..._constants2._TRANSFER_CHAIN_GROUP.acala, ..._constants2._TRANSFER_CHAIN_GROUP.genshiro, ..._constants2._TRANSFER_CHAIN_GROUP.bitcountry, ..._constants2._TRANSFER_CHAIN_GROUP.statemine].includes(nativeTokenInfo.originChain);
|
|
202
|
+
if (bnNativeTokenTransferAmount.plus(bnFee).gt(bnNativeTokenAvailable) && (!isTransferAll || isChainNotSupportTransferAll)) {
|
|
203
|
+
validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.NOT_ENOUGH_BALANCE)); // todo: should be generalized and reused in all features
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
// todo: only system.pallet has metadata, we should add for other pallets and mechanisms as well
|
|
207
|
+
const isNeedCheckRemainingBalance = !isTransferAll && extrinsicType === _KoniTypes.ExtrinsicType.TRANSFER_BALANCE && nativeTokenAvailable.metadata && (0, _systemPallet._canAccountBeReaped)(nativeTokenAvailable.metadata);
|
|
208
|
+
const isRemainingBalanceValid = bnNativeTokenAvailable.minus(bnNativeTokenTransferAmount).minus(bnFee).lt((0, _utils._getTokenMinAmount)(nativeTokenInfo));
|
|
209
|
+
if (isNeedCheckRemainingBalance && isRemainingBalanceValid) {
|
|
210
|
+
edAsWarning ? validationResponse.warnings.push(new _TransactionWarning.TransactionWarning(_KoniTypes.BasicTxWarningCode.NOT_ENOUGH_EXISTENTIAL_DEPOSIT)) : validationResponse.errors.push(new _TransactionError.TransactionError(_KoniTypes.BasicTxErrorType.NOT_ENOUGH_EXISTENTIAL_DEPOSIT));
|
|
211
|
+
}
|
|
212
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
4
|
+
Object.defineProperty(exports, "__esModule", {
|
|
5
|
+
value: true
|
|
6
|
+
});
|
|
7
|
+
exports._getActiveStakeInNominationPool = _getActiveStakeInNominationPool;
|
|
8
|
+
exports._getTotalStakeInNominationPool = _getTotalStakeInNominationPool;
|
|
9
|
+
exports._getUnbondingStakeInNominationPool = _getUnbondingStakeInNominationPool;
|
|
10
|
+
var _bignumber = _interopRequireDefault(require("bignumber.js"));
|
|
11
|
+
// Copyright 2019-2022 @subwallet/extension-base
|
|
12
|
+
// SPDX-License-Identifier: Apache-2.0
|
|
13
|
+
|
|
14
|
+
function _getActiveStakeInNominationPool(memberInfo) {
|
|
15
|
+
return new _bignumber.default(memberInfo.points.toString());
|
|
16
|
+
}
|
|
17
|
+
function _getUnbondingStakeInNominationPool(memberInfo) {
|
|
18
|
+
return new _bignumber.default(Object.values(memberInfo.unbondingEras).reduce((a, b) => a + b, 0));
|
|
19
|
+
}
|
|
20
|
+
function _getTotalStakeInNominationPool(memberInfo) {
|
|
21
|
+
return _getActiveStakeInNominationPool(memberInfo).plus(_getUnbondingStakeInNominationPool(memberInfo));
|
|
22
|
+
}
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
4
|
+
Object.defineProperty(exports, "__esModule", {
|
|
5
|
+
value: true
|
|
6
|
+
});
|
|
7
|
+
exports._canAccountBeReaped = _canAccountBeReaped;
|
|
8
|
+
exports._getAppliedExistentialDepositWithExtrinsicType = _getAppliedExistentialDepositWithExtrinsicType;
|
|
9
|
+
exports._getSystemPalletTotalBalance = _getSystemPalletTotalBalance;
|
|
10
|
+
exports._getSystemPalletTransferable = _getSystemPalletTransferable;
|
|
11
|
+
exports._isAccountActive = _isAccountActive;
|
|
12
|
+
var _KoniTypes = require("@subwallet/extension-base/background/KoniTypes");
|
|
13
|
+
var _bignumber = _interopRequireDefault(require("bignumber.js"));
|
|
14
|
+
// Copyright 2019-2022 @subwallet/extension-base
|
|
15
|
+
// SPDX-License-Identifier: Apache-2.0
|
|
16
|
+
|
|
17
|
+
function isV1(accountInfo) {
|
|
18
|
+
return accountInfo.data.miscFrozen !== undefined && accountInfo.data.feeFrozen !== undefined;
|
|
19
|
+
}
|
|
20
|
+
function _getSystemPalletTransferable(accountInfo, existentialDeposit, extrinsicType) {
|
|
21
|
+
const strictMode = !extrinsicType || ![_KoniTypes.ExtrinsicType.TRANSFER_BALANCE].includes(extrinsicType); // always apply strict mode to keep account alive unless explicitly specified otherwise
|
|
22
|
+
|
|
23
|
+
if (isV1(accountInfo)) {
|
|
24
|
+
return _getSystemPalletTransferableV1(accountInfo, existentialDeposit, strictMode);
|
|
25
|
+
} else {
|
|
26
|
+
return _getSystemPalletTransferableV2(accountInfo, existentialDeposit, strictMode);
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
function _canAccountBeReaped(accountInfo) {
|
|
30
|
+
return accountInfo.consumers === 0; // might need to check refCount
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
function _isAccountActive(accountInfo) {
|
|
34
|
+
return accountInfo.providers === 0 && accountInfo.consumers === 0;
|
|
35
|
+
}
|
|
36
|
+
function _getSystemPalletTotalBalance(accountInfo) {
|
|
37
|
+
if (isV1(accountInfo)) {
|
|
38
|
+
return _getSystemPalletTotalBalanceV1(accountInfo);
|
|
39
|
+
} else {
|
|
40
|
+
return _getSystemPalletTotalBalanceV2(accountInfo);
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
function _getAppliedExistentialDepositWithExtrinsicType(accountInfo, existentialDeposit, extrinsicType) {
|
|
44
|
+
const strictMode = !extrinsicType || ![_KoniTypes.ExtrinsicType.TRANSFER_BALANCE].includes(extrinsicType); // always apply strict mode to keep account alive unless explicitly specified otherwise
|
|
45
|
+
|
|
46
|
+
return _getAppliedExistentialDeposit(accountInfo, existentialDeposit, strictMode);
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
// ----------------------------------------------------------------------
|
|
50
|
+
|
|
51
|
+
function _getAppliedExistentialDeposit(accountInfo, existentialDeposit, strictMode) {
|
|
52
|
+
// strict mode will always apply existential deposit to keep account alive
|
|
53
|
+
if (strictMode) {
|
|
54
|
+
return existentialDeposit;
|
|
55
|
+
}
|
|
56
|
+
return _canAccountBeReaped(accountInfo) ? '0' : existentialDeposit; // account for ED here will go better with max transfer logic
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
function _getSystemPalletTransferableV2(accountInfo, existentialDeposit, strictMode) {
|
|
60
|
+
const bnFree = new _bignumber.default(accountInfo.data.free);
|
|
61
|
+
const bnLocked = new _bignumber.default(accountInfo.data.frozen).minus(accountInfo.data.reserved); // locked can go below 0 but this shouldn't matter
|
|
62
|
+
const bnAppliedExistentialDeposit = new _bignumber.default(_getAppliedExistentialDeposit(accountInfo, existentialDeposit, strictMode));
|
|
63
|
+
const bnTransferableBalance = bnFree.minus(_bignumber.default.max(bnLocked, bnAppliedExistentialDeposit));
|
|
64
|
+
return _bignumber.default.max(bnTransferableBalance, 0).toFixed();
|
|
65
|
+
}
|
|
66
|
+
function _getSystemPalletTotalBalanceV2(accountInfo) {
|
|
67
|
+
return new _bignumber.default(accountInfo.data.free).plus(accountInfo.data.reserved).toFixed();
|
|
68
|
+
}
|
|
69
|
+
function _getSystemPalletTransferableV1(accountInfo, existentialDeposit, strictMode) {
|
|
70
|
+
const bnAppliedExistentialDeposit = new _bignumber.default(_getAppliedExistentialDeposit(accountInfo, existentialDeposit, strictMode));
|
|
71
|
+
const bnAppliedFrozen = _bignumber.default.max(accountInfo.data.feeFrozen, accountInfo.data.miscFrozen);
|
|
72
|
+
const bnTransferableBalance = new _bignumber.default(accountInfo.data.free).minus(_bignumber.default.max(bnAppliedFrozen, bnAppliedExistentialDeposit));
|
|
73
|
+
return _bignumber.default.max(bnTransferableBalance, 0).toFixed();
|
|
74
|
+
}
|
|
75
|
+
function _getSystemPalletTotalBalanceV1(accountInfo) {
|
|
76
|
+
return new _bignumber.default(accountInfo.data.free).plus(accountInfo.data.reserved).toFixed();
|
|
77
|
+
}
|
|
@@ -0,0 +1,190 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports._getXcmBeneficiary = _getXcmBeneficiary;
|
|
7
|
+
exports._getXcmDestWeight = _getXcmDestWeight;
|
|
8
|
+
exports._getXcmMultiAssets = _getXcmMultiAssets;
|
|
9
|
+
exports._getXcmMultiLocation = _getXcmMultiLocation;
|
|
10
|
+
var _chainList = require("@subwallet/chain-list");
|
|
11
|
+
var _utils = require("@subwallet/extension-base/services/chain-service/utils");
|
|
12
|
+
var _utilCrypto = require("@polkadot/util-crypto");
|
|
13
|
+
// Copyright 2019-2022 @subwallet/extension-base
|
|
14
|
+
// SPDX-License-Identifier: Apache-2.0
|
|
15
|
+
|
|
16
|
+
const FOUR_INSTRUCTIONS_WEIGHT = 5000000000;
|
|
17
|
+
const UNLIMITED_WEIGHT = 'Unlimited';
|
|
18
|
+
function _getXcmDestWeight(originChainInfo) {
|
|
19
|
+
if (['pioneer'].includes(originChainInfo.slug)) {
|
|
20
|
+
return FOUR_INSTRUCTIONS_WEIGHT;
|
|
21
|
+
}
|
|
22
|
+
return UNLIMITED_WEIGHT;
|
|
23
|
+
}
|
|
24
|
+
function _getXcmBeneficiary(destChainInfo, recipient, version) {
|
|
25
|
+
const receiverLocation = version < 4 // from V4, X1 is also an array
|
|
26
|
+
? _getRecipientLocation(destChainInfo, recipient, version) : [_getRecipientLocation(destChainInfo, recipient, version)];
|
|
27
|
+
return {
|
|
28
|
+
[`V${version}`]: {
|
|
29
|
+
parents: 0,
|
|
30
|
+
interior: {
|
|
31
|
+
X1: receiverLocation
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
};
|
|
35
|
+
}
|
|
36
|
+
function _getXcmMultiAssets(tokenInfo, value, version) {
|
|
37
|
+
const assetId = _getAssetIdentifier(tokenInfo, version);
|
|
38
|
+
return {
|
|
39
|
+
[`V${version}`]: [{
|
|
40
|
+
id: assetId,
|
|
41
|
+
fun: {
|
|
42
|
+
Fungible: value
|
|
43
|
+
}
|
|
44
|
+
}]
|
|
45
|
+
};
|
|
46
|
+
}
|
|
47
|
+
function _getXcmMultiLocation(originChainInfo, destChainInfo, version, recipient) {
|
|
48
|
+
const isWithinSameConsensus = _isXcmWithinSameConsensus(originChainInfo, destChainInfo);
|
|
49
|
+
const parents = _getMultiLocationParent(originChainInfo, isWithinSameConsensus);
|
|
50
|
+
const interior = _getMultiLocationInterior(destChainInfo, isWithinSameConsensus, version, recipient);
|
|
51
|
+
return {
|
|
52
|
+
[`V${version}`]: {
|
|
53
|
+
parents,
|
|
54
|
+
interior
|
|
55
|
+
}
|
|
56
|
+
};
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
// ---------------------------------------------------------------------------------------------------------------------
|
|
60
|
+
|
|
61
|
+
function _isXcmWithinSameConsensus(originChainInfo, destChainInfo) {
|
|
62
|
+
return (0, _utils._getSubstrateRelayParent)(originChainInfo) === destChainInfo.slug || (0, _utils._getSubstrateRelayParent)(destChainInfo) === originChainInfo.slug || (0, _utils._getSubstrateRelayParent)(originChainInfo) === (0, _utils._getSubstrateRelayParent)(destChainInfo);
|
|
63
|
+
}
|
|
64
|
+
function _getMultiLocationParent(originChainInfo, isWithinSameConsensus) {
|
|
65
|
+
let parent = 0; // how many hops up the hierarchy
|
|
66
|
+
|
|
67
|
+
if ((0, _utils._isSubstrateParaChain)(originChainInfo)) {
|
|
68
|
+
parent += 1;
|
|
69
|
+
}
|
|
70
|
+
if (!isWithinSameConsensus) {
|
|
71
|
+
parent += 1;
|
|
72
|
+
}
|
|
73
|
+
return parent;
|
|
74
|
+
}
|
|
75
|
+
function _getMultiLocationInterior(destChainInfo, isWithinSameConsensus, version, recipient) {
|
|
76
|
+
const junctions = [];
|
|
77
|
+
if (isWithinSameConsensus) {
|
|
78
|
+
if ((0, _utils._isSubstrateParaChain)(destChainInfo)) {
|
|
79
|
+
junctions.push({
|
|
80
|
+
Parachain: (0, _utils._getSubstrateParaId)(destChainInfo)
|
|
81
|
+
});
|
|
82
|
+
}
|
|
83
|
+
} else {
|
|
84
|
+
junctions.push({
|
|
85
|
+
GlobalConsensus: _getGlobalConsensusJunction(destChainInfo, version)
|
|
86
|
+
});
|
|
87
|
+
if ((0, _utils._isSubstrateParaChain)(destChainInfo)) {
|
|
88
|
+
junctions.push({
|
|
89
|
+
Parachain: (0, _utils._getSubstrateParaId)(destChainInfo)
|
|
90
|
+
});
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
if (recipient) {
|
|
94
|
+
junctions.push(_getRecipientLocation(destChainInfo, recipient, version));
|
|
95
|
+
}
|
|
96
|
+
if (junctions.length === 0 && !recipient) {
|
|
97
|
+
return 'Here';
|
|
98
|
+
}
|
|
99
|
+
if (version < 4 && junctions.length === 1) {
|
|
100
|
+
return {
|
|
101
|
+
X1: junctions[0]
|
|
102
|
+
};
|
|
103
|
+
}
|
|
104
|
+
return {
|
|
105
|
+
[`X${junctions.length}`]: junctions
|
|
106
|
+
};
|
|
107
|
+
}
|
|
108
|
+
function _getGlobalConsensusJunction(destChainInfo, version) {
|
|
109
|
+
let chainSlug = destChainInfo.slug;
|
|
110
|
+
let evmChainId;
|
|
111
|
+
if ((0, _utils._isSubstrateParaChain)(destChainInfo)) {
|
|
112
|
+
const relaySlug = (0, _utils._getSubstrateRelayParent)(destChainInfo);
|
|
113
|
+
if (!relaySlug) {
|
|
114
|
+
throw Error('Parachain must have a parent chainSlug');
|
|
115
|
+
}
|
|
116
|
+
chainSlug = relaySlug;
|
|
117
|
+
} else {
|
|
118
|
+
evmChainId = (0, _utils._getEvmChainId)(destChainInfo);
|
|
119
|
+
}
|
|
120
|
+
if (evmChainId) {
|
|
121
|
+
return {
|
|
122
|
+
Ethereum: {
|
|
123
|
+
chainId: evmChainId
|
|
124
|
+
}
|
|
125
|
+
};
|
|
126
|
+
}
|
|
127
|
+
switch (chainSlug) {
|
|
128
|
+
case _chainList.COMMON_CHAIN_SLUGS.POLKADOT:
|
|
129
|
+
return version < 4 ? {
|
|
130
|
+
Polkadot: null
|
|
131
|
+
} : 'Polkadot';
|
|
132
|
+
case _chainList.COMMON_CHAIN_SLUGS.KUSAMA:
|
|
133
|
+
return version < 4 ? {
|
|
134
|
+
Kusama: null
|
|
135
|
+
} : 'Kusama';
|
|
136
|
+
default:
|
|
137
|
+
return version < 4 ? {
|
|
138
|
+
Rococo: null
|
|
139
|
+
} : 'Rococo';
|
|
140
|
+
}
|
|
141
|
+
}
|
|
142
|
+
function _getRecipientLocation(destChainInfo, recipient, version) {
|
|
143
|
+
const network = _getNetworkByVersion(version);
|
|
144
|
+
if (destChainInfo.slug === _chainList.COMMON_CHAIN_SLUGS.ASTAR_EVM) {
|
|
145
|
+
const ss58Address = (0, _utilCrypto.evmToAddress)(recipient, (0, _utils._getChainSubstrateAddressPrefix)(destChainInfo)); // TODO: shouldn't pass addressPrefix directly
|
|
146
|
+
|
|
147
|
+
return {
|
|
148
|
+
AccountId32: {
|
|
149
|
+
network,
|
|
150
|
+
id: (0, _utilCrypto.decodeAddress)(ss58Address)
|
|
151
|
+
}
|
|
152
|
+
};
|
|
153
|
+
}
|
|
154
|
+
if ((0, _utils._isChainEvmCompatible)(destChainInfo)) {
|
|
155
|
+
return {
|
|
156
|
+
AccountKey20: {
|
|
157
|
+
network,
|
|
158
|
+
key: recipient
|
|
159
|
+
}
|
|
160
|
+
};
|
|
161
|
+
}
|
|
162
|
+
return {
|
|
163
|
+
AccountId32: {
|
|
164
|
+
network,
|
|
165
|
+
id: (0, _utilCrypto.decodeAddress)(recipient)
|
|
166
|
+
}
|
|
167
|
+
};
|
|
168
|
+
}
|
|
169
|
+
function _getAssetIdentifier(tokenInfo, version) {
|
|
170
|
+
const assetIdentifier = (0, _utils._getXcmAssetMultilocation)(tokenInfo);
|
|
171
|
+
if (!assetIdentifier) {
|
|
172
|
+
throw new Error('Asset must have multilocation');
|
|
173
|
+
}
|
|
174
|
+
return version >= 4 // from V4, Concrete is removed
|
|
175
|
+
? assetIdentifier : {
|
|
176
|
+
Concrete: assetIdentifier
|
|
177
|
+
};
|
|
178
|
+
}
|
|
179
|
+
function _getNetworkByVersion(version) {
|
|
180
|
+
switch (version) {
|
|
181
|
+
case 1:
|
|
182
|
+
case 2:
|
|
183
|
+
return 'Any';
|
|
184
|
+
case 3:
|
|
185
|
+
case 4:
|
|
186
|
+
return undefined;
|
|
187
|
+
default:
|
|
188
|
+
return undefined;
|
|
189
|
+
}
|
|
190
|
+
}
|