@subwallet/extension-base 1.0.7-0 → 1.0.7-1

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 (55) hide show
  1. package/background/KoniTypes.d.ts +4 -5
  2. package/cjs/constants/index.js +1 -1
  3. package/cjs/koni/api/staking/bonding/amplitude.js +83 -0
  4. package/cjs/koni/api/staking/bonding/astar.js +104 -1
  5. package/cjs/koni/api/staking/bonding/index.js +35 -0
  6. package/cjs/koni/api/staking/bonding/paraChain.js +97 -0
  7. package/cjs/koni/api/staking/bonding/relayChain.js +191 -12
  8. package/cjs/koni/api/staking/index.js +11 -11
  9. package/cjs/koni/api/staking/paraChain.js +200 -130
  10. package/cjs/koni/api/staking/relayChain.js +66 -68
  11. package/cjs/koni/api/staking/subsquidStaking.js +6 -11
  12. package/cjs/koni/background/cron.js +0 -25
  13. package/cjs/koni/background/handlers/State.js +17 -19
  14. package/cjs/koni/background/subscription.js +57 -12
  15. package/cjs/packageInfo.js +1 -1
  16. package/cjs/services/chain-service/utils.js +6 -1
  17. package/cjs/services/storage-service/DatabaseService.js +7 -3
  18. package/cjs/services/storage-service/db-stores/ChainStakingMetadata.js +5 -0
  19. package/cjs/services/storage-service/db-stores/NominatorMetadata.js +4 -4
  20. package/cjs/services/transaction-service/index.js +6 -1
  21. package/constants/index.d.ts +1 -1
  22. package/constants/index.js +1 -1
  23. package/koni/api/staking/bonding/amplitude.d.ts +4 -0
  24. package/koni/api/staking/bonding/amplitude.js +81 -0
  25. package/koni/api/staking/bonding/astar.d.ts +4 -0
  26. package/koni/api/staking/bonding/astar.js +102 -1
  27. package/koni/api/staking/bonding/index.d.ts +1 -0
  28. package/koni/api/staking/bonding/index.js +38 -4
  29. package/koni/api/staking/bonding/paraChain.d.ts +4 -0
  30. package/koni/api/staking/bonding/paraChain.js +95 -0
  31. package/koni/api/staking/bonding/relayChain.d.ts +5 -0
  32. package/koni/api/staking/bonding/relayChain.js +185 -10
  33. package/koni/api/staking/index.d.ts +4 -4
  34. package/koni/api/staking/index.js +11 -11
  35. package/koni/api/staking/paraChain.d.ts +5 -5
  36. package/koni/api/staking/paraChain.js +201 -131
  37. package/koni/api/staking/relayChain.d.ts +4 -4
  38. package/koni/api/staking/relayChain.js +66 -67
  39. package/koni/api/staking/subsquidStaking.d.ts +1 -1
  40. package/koni/api/staking/subsquidStaking.js +6 -11
  41. package/koni/background/cron.js +1 -26
  42. package/koni/background/handlers/State.d.ts +2 -2
  43. package/koni/background/handlers/State.js +17 -19
  44. package/koni/background/subscription.d.ts +2 -1
  45. package/koni/background/subscription.js +58 -13
  46. package/package.json +5 -5
  47. package/packageInfo.js +1 -1
  48. package/services/chain-service/utils.js +6 -1
  49. package/services/storage-service/DatabaseService.d.ts +2 -2
  50. package/services/storage-service/DatabaseService.js +7 -3
  51. package/services/storage-service/db-stores/ChainStakingMetadata.d.ts +1 -0
  52. package/services/storage-service/db-stores/ChainStakingMetadata.js +3 -0
  53. package/services/storage-service/db-stores/NominatorMetadata.d.ts +2 -2
  54. package/services/storage-service/db-stores/NominatorMetadata.js +4 -4
  55. package/services/transaction-service/index.js +6 -1
@@ -110,8 +110,7 @@ export interface StakingJson {
110
110
  }
111
111
  export interface StakingRewardJson {
112
112
  ready: boolean;
113
- slowInterval: Array<StakingRewardItem>;
114
- fastInterval: Array<StakingRewardItem>;
113
+ data: Record<string, StakingRewardItem>;
115
114
  }
116
115
  export interface PriceJson {
117
116
  ready?: boolean;
@@ -1077,15 +1076,15 @@ export interface ChainStakingMetadata {
1077
1076
  chain: string;
1078
1077
  type: StakingType;
1079
1078
  era: number;
1080
- expectedReturn?: number;
1081
- inflation?: number;
1082
1079
  minJoinNominationPool?: string;
1083
1080
  minStake: string;
1084
- nominatorCount?: number;
1085
1081
  maxValidatorPerNominator: number;
1086
1082
  maxWithdrawalRequestPerValidator: number;
1087
1083
  allowCancelUnstaking: boolean;
1088
1084
  unstakingPeriod: number;
1085
+ expectedReturn?: number;
1086
+ inflation?: number;
1087
+ nominatorCount?: number;
1089
1088
  }
1090
1089
  export interface NominationInfo {
1091
1090
  chain: string;
@@ -56,7 +56,7 @@ const CRON_REFRESH_NFT_INTERVAL = 7200000;
56
56
  exports.CRON_REFRESH_NFT_INTERVAL = CRON_REFRESH_NFT_INTERVAL;
57
57
  const CRON_REFRESH_STAKING_REWARD_INTERVAL = 900000;
58
58
  exports.CRON_REFRESH_STAKING_REWARD_INTERVAL = CRON_REFRESH_STAKING_REWARD_INTERVAL;
59
- const CRON_REFRESH_STAKING_REWARD_FAST_INTERVAL = 45000;
59
+ const CRON_REFRESH_STAKING_REWARD_FAST_INTERVAL = 300000;
60
60
  exports.CRON_REFRESH_STAKING_REWARD_FAST_INTERVAL = CRON_REFRESH_STAKING_REWARD_FAST_INTERVAL;
61
61
  const CRON_REFRESH_HISTORY_INTERVAL = 900000;
62
62
  exports.CRON_REFRESH_HISTORY_INTERVAL = CRON_REFRESH_HISTORY_INTERVAL;
@@ -10,6 +10,8 @@ exports.getAmplitudeNominatorMetadata = getAmplitudeNominatorMetadata;
10
10
  exports.getAmplitudeStakingMetadata = getAmplitudeStakingMetadata;
11
11
  exports.getAmplitudeUnbondingExtrinsic = getAmplitudeUnbondingExtrinsic;
12
12
  exports.getAmplitudeWithdrawalExtrinsic = getAmplitudeWithdrawalExtrinsic;
13
+ exports.subscribeAmplitudeNominatorMetadata = subscribeAmplitudeNominatorMetadata;
14
+ exports.subscribeAmplitudeStakingMetadata = subscribeAmplitudeStakingMetadata;
13
15
  var _KoniTypes = require("@subwallet/extension-base/background/KoniTypes");
14
16
  var _utils = require("@subwallet/extension-base/koni/api/staking/bonding/utils");
15
17
  var _constants = require("@subwallet/extension-base/services/chain-service/constants");
@@ -19,6 +21,30 @@ var _utilCrypto = require("@polkadot/util-crypto");
19
21
  // Copyright 2019-2022 @subwallet/extension-koni authors & contributors
20
22
  // SPDX-License-Identifier: Apache-2.0
21
23
 
24
+ function subscribeAmplitudeStakingMetadata(chain, substrateApi, callback) {
25
+ return substrateApi.api.query.parachainStaking.round(_round => {
26
+ const roundObj = _round.toHuman();
27
+ const round = (0, _utils2.parseRawNumber)(roundObj.current);
28
+ const maxDelegations = substrateApi.api.consts.parachainStaking.maxDelegationsPerRound.toString();
29
+ const minDelegatorStake = substrateApi.api.consts.parachainStaking.minDelegatorStake.toString();
30
+ const unstakingDelay = substrateApi.api.consts.parachainStaking.stakeDuration.toString();
31
+ const _blockPerRound = substrateApi.api.consts.parachainStaking.defaultBlocksPerRound.toString();
32
+ const blockPerRound = parseFloat(_blockPerRound);
33
+ const blockDuration = (_constants._STAKING_ERA_LENGTH_MAP[chain] || _constants._STAKING_ERA_LENGTH_MAP.default) / blockPerRound; // in hours
34
+ const unstakingPeriod = blockDuration * parseInt(unstakingDelay);
35
+ callback(chain, {
36
+ chain,
37
+ type: _KoniTypes.StakingType.NOMINATED,
38
+ era: round,
39
+ minStake: minDelegatorStake,
40
+ maxValidatorPerNominator: parseInt(maxDelegations),
41
+ maxWithdrawalRequestPerValidator: 1,
42
+ // by default
43
+ allowCancelUnstaking: true,
44
+ unstakingPeriod
45
+ });
46
+ });
47
+ }
22
48
  async function getAmplitudeStakingMetadata(chain, substrateApi) {
23
49
  const chainApi = await substrateApi.isReady;
24
50
  const _round = (await chainApi.api.query.parachainStaking.round()).toHuman();
@@ -42,6 +68,63 @@ async function getAmplitudeStakingMetadata(chain, substrateApi) {
42
68
  unstakingPeriod
43
69
  };
44
70
  }
71
+ async function subscribeAmplitudeNominatorMetadata(chainInfo, address, substrateApi, delegatorState, unstakingInfo) {
72
+ const nominationList = [];
73
+ const unstakingList = [];
74
+ const minDelegatorStake = substrateApi.api.consts.parachainStaking.minDelegatorStake.toString();
75
+ let activeStake = '0';
76
+ if (delegatorState) {
77
+ // delegatorState can be null while unstaking all
78
+ const identityInfo = substrateApi.api.query.identity ? (await substrateApi.api.query.identity.identityOf(delegatorState.owner)).toPrimitive() : undefined;
79
+ const identity = identityInfo ? (0, _utils.parseIdentity)(identityInfo) : undefined;
80
+ activeStake = delegatorState.amount.toString();
81
+ const bnActiveStake = new _util.BN(activeStake);
82
+ let delegationStatus = _KoniTypes.StakingStatus.NOT_EARNING;
83
+ if (bnActiveStake.gt(_util.BN_ZERO) && bnActiveStake.gte(new _util.BN(minDelegatorStake))) {
84
+ delegationStatus = _KoniTypes.StakingStatus.EARNING_REWARD;
85
+ }
86
+ nominationList.push({
87
+ status: delegationStatus,
88
+ chain: chainInfo.slug,
89
+ validatorAddress: delegatorState.owner,
90
+ activeStake: delegatorState.amount.toString(),
91
+ validatorMinStake: '0',
92
+ hasUnstaking: !!unstakingInfo && Object.values(unstakingInfo).length > 0,
93
+ validatorIdentity: identity
94
+ });
95
+ }
96
+ if (unstakingInfo && Object.values(unstakingInfo).length > 0) {
97
+ const _currentBlockInfo = await substrateApi.api.rpc.chain.getHeader();
98
+ const currentBlockInfo = _currentBlockInfo.toPrimitive();
99
+ const currentBlockNumber = currentBlockInfo.number;
100
+ const _blockPerRound = substrateApi.api.consts.parachainStaking.defaultBlocksPerRound.toString();
101
+ const blockPerRound = parseFloat(_blockPerRound);
102
+ const nearestUnstakingBlock = Object.keys(unstakingInfo)[0];
103
+ const nearestUnstakingAmount = Object.values(unstakingInfo)[0];
104
+ const blockDuration = (_constants._STAKING_ERA_LENGTH_MAP[chainInfo.slug] || _constants._STAKING_ERA_LENGTH_MAP.default) / blockPerRound; // in hours
105
+
106
+ const isClaimable = parseInt(nearestUnstakingBlock) - currentBlockNumber <= 0;
107
+ const remainingBlock = parseInt(nearestUnstakingBlock) - (currentBlockNumber + 1);
108
+ const waitingTime = remainingBlock * blockDuration;
109
+ unstakingList.push({
110
+ chain: chainInfo.slug,
111
+ status: isClaimable ? _KoniTypes.UnstakingStatus.CLAIMABLE : _KoniTypes.UnstakingStatus.UNLOCKING,
112
+ claimable: nearestUnstakingAmount.toString(),
113
+ waitingTime: waitingTime > 0 ? waitingTime : 0,
114
+ validatorAddress: (delegatorState === null || delegatorState === void 0 ? void 0 : delegatorState.owner) || undefined
115
+ });
116
+ }
117
+ const stakingStatus = (0, _utils.getStakingStatusByNominations)(new _util.BN(activeStake), nominationList);
118
+ return {
119
+ chain: chainInfo.slug,
120
+ type: _KoniTypes.StakingType.NOMINATED,
121
+ status: stakingStatus,
122
+ address: address,
123
+ activeStake: activeStake,
124
+ nominations: nominationList,
125
+ unstakings: unstakingList
126
+ };
127
+ }
45
128
  async function getAmplitudeNominatorMetadata(chainInfo, address, substrateApi) {
46
129
  if ((0, _utilCrypto.isEthereumAddress)(address)) {
47
130
  return;
@@ -12,6 +12,8 @@ exports.getAstarStakingMetadata = getAstarStakingMetadata;
12
12
  exports.getAstarUnbondingExtrinsic = getAstarUnbondingExtrinsic;
13
13
  exports.getAstarWithdrawable = getAstarWithdrawable;
14
14
  exports.getAstarWithdrawalExtrinsic = getAstarWithdrawalExtrinsic;
15
+ exports.subscribeAstarNominatorMetadata = subscribeAstarNominatorMetadata;
16
+ exports.subscribeAstarStakingMetadata = subscribeAstarStakingMetadata;
15
17
  var _KoniTypes = require("@subwallet/extension-base/background/KoniTypes");
16
18
  var _utils = require("@subwallet/extension-base/koni/api/staking/bonding/utils");
17
19
  var _constants = require("@subwallet/extension-base/services/chain-service/constants");
@@ -22,6 +24,26 @@ var _utilCrypto = require("@polkadot/util-crypto");
22
24
  // Copyright 2019-2022 @subwallet/extension-koni authors & contributors
23
25
  // SPDX-License-Identifier: Apache-2.0
24
26
 
27
+ function subscribeAstarStakingMetadata(chain, substrateApi, callback) {
28
+ return substrateApi.api.query.dappsStaking.currentEra(_currentEra => {
29
+ const era = _currentEra.toString();
30
+ const minDelegatorStake = substrateApi.api.consts.dappsStaking.minimumStakingAmount.toString();
31
+ const unstakingDelay = substrateApi.api.consts.dappsStaking.unbondingPeriod.toString();
32
+ const unstakingPeriod = parseInt(unstakingDelay) * _constants._STAKING_ERA_LENGTH_MAP[chain];
33
+ callback(chain, {
34
+ chain,
35
+ type: _KoniTypes.StakingType.NOMINATED,
36
+ era: parseInt(era),
37
+ minStake: minDelegatorStake,
38
+ maxValidatorPerNominator: 100,
39
+ // temporary fix for Astar, there's no limit for now
40
+ maxWithdrawalRequestPerValidator: 1,
41
+ // by default
42
+ allowCancelUnstaking: true,
43
+ unstakingPeriod
44
+ });
45
+ });
46
+ }
25
47
  async function getAstarStakingMetadata(chain, substrateApi) {
26
48
  const aprPromise = new Promise(function (resolve) {
27
49
  (0, _crossFetch.default)(`https://api.astar.network/api/v1/${chain}/dapps-staking/apr`, {
@@ -57,6 +79,87 @@ async function getAstarStakingMetadata(chain, substrateApi) {
57
79
  unstakingPeriod
58
80
  };
59
81
  }
82
+ async function subscribeAstarNominatorMetadata(chainInfo, address, substrateApi, ledger) {
83
+ const nominationList = [];
84
+ const unstakingList = [];
85
+ const allDappsReq = new Promise(function (resolve) {
86
+ (0, _crossFetch.default)(`https://api.astar.network/api/v1/${chainInfo.slug}/dapps-staking/dapps`, {
87
+ method: 'GET'
88
+ }).then(resp => {
89
+ resolve(resp.json());
90
+ }).catch(console.error);
91
+ });
92
+ const [_allDapps, _era, _stakerInfo] = await Promise.all([allDappsReq, substrateApi.api.query.dappsStaking.currentEra(), substrateApi.api.query.dappsStaking.generalStakerInfo.entries(address)]);
93
+ const currentEra = _era.toString();
94
+ const minDelegatorStake = substrateApi.api.consts.dappsStaking.minimumStakingAmount.toString();
95
+ const allDapps = _allDapps;
96
+ let bnTotalActiveStake = _util.BN_ZERO;
97
+ if (_stakerInfo.length > 0) {
98
+ const dAppInfoMap = {};
99
+ allDapps.forEach(dappInfo => {
100
+ dAppInfoMap[dappInfo.address.toLowerCase()] = dappInfo;
101
+ });
102
+ for (const item of _stakerInfo) {
103
+ const data = item[0].toHuman();
104
+ const stakedDapp = data[1];
105
+ const stakeData = item[1].toPrimitive();
106
+ const stakeList = stakeData.stakes;
107
+ const dappAddress = stakedDapp.Evm ? stakedDapp.Evm.toLowerCase() : stakedDapp.Wasm;
108
+ const currentStake = stakeList.slice(-1)[0].staked.toString() || '0';
109
+ const bnCurrentStake = new _util.BN(currentStake);
110
+ if (bnCurrentStake.gt(_util.BN_ZERO)) {
111
+ const dappStakingStatus = bnCurrentStake.gt(_util.BN_ZERO) && bnCurrentStake.gte(new _util.BN(minDelegatorStake)) ? _KoniTypes.StakingStatus.EARNING_REWARD : _KoniTypes.StakingStatus.NOT_EARNING;
112
+ bnTotalActiveStake = bnTotalActiveStake.add(bnCurrentStake);
113
+ const dappInfo = dAppInfoMap[dappAddress];
114
+ nominationList.push({
115
+ status: dappStakingStatus,
116
+ chain: chainInfo.slug,
117
+ validatorAddress: dappAddress.toLowerCase(),
118
+ activeStake: currentStake,
119
+ validatorMinStake: '0',
120
+ validatorIdentity: dappInfo === null || dappInfo === void 0 ? void 0 : dappInfo.name,
121
+ hasUnstaking: false // cannot get unstaking info by dapp
122
+ });
123
+ }
124
+ }
125
+ }
126
+
127
+ const unlockingChunks = ledger.unbondingInfo.unlockingChunks;
128
+ if (unlockingChunks.length > 0) {
129
+ for (const unlockingChunk of unlockingChunks) {
130
+ const isClaimable = unlockingChunk.unlockEra - parseInt(currentEra) <= 0;
131
+ const remainingEra = unlockingChunk.unlockEra - (parseInt(currentEra) + 1);
132
+ const waitingTime = remainingEra * _constants._STAKING_ERA_LENGTH_MAP[chainInfo.slug];
133
+ unstakingList.push({
134
+ chain: chainInfo.slug,
135
+ status: isClaimable ? _KoniTypes.UnstakingStatus.CLAIMABLE : _KoniTypes.UnstakingStatus.UNLOCKING,
136
+ claimable: unlockingChunk.amount.toString(),
137
+ waitingTime: waitingTime > 0 ? waitingTime : 0
138
+ });
139
+ }
140
+ }
141
+ if (nominationList.length === 0 && unstakingList.length === 0) {
142
+ return {
143
+ chain: chainInfo.slug,
144
+ type: _KoniTypes.StakingType.NOMINATED,
145
+ address,
146
+ status: _KoniTypes.StakingStatus.NOT_STAKING,
147
+ activeStake: '0',
148
+ nominations: [],
149
+ unstakings: []
150
+ };
151
+ }
152
+ const stakingStatus = (0, _utils.getStakingStatusByNominations)(bnTotalActiveStake, nominationList);
153
+ return {
154
+ chain: chainInfo.slug,
155
+ type: _KoniTypes.StakingType.NOMINATED,
156
+ address: address,
157
+ activeStake: bnTotalActiveStake.toString(),
158
+ nominations: nominationList,
159
+ unstakings: unstakingList,
160
+ status: stakingStatus
161
+ };
162
+ }
60
163
  async function getAstarNominatorMetadata(chainInfo, address, substrateApi) {
61
164
  if ((0, _utilCrypto.isEthereumAddress)(address)) {
62
165
  return;
@@ -181,7 +284,7 @@ async function getAstarDappsInfo(networkKey, substrateApi) {
181
284
  allDappsInfo.push({
182
285
  commission: 0,
183
286
  expectedReturn: 0,
184
- address: dappAddress.toLowerCase(),
287
+ address: (0, _utilCrypto.isEthereumAddress)(dappAddress) ? dappAddress.toLowerCase() : dappAddress,
185
288
  totalStake: totalStake,
186
289
  ownStake: '0',
187
290
  otherStake: totalStake.toString(),
@@ -12,6 +12,7 @@ exports.getNominatorMetadata = getNominatorMetadata;
12
12
  exports.getUnbondingExtrinsic = getUnbondingExtrinsic;
13
13
  exports.getValidatorsInfo = getValidatorsInfo;
14
14
  exports.getWithdrawalExtrinsic = getWithdrawalExtrinsic;
15
+ exports.subscribeEssentialChainStakingMetadata = subscribeEssentialChainStakingMetadata;
15
16
  exports.validateBondingCondition = validateBondingCondition;
16
17
  exports.validateUnbondingCondition = validateUnbondingCondition;
17
18
  var _KoniTypes = require("@subwallet/extension-base/background/KoniTypes");
@@ -117,4 +118,38 @@ async function getCancelWithdrawalExtrinsic(substrateApi, chain, selectedUnstaki
117
118
  return (0, _paraChain.getParaCancelWithdrawalExtrinsic)(substrateApi, selectedUnstaking);
118
119
  }
119
120
  return (0, _relayChain.getRelayCancelWithdrawalExtrinsic)(substrateApi, selectedUnstaking);
121
+ }
122
+ function subscribeEssentialChainStakingMetadata(substrateApiMap, chainInfoMap, callback) {
123
+ const unsubList = [];
124
+
125
+ // eslint-disable-next-line @typescript-eslint/no-misused-promises
126
+ Object.values(chainInfoMap).forEach(async chainInfo => {
127
+ const substrateApi = await substrateApiMap[chainInfo.slug].isReady;
128
+ if (_constants._STAKING_CHAIN_GROUP.astar.includes(chainInfo.slug)) {
129
+ const unsub = await (0, _astar.subscribeAstarStakingMetadata)(chainInfo.slug, substrateApi, callback);
130
+
131
+ // @ts-ignore
132
+ unsubList.push(unsub);
133
+ } else if (_constants._STAKING_CHAIN_GROUP.para.includes(chainInfo.slug)) {
134
+ const unsub = await (0, _paraChain.subscribeParaChainStakingMetadata)(chainInfo.slug, substrateApi, callback);
135
+
136
+ // @ts-ignore
137
+ unsubList.push(unsub);
138
+ } else if (_constants._STAKING_CHAIN_GROUP.amplitude.includes(chainInfo.slug)) {
139
+ const unsub = await (0, _amplitude.subscribeAmplitudeStakingMetadata)(chainInfo.slug, substrateApi, callback);
140
+
141
+ // @ts-ignore
142
+ unsubList.push(unsub);
143
+ } else if (_constants._STAKING_CHAIN_GROUP.relay.includes(chainInfo.slug)) {
144
+ const unsub = await (0, _relayChain.subscribeRelayChainStakingMetadata)(chainInfo, substrateApi, callback);
145
+
146
+ // @ts-ignore
147
+ unsubList.push(unsub);
148
+ }
149
+ });
150
+ return () => {
151
+ unsubList.forEach(unsub => {
152
+ unsub && unsub();
153
+ });
154
+ };
120
155
  }
@@ -12,6 +12,8 @@ exports.getParaWithdrawalExtrinsic = getParaWithdrawalExtrinsic;
12
12
  exports.getParachainCollatorsInfo = getParachainCollatorsInfo;
13
13
  exports.getTuringCancelCompoundingExtrinsic = getTuringCancelCompoundingExtrinsic;
14
14
  exports.getTuringCompoundExtrinsic = getTuringCompoundExtrinsic;
15
+ exports.subscribeParaChainNominatorMetadata = subscribeParaChainNominatorMetadata;
16
+ exports.subscribeParaChainStakingMetadata = subscribeParaChainStakingMetadata;
15
17
  exports.validateParaChainBondingCondition = validateParaChainBondingCondition;
16
18
  exports.validateParaChainUnbondingCondition = validateParaChainUnbondingCondition;
17
19
  var _TransactionError = require("@subwallet/extension-base/background/errors/TransactionError");
@@ -97,6 +99,26 @@ function validateParaChainBondingCondition(chainInfo, amount, selectedCollators,
97
99
  }
98
100
  return errors;
99
101
  }
102
+ function subscribeParaChainStakingMetadata(chain, substrateApi, callback) {
103
+ return substrateApi.api.query.parachainStaking.round(_round => {
104
+ const roundObj = _round.toHuman();
105
+ const round = (0, _utils3.parseRawNumber)(roundObj.current);
106
+ const maxDelegations = substrateApi.api.consts.parachainStaking.maxDelegationsPerDelegator.toString();
107
+ const unstakingDelay = substrateApi.api.consts.parachainStaking.delegationBondLessDelay.toString();
108
+ const unstakingPeriod = parseInt(unstakingDelay) * (_constants._STAKING_ERA_LENGTH_MAP[chain] || _constants._STAKING_ERA_LENGTH_MAP.default);
109
+ callback(chain, {
110
+ chain,
111
+ type: _KoniTypes.StakingType.NOMINATED,
112
+ era: round,
113
+ minStake: '0',
114
+ maxValidatorPerNominator: parseInt(maxDelegations),
115
+ maxWithdrawalRequestPerValidator: 1,
116
+ // by default
117
+ allowCancelUnstaking: true,
118
+ unstakingPeriod
119
+ });
120
+ });
121
+ }
100
122
  async function getParaChainStakingMetadata(chain, substrateApi) {
101
123
  const chainApi = await substrateApi.isReady;
102
124
  const _round = (await chainApi.api.query.parachainStaking.round()).toHuman();
@@ -135,6 +157,81 @@ async function getParaChainStakingMetadata(chain, substrateApi) {
135
157
  unstakingPeriod
136
158
  };
137
159
  }
160
+ async function subscribeParaChainNominatorMetadata(chainInfo, address, substrateApi, delegatorState) {
161
+ const nominationList = [];
162
+ const unstakingMap = {};
163
+ let bnTotalActiveStake = _util.BN_ZERO;
164
+ const _roundInfo = await substrateApi.api.query.parachainStaking.round();
165
+ const roundInfo = _roundInfo.toPrimitive();
166
+ const currentRound = roundInfo.current;
167
+ await Promise.all(delegatorState.delegations.map(async delegation => {
168
+ const [_delegationScheduledRequests, _identity, _collatorInfo] = await Promise.all([substrateApi.api.query.parachainStaking.delegationScheduledRequests(delegation.owner), substrateApi.api.query.identity.identityOf(delegation.owner), substrateApi.api.query.parachainStaking.candidateInfo(delegation.owner)]);
169
+ const collatorInfo = _collatorInfo.toPrimitive();
170
+ const minDelegation = collatorInfo === null || collatorInfo === void 0 ? void 0 : collatorInfo.lowestTopDelegationAmount.toString();
171
+ const identityInfo = _identity.toHuman();
172
+ const delegationScheduledRequests = _delegationScheduledRequests.toPrimitive();
173
+ const identity = (0, _utils.parseIdentity)(identityInfo);
174
+ let hasUnstaking = false;
175
+ let delegationStatus = _KoniTypes.StakingStatus.NOT_EARNING;
176
+
177
+ // parse unstaking info
178
+ if (delegationScheduledRequests) {
179
+ for (const scheduledRequest of delegationScheduledRequests) {
180
+ if ((0, _utils3.reformatAddress)(scheduledRequest.delegator, 0) === (0, _utils3.reformatAddress)(address, 0)) {
181
+ // add network prefix
182
+ const isClaimable = scheduledRequest.whenExecutable - currentRound <= 0;
183
+ const remainingEra = scheduledRequest.whenExecutable - (currentRound + 1);
184
+ const waitingTime = remainingEra * _constants._STAKING_ERA_LENGTH_MAP[chainInfo.slug];
185
+ const claimable = Object.values(scheduledRequest.action)[0];
186
+ unstakingMap[delegation.owner] = {
187
+ chain: chainInfo.slug,
188
+ status: isClaimable ? _KoniTypes.UnstakingStatus.CLAIMABLE : _KoniTypes.UnstakingStatus.UNLOCKING,
189
+ validatorAddress: delegation.owner,
190
+ claimable: claimable.toString(),
191
+ waitingTime: waitingTime > 0 ? waitingTime : 0
192
+ };
193
+ hasUnstaking = true;
194
+ break; // only handle 1 scheduledRequest per collator
195
+ }
196
+ }
197
+ }
198
+
199
+ const bnStake = new _util.BN(delegation.amount);
200
+ const bnUnstakeBalance = unstakingMap[delegation.owner] ? new _util.BN(unstakingMap[delegation.owner].claimable) : _util.BN_ZERO;
201
+ const bnActiveStake = bnStake.sub(bnUnstakeBalance);
202
+ if (bnActiveStake.gt(_util.BN_ZERO) && bnActiveStake.gte(new _util.BN(minDelegation))) {
203
+ delegationStatus = _KoniTypes.StakingStatus.EARNING_REWARD;
204
+ }
205
+ bnTotalActiveStake = bnTotalActiveStake.add(bnActiveStake);
206
+ nominationList.push({
207
+ chain: chainInfo.slug,
208
+ status: delegationStatus,
209
+ validatorAddress: delegation.owner,
210
+ validatorIdentity: identity,
211
+ activeStake: bnActiveStake.toString(),
212
+ hasUnstaking,
213
+ validatorMinStake: collatorInfo.lowestTopDelegationAmount.toString()
214
+ });
215
+ }));
216
+
217
+ // await Promise.all(nominationList.map(async (nomination) => {
218
+ // const _collatorInfo = await substrateApi.api.query.parachainStaking.candidateInfo(nomination.validatorAddress);
219
+ // const collatorInfo = _collatorInfo.toPrimitive() as unknown as ParachainStakingCandidateMetadata;
220
+ //
221
+ // nomination.validatorMinStake = collatorInfo.lowestTopDelegationAmount.toString();
222
+ // }));
223
+
224
+ const stakingStatus = (0, _utils.getStakingStatusByNominations)(bnTotalActiveStake, nominationList);
225
+ return {
226
+ chain: chainInfo.slug,
227
+ type: _KoniTypes.StakingType.NOMINATED,
228
+ status: stakingStatus,
229
+ address: address,
230
+ activeStake: bnTotalActiveStake.toString(),
231
+ nominations: nominationList,
232
+ unstakings: Object.values(unstakingMap)
233
+ };
234
+ }
138
235
  async function getParaChainNominatorMetadata(chainInfo, address, substrateApi) {
139
236
  if ((0, _utils2._isChainEvmCompatible)(chainInfo) && !(0, _utilCrypto.isEthereumAddress)(address)) {
140
237
  return;