@subwallet/extension-base 1.1.21-3 → 1.1.23-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 (59) hide show
  1. package/background/KoniTypes.d.ts +10 -1
  2. package/cjs/koni/api/dotsama/balance.js +51 -1
  3. package/cjs/koni/api/dotsama/crowdloan.js +29 -3
  4. package/cjs/koni/api/dotsama/transfer.js +10 -3
  5. package/cjs/koni/api/staking/bonding/astar.js +9 -5
  6. package/cjs/koni/api/staking/bonding/relayChain.js +2 -2
  7. package/cjs/koni/api/xcm/index.js +6 -1
  8. package/cjs/koni/api/xcm/polkadotXcm.js +1 -3
  9. package/cjs/koni/api/xcm/xTokens.js +1 -1
  10. package/cjs/koni/background/handlers/Extension.js +117 -99
  11. package/cjs/koni/background/handlers/State.js +12 -6
  12. package/cjs/koni/background/subscription.js +1 -1
  13. package/cjs/packageInfo.js +1 -1
  14. package/cjs/services/chain-service/constants.js +8 -4
  15. package/cjs/services/chain-service/handler/SubstrateApi.js +9 -0
  16. package/cjs/services/chain-service/handler/chain-spec/goldberg.js +123 -0
  17. package/cjs/services/chain-service/index.js +18 -0
  18. package/cjs/services/history-service/helpers/subscan-extrinsic-parser-helper.js +53 -0
  19. package/cjs/services/history-service/index.js +78 -21
  20. package/cjs/services/history-service/subscan-history.js +107 -0
  21. package/cjs/services/subscan-service/index.js +109 -4
  22. package/cjs/services/subscan-service/subscan-chain-map.js +82 -8
  23. package/cjs/utils/index.js +10 -1
  24. package/koni/api/dotsama/balance.js +51 -1
  25. package/koni/api/dotsama/crowdloan.d.ts +2 -2
  26. package/koni/api/dotsama/crowdloan.js +29 -2
  27. package/koni/api/dotsama/transfer.js +10 -3
  28. package/koni/api/staking/bonding/astar.js +9 -5
  29. package/koni/api/staking/bonding/relayChain.js +2 -2
  30. package/koni/api/xcm/index.js +6 -1
  31. package/koni/api/xcm/polkadotXcm.js +2 -4
  32. package/koni/api/xcm/xTokens.js +1 -1
  33. package/koni/background/handlers/Extension.d.ts +1 -0
  34. package/koni/background/handlers/Extension.js +20 -3
  35. package/koni/background/handlers/State.d.ts +1 -0
  36. package/koni/background/handlers/State.js +13 -7
  37. package/koni/background/subscription.js +1 -1
  38. package/package.json +21 -6
  39. package/packageInfo.js +1 -1
  40. package/services/chain-service/constants.d.ts +3 -0
  41. package/services/chain-service/constants.js +8 -5
  42. package/services/chain-service/handler/SubstrateApi.js +8 -0
  43. package/services/chain-service/handler/chain-spec/goldberg.d.ts +115 -0
  44. package/services/chain-service/handler/chain-spec/goldberg.js +116 -0
  45. package/services/chain-service/index.d.ts +1 -0
  46. package/services/chain-service/index.js +18 -0
  47. package/services/history-service/helpers/subscan-extrinsic-parser-helper.d.ts +6 -0
  48. package/services/history-service/helpers/subscan-extrinsic-parser-helper.js +44 -0
  49. package/services/history-service/index.d.ts +10 -6
  50. package/services/history-service/index.js +79 -22
  51. package/services/history-service/subscan-history.d.ts +5 -0
  52. package/services/history-service/subscan-history.js +100 -0
  53. package/services/subscan-service/index.d.ts +10 -2
  54. package/services/subscan-service/index.js +105 -4
  55. package/services/subscan-service/subscan-chain-map.d.ts +9 -3
  56. package/services/subscan-service/subscan-chain-map.js +78 -5
  57. package/services/subscan-service/types.d.ts +146 -0
  58. package/utils/index.d.ts +1 -0
  59. package/utils/index.js +7 -0
@@ -6,11 +6,12 @@ Object.defineProperty(exports, "__esModule", {
6
6
  });
7
7
  exports.SubscanService = void 0;
8
8
  var _SWError = require("@subwallet/extension-base/background/errors/SWError");
9
- var _subscanChainMap = _interopRequireDefault(require("@subwallet/extension-base/services/subscan-service/subscan-chain-map"));
9
+ var _utils = require("@subwallet/extension-base/utils");
10
10
  var _crossFetch = _interopRequireDefault(require("cross-fetch"));
11
11
  // Copyright 2019-2022 @subwallet/extension-base
12
12
  // SPDX-License-Identifier: Apache-2.0
13
13
 
14
+ const QUERY_ROW = 100;
14
15
  class SubscanService {
15
16
  limitRate = 2; // limit per interval check
16
17
  intervalCheck = 1000; // interval check in ms
@@ -21,17 +22,18 @@ class SubscanService {
21
22
  getId() {
22
23
  return this.nextId++;
23
24
  }
24
- constructor(options) {
25
+ constructor(subscanChainMap, options) {
26
+ this.subscanChainMap = subscanChainMap;
25
27
  this.limitRate = (options === null || options === void 0 ? void 0 : options.limitRate) || this.limitRate;
26
28
  this.intervalCheck = (options === null || options === void 0 ? void 0 : options.intervalCheck) || this.intervalCheck;
27
29
  this.maxRetry = (options === null || options === void 0 ? void 0 : options.maxRetry) || this.maxRetry;
28
30
  }
29
31
  getApiUrl(chain, path) {
30
- const subscanChain = _subscanChainMap.default[chain];
32
+ const subscanChain = this.subscanChainMap[chain];
31
33
  if (!subscanChain) {
32
34
  throw new _SWError.SWError('NOT_SUPPORTED', 'Chain is not supported');
33
35
  }
34
- return `https://${chain}.api.subscan.io/${path}`;
36
+ return `https://${subscanChain}.api.subscan.io/${path}`;
35
37
  }
36
38
  postRequest(url, body) {
37
39
  return (0, _crossFetch.default)(url, {
@@ -89,6 +91,12 @@ class SubscanService {
89
91
  });
90
92
  }, this.intervalCheck);
91
93
  }
94
+ checkSupportedSubscanChain(chain) {
95
+ return !!this.subscanChainMap[chain];
96
+ }
97
+ setSubscanChainMap(subscanChainMap) {
98
+ this.subscanChainMap = subscanChainMap;
99
+ }
92
100
 
93
101
  // Implement Subscan API
94
102
  getMultiChainBalance(address) {
@@ -103,5 +111,102 @@ class SubscanService {
103
111
  return jsonData.data;
104
112
  });
105
113
  }
114
+ getCrowdloanContributions(relayChain, address) {
115
+ let page = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 0;
116
+ return this.addRequest(async () => {
117
+ const rs = await this.postRequest(this.getApiUrl(relayChain, 'api/scan/account/contributions'), {
118
+ include_total: true,
119
+ page,
120
+ row: QUERY_ROW,
121
+ who: address
122
+ });
123
+ if (rs.status !== 200) {
124
+ throw new _SWError.SWError('SubscanService.getCrowdloanContributions', await rs.text());
125
+ }
126
+ const jsonData = await rs.json();
127
+ return jsonData.data;
128
+ });
129
+ }
130
+ getExtrinsicsList(chain, address) {
131
+ let page = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 0;
132
+ return this.addRequest(async () => {
133
+ const rs = await this.postRequest(this.getApiUrl(chain, 'api/scan/extrinsics'), {
134
+ page,
135
+ row: QUERY_ROW,
136
+ address
137
+ });
138
+ if (rs.status !== 200) {
139
+ throw new _SWError.SWError('SubscanService.getExtrinsicsList', await rs.text());
140
+ }
141
+ const jsonData = await rs.json();
142
+ return jsonData.data;
143
+ });
144
+ }
145
+ async fetchAllPossibleExtrinsicItems(chain, address, cbAfterEachRequest) {
146
+ let count = 0;
147
+ const resultMap = {};
148
+ const _getExtrinsicItems = async page => {
149
+ const res = await this.getExtrinsicsList(chain, address, page);
150
+ if (!res || !res.count || !res.extrinsics || !res.extrinsics.length) {
151
+ return;
152
+ }
153
+ if (res.count > count) {
154
+ count = res.count;
155
+ }
156
+ cbAfterEachRequest === null || cbAfterEachRequest === void 0 ? void 0 : cbAfterEachRequest(res.extrinsics);
157
+ res.extrinsics.forEach(item => {
158
+ resultMap[item.extrinsic_hash] = item;
159
+ });
160
+ if (Object.values(resultMap).length < count) {
161
+ await (0, _utils.wait)(100);
162
+ await _getExtrinsicItems(++page);
163
+ }
164
+ };
165
+ await _getExtrinsicItems(0);
166
+ return Object.values(resultMap);
167
+ }
168
+ getTransfersList(chain, address) {
169
+ let page = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 0;
170
+ let direction = arguments.length > 3 ? arguments[3] : undefined;
171
+ const requestBody = {
172
+ page,
173
+ row: QUERY_ROW,
174
+ address
175
+ };
176
+ if (direction) {
177
+ requestBody.direction = direction;
178
+ }
179
+ return this.addRequest(async () => {
180
+ const rs = await this.postRequest(this.getApiUrl(chain, 'api/v2/scan/transfers'), requestBody);
181
+ if (rs.status !== 200) {
182
+ throw new _SWError.SWError('SubscanService.getTransfersList', await rs.text());
183
+ }
184
+ const jsonData = await rs.json();
185
+ return jsonData.data;
186
+ });
187
+ }
188
+ async fetchAllPossibleTransferItems(chain, address, direction, cbAfterEachRequest) {
189
+ let count = 0;
190
+ const resultMap = {};
191
+ const _getTransferItems = async page => {
192
+ const res = await this.getTransfersList(chain, address, page, direction);
193
+ if (!res || !res.count || !res.transfers || !res.transfers.length) {
194
+ return;
195
+ }
196
+ if (res.count > count) {
197
+ count = res.count;
198
+ }
199
+ cbAfterEachRequest === null || cbAfterEachRequest === void 0 ? void 0 : cbAfterEachRequest(res.transfers);
200
+ res.transfers.forEach(item => {
201
+ resultMap[item.hash] = item;
202
+ });
203
+ if (Object.values(resultMap).length < count) {
204
+ await (0, _utils.wait)(100);
205
+ await _getTransferItems(++page);
206
+ }
207
+ };
208
+ await _getTransferItems(0);
209
+ return Object.values(resultMap);
210
+ }
106
211
  }
107
212
  exports.SubscanService = SubscanService;
@@ -3,11 +3,81 @@
3
3
  Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
- exports.default = exports.SUBSCAN_CHAIN_MAP_REVERSE = void 0;
6
+ exports.SUBSCAN_BALANCE_CHAIN_MAP_REVERSE = exports.SUBSCAN_BALANCE_CHAIN_MAP = exports.SUBSCAN_API_CHAIN_MAP = void 0;
7
7
  // Copyright 2019-2022 @subwallet/extension-base
8
8
  // SPDX-License-Identifier: Apache-2.0
9
9
 
10
- const SUBSCAN_CHAIN_MAP = {
10
+ /**
11
+ * Only use this for initiating SubscanService or unit test
12
+ */
13
+ const SUBSCAN_API_CHAIN_MAP = {
14
+ polkadot: 'polkadot',
15
+ kusama: 'kusama',
16
+ moonbeam: 'moonbeam',
17
+ pioneer: 'pioneer',
18
+ aleph: 'alephzero',
19
+ astar: 'astar',
20
+ statemint: 'assethub-polkadot',
21
+ acala: 'acala',
22
+ shiden: 'shiden',
23
+ shibuya: 'shibuya',
24
+ westend: 'westend',
25
+ rococo: 'rococo',
26
+ moonbase: 'moonbase',
27
+ moonriver: 'moonriver',
28
+ turing: 'turing',
29
+ bifrost: 'bifrost-kusama',
30
+ bifrost_dot: 'bifrost',
31
+ calamari: 'calamari',
32
+ parallel: 'parallel',
33
+ clover: 'clv',
34
+ hydradx_main: 'hydradx',
35
+ centrifuge: 'centrifuge',
36
+ interlay: 'interlay',
37
+ nodle: 'nodle',
38
+ darwinia2: 'darwinia',
39
+ polkadex: 'polkadex-parachain',
40
+ composableFinance: 'composable',
41
+ phala: 'phala',
42
+ crust: 'crust-parachain',
43
+ statemine: 'assethub-kusama',
44
+ karura: 'karura',
45
+ khala: 'khala',
46
+ kilt: 'spiritnet',
47
+ basilisk: 'basilisk',
48
+ altair: 'altair',
49
+ heiko: 'parallel-heiko',
50
+ kintsugi: 'kintsugi',
51
+ picasso: 'picasso',
52
+ unique_network: 'unique',
53
+ zeitgeist: 'zeitgeist',
54
+ sakura: 'sakura',
55
+ shadow: 'shadow',
56
+ robonomics: 'robonomics',
57
+ integritee: 'integritee',
58
+ crabParachain: 'crab',
59
+ acala_testnet: 'acala-testnet',
60
+ mangatax_para: 'mangatax',
61
+ origintrail: 'origintrail',
62
+ subspace_gemini_3g: 'subspace',
63
+ bajun: 'bajun',
64
+ tanganika: 'datahighway',
65
+ kilt_peregrine: 'kilt-testnet',
66
+ dockPosMainnet: 'dock',
67
+ polymesh: 'polymesh',
68
+ sora_substrate: 'sora',
69
+ joystream: 'joystream',
70
+ vara_network: 'vara',
71
+ krest_network: 'krest',
72
+ crust_mainnet: 'crust',
73
+ manta_network: 'manta'
74
+ };
75
+
76
+ /**
77
+ * Map for token self-activation feature
78
+ */
79
+ exports.SUBSCAN_API_CHAIN_MAP = SUBSCAN_API_CHAIN_MAP;
80
+ const SUBSCAN_BALANCE_CHAIN_MAP = {
11
81
  polkadot: 'polkadot',
12
82
  kusama: 'kusama',
13
83
  moonbeam: 'moonbeam',
@@ -27,7 +97,7 @@ const SUBSCAN_CHAIN_MAP = {
27
97
  clover: 'clover',
28
98
  hydradx_main: 'hydradx',
29
99
  edgeware: 'edgeware',
30
- centrifuge: 'centrifuge',
100
+ centrifuge: 'centrifuge-parachain',
31
101
  interlay: 'interlay',
32
102
  nodle: 'nodle',
33
103
  darwinia: 'darwinia',
@@ -63,12 +133,16 @@ const SUBSCAN_CHAIN_MAP = {
63
133
  bajun: 'bajun',
64
134
  snow: 'snow',
65
135
  kilt_peregrine: 'kilt-testnet',
66
- polymesh: 'polymesh'
136
+ polymesh: 'polymesh',
137
+ bifrost_dot: 'bifrost-p',
138
+ vara_network: 'vara',
139
+ bifrost: 'bifrost',
140
+ creditcoin: 'creditcoin',
141
+ joystream: 'joystream'
67
142
  };
68
- const SUBSCAN_CHAIN_MAP_REVERSE = Object.fromEntries(Object.entries(SUBSCAN_CHAIN_MAP).map(_ref => {
143
+ exports.SUBSCAN_BALANCE_CHAIN_MAP = SUBSCAN_BALANCE_CHAIN_MAP;
144
+ const SUBSCAN_BALANCE_CHAIN_MAP_REVERSE = Object.fromEntries(Object.entries(SUBSCAN_BALANCE_CHAIN_MAP).map(_ref => {
69
145
  let [k, v] = _ref;
70
146
  return [v, k];
71
147
  }));
72
- exports.SUBSCAN_CHAIN_MAP_REVERSE = SUBSCAN_CHAIN_MAP_REVERSE;
73
- var _default = SUBSCAN_CHAIN_MAP;
74
- exports.default = _default;
148
+ exports.SUBSCAN_BALANCE_CHAIN_MAP_REVERSE = SUBSCAN_BALANCE_CHAIN_MAP_REVERSE;
@@ -36,6 +36,7 @@ var _exportNames = {
36
36
  getDomainFromUrl: true,
37
37
  waitTimeout: true,
38
38
  stripUrl: true,
39
+ wait: true,
39
40
  canDerive: true
40
41
  };
41
42
  Object.defineProperty(exports, "canDerive", {
@@ -68,6 +69,7 @@ exports.stripUrl = void 0;
68
69
  exports.sumBN = sumBN;
69
70
  exports.toUnit = void 0;
70
71
  exports.utf16ToString = utf16ToString;
72
+ exports.wait = wait;
71
73
  exports.waitTimeout = waitTimeout;
72
74
  var _KoniTypes = require("@subwallet/extension-base/background/KoniTypes");
73
75
  var _constants = require("@subwallet/extension-base/constants");
@@ -435,4 +437,11 @@ const stripUrl = url => {
435
437
  const parts = url.split('/');
436
438
  return parts[2];
437
439
  };
438
- exports.stripUrl = stripUrl;
440
+ exports.stripUrl = stripUrl;
441
+ function wait(milliseconds) {
442
+ return new Promise(resolve => {
443
+ setTimeout(() => {
444
+ resolve();
445
+ }, milliseconds);
446
+ });
447
+ }
@@ -69,6 +69,8 @@ export async function subscribeSubstrateBalance(addresses, chainInfo, chain, net
69
69
  unsubLocalToken = await subscribeEqBalanceAccountPallet(addresses, chain, networkAPI.api, callBack, true);
70
70
  } else if (_BALANCE_CHAIN_GROUP.equilibrium_parachain.includes(chain)) {
71
71
  unsubLocalToken = await subscribeEquilibriumTokenBalance(addresses, chain, networkAPI.api, callBack, true);
72
+ } else if (_BALANCE_CHAIN_GROUP.centrifuge.includes(chain)) {
73
+ unsubLocalToken = await subscribeOrmlTokensPallet(addresses, chain, networkAPI.api, callBack);
72
74
  }
73
75
  if (_isChainEvmCompatible(chainInfo)) {
74
76
  unsubEvmContractToken = subscribeERC20Interval(addresses, chain, evmApiMap, callBack);
@@ -95,7 +97,8 @@ async function subscribeWithSystemAccountPallet(addresses, chainInfo, networkAPI
95
97
  let [total, reserved, miscFrozen, feeFrozen] = [new BN(0), new BN(0), new BN(0), new BN(0)];
96
98
  let pooledStakingBalance = BN_ZERO;
97
99
  if (_isSubstrateRelayChain(chainInfo) && networkAPI.query.nominationPools) {
98
- const poolMemberDatas = await networkAPI.query.nominationPools.poolMembers.multi(addresses);
100
+ var _networkAPI$query$nom;
101
+ const poolMemberDatas = await ((_networkAPI$query$nom = networkAPI.query.nominationPools.poolMembers) === null || _networkAPI$query$nom === void 0 ? void 0 : _networkAPI$query$nom.multi(addresses));
99
102
  if (poolMemberDatas) {
100
103
  for (const _poolMemberData of poolMemberDatas) {
101
104
  const poolMemberData = _poolMemberData.toPrimitive();
@@ -279,6 +282,53 @@ async function subscribeEqBalanceAccountPallet(addresses, chain, api, callBack,
279
282
  });
280
283
  };
281
284
  }
285
+
286
+ // eslint-disable-next-line @typescript-eslint/require-await
287
+ async function subscribeOrmlTokensPallet(addresses, chain, api, callBack) {
288
+ const tokenTypes = [_AssetType.LOCAL];
289
+ const tokenMap = state.getAssetByChainAndAsset(chain, tokenTypes);
290
+ const unsubList = Object.values(tokenMap).map(async tokenInfo => {
291
+ try {
292
+ const onChainInfo = _getTokenOnChainInfo(tokenInfo);
293
+
294
+ // Get Token Balance
295
+ // @ts-ignore
296
+ const unsub = await api.query.ormlTokens.accounts.multi(addresses.map(address => [address, onChainInfo]), balances => {
297
+ const tokenBalance = {
298
+ reserved: sumBN(balances.map(b => b.reserved || new BN(0))),
299
+ frozen: sumBN(balances.map(b => b.frozen || new BN(0))),
300
+ free: sumBN(balances.map(b => b.free || new BN(0))) // free is actually total balance
301
+ };
302
+
303
+ // free balance = total balance - frozen misc
304
+ // locked balance = reserved + frozen misc
305
+ const freeBalance = tokenBalance.free.sub(tokenBalance.frozen);
306
+ const lockedBalance = tokenBalance.frozen.add(tokenBalance.reserved);
307
+ callBack({
308
+ tokenSlug: tokenInfo.slug,
309
+ state: APIItemState.READY,
310
+ free: freeBalance.toString(),
311
+ locked: lockedBalance.toString(),
312
+ substrateInfo: {
313
+ reserved: tokenBalance.reserved.toString(),
314
+ miscFrozen: tokenBalance.frozen.toString()
315
+ }
316
+ });
317
+ });
318
+ return unsub;
319
+ } catch (err) {
320
+ console.warn(err);
321
+ return undefined;
322
+ }
323
+ });
324
+ return () => {
325
+ unsubList.forEach(subProm => {
326
+ subProm.then(unsub => {
327
+ unsub && unsub();
328
+ }).catch(console.error);
329
+ });
330
+ };
331
+ }
282
332
  async function subscribeTokensAccountsPallet(addresses, chain, api, callBack, includeNativeToken) {
283
333
  const tokenTypes = includeNativeToken ? [_AssetType.NATIVE, _AssetType.LOCAL] : [_AssetType.LOCAL];
284
334
  const tokenMap = state.getAssetByChainAndAsset(chain, tokenTypes);
@@ -1,8 +1,8 @@
1
- import { _ChainInfo, _CrowdloanFund } from '@subwallet/chain-list/types';
1
+ import { _CrowdloanFund } from '@subwallet/chain-list/types';
2
2
  import { CrowdloanItem } from '@subwallet/extension-base/background/KoniTypes';
3
3
  import { _SubstrateApi } from '@subwallet/extension-base/services/chain-service/types';
4
4
  export declare type CrowdloanFundInfo = _CrowdloanFund & {
5
5
  chain: string;
6
6
  };
7
7
  export declare const subscribeAcalaContributeInterval: (polkadotAddresses: string[], fundInfo: _CrowdloanFund, callback: (rs: CrowdloanItem) => void) => () => void;
8
- export declare function subscribeCrowdloan(addresses: string[], substrateApiMap: Record<string, _SubstrateApi>, callback: (networkKey: string, rs: CrowdloanItem) => void, chainInfoMap: Record<string, _ChainInfo>): Promise<(() => void) | undefined>;
8
+ export declare function subscribeCrowdloan(addresses: string[], substrateApiMap: Record<string, _SubstrateApi>, callback: (networkKey: string, rs: CrowdloanItem) => void): Promise<(() => void) | undefined>;
@@ -16,7 +16,20 @@ const STATUS_MAP = {
16
16
  [_FundStatus.FAILED]: CrowdloanParaState.FAILED,
17
17
  [_FundStatus.WON]: CrowdloanParaState.COMPLETED
18
18
  };
19
+ function getChainInfoMap(chainInfoList) {
20
+ const result = {};
21
+ chainInfoList.forEach(ci => {
22
+ if (ci.slug) {
23
+ result[ci.slug] = ci;
24
+ }
25
+ });
26
+ return result;
27
+ }
19
28
  const getOnlineFundList = fetchStaticData('crowdloan-funds');
29
+ const getOnlineChainInfoMap = (async () => {
30
+ const chainInfoList = await fetchStaticData('chains');
31
+ return getChainInfoMap(chainInfoList);
32
+ })();
20
33
  function getRPCCrowdloan(parentAPI, fundInfo, hexAddresses, callback) {
21
34
  const {
22
35
  auctionIndex,
@@ -123,14 +136,28 @@ export const subscribeAcalaContributeInterval = (polkadotAddresses, fundInfo, ca
123
136
  // }, {} as Record<string, CrowdloanParaState>);
124
137
  // }
125
138
 
139
+ function isNeedToUpdateLatestFundInfoMap(latestMap, chainSlug, fundInfo) {
140
+ if (!latestMap[chainSlug]) {
141
+ return true;
142
+ }
143
+ if (!fundInfo.auctionIndex && fundInfo.status === _FundStatus.IN_AUCTION) {
144
+ return true;
145
+ }
146
+ if (fundInfo.auctionIndex > latestMap[chainSlug].auctionIndex) {
147
+ return true;
148
+ }
149
+ return false;
150
+ }
151
+
126
152
  // Get All crowdloan
127
- export async function subscribeCrowdloan(addresses, substrateApiMap, callback, chainInfoMap) {
153
+ export async function subscribeCrowdloan(addresses, substrateApiMap, callback) {
128
154
  const unsubMap = {};
129
155
  const latestMap = {};
130
156
  const rawFundList = await getOnlineFundList;
157
+ const chainInfoMap = await getOnlineChainInfoMap;
131
158
  rawFundList.forEach(fundInfo => {
132
159
  const chainSlug = fundInfo.chain;
133
- if (!latestMap[chainSlug] || fundInfo.auctionIndex > latestMap[chainSlug].auctionIndex) {
160
+ if (isNeedToUpdateLatestFundInfoMap(latestMap, chainSlug, fundInfo)) {
134
161
  latestMap[chainSlug] = fundInfo;
135
162
  }
136
163
  });
@@ -97,8 +97,11 @@ export async function checkSupportTransfer(networkKey, tokenInfo, substrateApiMa
97
97
  // result.supportTransfer = true;
98
98
  // result.supportTransferAll = true;
99
99
  } else if (_TRANSFER_CHAIN_GROUP.avail.includes(networkKey)) {
100
- result.supportTransfer = false;
101
- result.supportTransferAll = false;
100
+ result.supportTransfer = true;
101
+ result.supportTransferAll = true;
102
+ } else if (_TRANSFER_CHAIN_GROUP.centrifuge.includes(networkKey)) {
103
+ result.supportTransfer = true;
104
+ result.supportTransferAll = true;
102
105
  }
103
106
  return result;
104
107
  }
@@ -181,7 +184,11 @@ export const createTransferExtrinsic = async ({
181
184
  if (transferAll) {
182
185
  transfer = api.tx.balances.transferAll(to, false);
183
186
  } else if (value) {
184
- transfer = api.tx.balances.transferKeepAlive(to, new BN(value));
187
+ if (api.tx.balances.transferKeepAlive) {
188
+ transfer = api.tx.balances.transferKeepAlive(to, new BN(value));
189
+ } else {
190
+ transfer = api.tx.balances.transfer(to, new BN(value));
191
+ }
185
192
  }
186
193
  }
187
194
  return [transfer, transferAmount || value];
@@ -63,6 +63,9 @@ export async function getAstarStakingMetadata(chain, substrateApi) {
63
63
  unstakingPeriod
64
64
  };
65
65
  }
66
+ const convertAddress = address => {
67
+ return isEthereumAddress(address) ? address.toLowerCase() : address;
68
+ };
66
69
  export async function subscribeAstarNominatorMetadata(chainInfo, address, substrateApi, ledger) {
67
70
  const nominationList = [];
68
71
  const unstakingList = [];
@@ -81,14 +84,15 @@ export async function subscribeAstarNominatorMetadata(chainInfo, address, substr
81
84
  if (_stakerInfo.length > 0) {
82
85
  const dAppInfoMap = {};
83
86
  allDapps.forEach(dappInfo => {
84
- dAppInfoMap[dappInfo.address.toLowerCase()] = dappInfo;
87
+ dAppInfoMap[convertAddress(dappInfo.address)] = dappInfo;
85
88
  });
86
89
  for (const item of _stakerInfo) {
87
90
  const data = item[0].toHuman();
88
91
  const stakedDapp = data[1];
89
92
  const stakeData = item[1].toPrimitive();
90
93
  const stakeList = stakeData.stakes;
91
- const dappAddress = stakedDapp.Evm ? stakedDapp.Evm.toLowerCase() : stakedDapp.Wasm;
94
+ const _dappAddress = stakedDapp.Evm ? stakedDapp.Evm.toLowerCase() : stakedDapp.Wasm;
95
+ const dappAddress = convertAddress(_dappAddress);
92
96
  const currentStake = stakeList.slice(-1)[0].staked.toString() || '0';
93
97
  const bnCurrentStake = new BN(currentStake);
94
98
  if (bnCurrentStake.gt(BN_ZERO)) {
@@ -98,7 +102,7 @@ export async function subscribeAstarNominatorMetadata(chainInfo, address, substr
98
102
  nominationList.push({
99
103
  status: dappStakingStatus,
100
104
  chain: chainInfo.slug,
101
- validatorAddress: isEthereumAddress(dappAddress) ? dappAddress.toLowerCase() : dappAddress,
105
+ validatorAddress: dappAddress,
102
106
  activeStake: currentStake,
103
107
  validatorMinStake: '0',
104
108
  validatorIdentity: dappInfo === null || dappInfo === void 0 ? void 0 : dappInfo.name,
@@ -176,7 +180,7 @@ export async function getAstarNominatorMetadata(chainInfo, address, substrateApi
176
180
  const stakedDapp = data[1];
177
181
  const stakeData = item[1].toPrimitive();
178
182
  const stakeList = stakeData.stakes;
179
- const dappAddress = isEthereumAddress(stakedDapp.Evm) ? stakedDapp.Evm.toLowerCase() : stakedDapp.Evm;
183
+ const dappAddress = convertAddress(stakedDapp.Evm);
180
184
  const currentStake = stakeList.slice(-1)[0].staked.toString() || '0';
181
185
  const bnCurrentStake = new BN(currentStake);
182
186
  if (bnCurrentStake.gt(BN_ZERO)) {
@@ -269,7 +273,7 @@ export async function getAstarDappsInfo(networkKey, substrateApi) {
269
273
  allDappsInfo.push({
270
274
  commission: 0,
271
275
  expectedReturn: 0,
272
- address: isEthereumAddress(dappAddress) ? dappAddress.toLowerCase() : dappAddress,
276
+ address: convertAddress(dappAddress),
273
277
  totalStake: totalStake,
274
278
  ownStake: '0',
275
279
  otherStake: totalStake.toString(),
@@ -77,9 +77,9 @@ export function validateRelayBondingCondition(chainInfo, amount, selectedValidat
77
77
  }
78
78
  export function subscribeRelayChainStakingMetadata(chainInfo, substrateApi, callback) {
79
79
  return substrateApi.api.query.staking.currentEra(async _currentEra => {
80
- var _substrateApi$api$que, _substrateApi$api$que2, _substrateApi$api$que3, _substrateApi$api$que4, _substrateApi$api$que5, _substrateApi$api$que6, _substrateApi$api$que7;
80
+ var _substrateApi$api$con, _substrateApi$api$con2, _substrateApi$api$que, _substrateApi$api$que2, _substrateApi$api$que3, _substrateApi$api$que4, _substrateApi$api$que5, _substrateApi$api$que6, _substrateApi$api$que7;
81
81
  const currentEra = _currentEra.toString();
82
- const maxNominations = substrateApi.api.consts.staking.maxNominations.toString();
82
+ const maxNominations = ((_substrateApi$api$con = substrateApi.api.consts.staking) === null || _substrateApi$api$con === void 0 ? void 0 : (_substrateApi$api$con2 = _substrateApi$api$con.maxNominations) === null || _substrateApi$api$con2 === void 0 ? void 0 : _substrateApi$api$con2.toString()) || '16'; // TODO
83
83
  const maxUnlockingChunks = substrateApi.api.consts.staking.maxUnlockingChunks.toString();
84
84
  const unlockingEras = substrateApi.api.consts.staking.bondingDuration.toString();
85
85
  const [_totalEraStake, _totalIssuance, _auctionCounter, _minNominatorBond, _minPoolJoin, _minimumActiveStake] = await Promise.all([substrateApi.api.query.staking.erasTotalStake(parseInt(currentEra)), substrateApi.api.query.balances.totalIssuance(), (_substrateApi$api$que = substrateApi.api.query.auctions) === null || _substrateApi$api$que === void 0 ? void 0 : _substrateApi$api$que.auctionCounter(), substrateApi.api.query.staking.minNominatorBond(), (_substrateApi$api$que2 = substrateApi.api.query) === null || _substrateApi$api$que2 === void 0 ? void 0 : (_substrateApi$api$que3 = _substrateApi$api$que2.nominationPools) === null || _substrateApi$api$que3 === void 0 ? void 0 : _substrateApi$api$que3.minJoinBond(), ((_substrateApi$api$que4 = substrateApi.api.query) === null || _substrateApi$api$que4 === void 0 ? void 0 : (_substrateApi$api$que5 = _substrateApi$api$que4.staking) === null || _substrateApi$api$que5 === void 0 ? void 0 : _substrateApi$api$que5.minimumActiveStake) && ((_substrateApi$api$que6 = substrateApi.api.query) === null || _substrateApi$api$que6 === void 0 ? void 0 : (_substrateApi$api$que7 = _substrateApi$api$que6.staking) === null || _substrateApi$api$que7 === void 0 ? void 0 : _substrateApi$api$que7.minimumActiveStake())]);
@@ -5,6 +5,7 @@ import { getExtrinsicByPolkadotXcmPallet } from '@subwallet/extension-base/koni/
5
5
  import { getExtrinsicByXcmPalletPallet } from '@subwallet/extension-base/koni/api/xcm/xcmPallet';
6
6
  import { getExtrinsicByXtokensPallet } from '@subwallet/extension-base/koni/api/xcm/xTokens';
7
7
  import { _XCM_CHAIN_GROUP } from '@subwallet/extension-base/services/chain-service/constants';
8
+ import { _isNativeToken } from '@subwallet/extension-base/services/chain-service/utils';
8
9
  export const createXcmExtrinsic = async ({
9
10
  chainInfoMap,
10
11
  destinationTokenInfo,
@@ -19,7 +20,11 @@ export const createXcmExtrinsic = async ({
19
20
  const api = chainApi.api;
20
21
  let extrinsic;
21
22
  if (_XCM_CHAIN_GROUP.polkadotXcm.includes(originTokenInfo.originChain)) {
22
- extrinsic = getExtrinsicByPolkadotXcmPallet(originTokenInfo, originChainInfo, destinationChainInfo, recipient, sendingValue, api);
23
+ if (['astar', 'shiden'].includes(originChainInfo.slug) && !_isNativeToken(originTokenInfo)) {
24
+ extrinsic = getExtrinsicByXtokensPallet(originTokenInfo, originChainInfo, destinationChainInfo, recipient, sendingValue, api);
25
+ } else {
26
+ extrinsic = getExtrinsicByPolkadotXcmPallet(originTokenInfo, originChainInfo, destinationChainInfo, recipient, sendingValue, api);
27
+ }
23
28
  } else if (_XCM_CHAIN_GROUP.xcmPallet.includes(originTokenInfo.originChain)) {
24
29
  extrinsic = getExtrinsicByXcmPalletPallet(originTokenInfo, originChainInfo, destinationChainInfo, recipient, sendingValue, api);
25
30
  } else {
@@ -2,7 +2,7 @@
2
2
  // SPDX-License-Identifier: Apache-2.0
3
3
 
4
4
  import { getBeneficiary, getDestinationChainLocation, getDestWeight, getTokenLocation } from '@subwallet/extension-base/koni/api/xcm/utils';
5
- import { _isNativeToken, _isSubstrateRelayChain } from '@subwallet/extension-base/services/chain-service/utils';
5
+ import { _isSubstrateRelayChain } from '@subwallet/extension-base/services/chain-service/utils';
6
6
  export function getExtrinsicByPolkadotXcmPallet(tokenInfo, originChainInfo, destinationChainInfo, recipientAddress, value, api) {
7
7
  const weightParam = getDestWeight();
8
8
  const version = ['statemint', 'statemine', 'shiden', 'astar'].includes(originChainInfo.slug) ? 'V3' : 'V1';
@@ -10,9 +10,7 @@ export function getExtrinsicByPolkadotXcmPallet(tokenInfo, originChainInfo, dest
10
10
  const destination = getDestinationChainLocation(originChainInfo, destinationChainInfo, version);
11
11
  let assetLocation = getTokenLocation(tokenInfo, value, version);
12
12
  let method = 'limitedReserveTransferAssets';
13
- if (['astar', 'shiden'].includes(originChainInfo.slug) && !_isNativeToken(tokenInfo)) {
14
- method = 'limitedReserveWithdrawAssets';
15
- } else if (['statemint', 'statemine'].includes(originChainInfo.slug) && _isSubstrateRelayChain(destinationChainInfo)) {
13
+ if (['statemint', 'statemine'].includes(originChainInfo.slug) && _isSubstrateRelayChain(destinationChainInfo)) {
16
14
  assetLocation = {
17
15
  [version]: [{
18
16
  id: {
@@ -19,6 +19,6 @@ function getCurrencyId(tokenInfo) {
19
19
  }
20
20
  export function getExtrinsicByXtokensPallet(tokenInfo, originChainInfo, destinationChainInfo, recipientAddress, value, api) {
21
21
  const weightParam = ['pioneer'].includes(originChainInfo.slug) ? FOUR_INSTRUCTIONS_WEIGHT : getDestWeight();
22
- const destVersion = ['moonbeam', 'moonriver', 'bifrost_dot', 'interlay', 'hydradx_main', 'acala', 'parallel'].includes(originChainInfo.slug) ? 'V3' : undefined;
22
+ const destVersion = ['moonbeam', 'moonriver', 'bifrost_dot', 'interlay', 'hydradx_main', 'acala', 'parallel', 'astar', 'shiden'].includes(originChainInfo.slug) ? 'V3' : undefined;
23
23
  return api.tx.xTokens.transfer(getCurrencyId(tokenInfo), value, getDestMultilocation(destinationChainInfo, recipientAddress, destVersion), weightParam);
24
24
  }
@@ -116,6 +116,7 @@ export default class KoniExtension {
116
116
  private getStaking;
117
117
  private subscribeStaking;
118
118
  private subscribeHistory;
119
+ private subscribeHistoryByChainAndAddress;
119
120
  private validateTransfer;
120
121
  private makeTransfer;
121
122
  private validateCrossChainTransfer;
@@ -1439,6 +1439,21 @@ export default class KoniExtension {
1439
1439
  // Re-filter
1440
1440
  return historySubject.getValue().filter(item => addresses.some(address => isSameAddress(item.address, address)));
1441
1441
  }
1442
+ subscribeHistoryByChainAndAddress({
1443
+ address,
1444
+ chain
1445
+ }, id, port) {
1446
+ const cb = createSubscription(id, port);
1447
+ const subscribeHistoriesResponse = this.#koniState.historyService.subscribeHistories(chain, address, cb);
1448
+ this.createUnsubscriptionHandle(id, subscribeHistoriesResponse.unsubscribe);
1449
+ port.onDisconnect.addListener(() => {
1450
+ this.cancelSubscription(id);
1451
+ });
1452
+ return {
1453
+ id,
1454
+ items: subscribeHistoriesResponse.value
1455
+ };
1456
+ }
1442
1457
 
1443
1458
  // Save address to contact
1444
1459
  // private addContact (to: string) {
@@ -2874,10 +2889,10 @@ export default class KoniExtension {
2874
2889
  registry.register(currentMetadata === null || currentMetadata === void 0 ? void 0 : currentMetadata.types);
2875
2890
  }
2876
2891
  const [, chainInfo] = this.#koniState.findNetworkKeyByGenesisHash(payload.genesisHash);
2877
- if (chainInfo && _API_OPTIONS_CHAIN_GROUP.avail.includes(chainInfo.slug)) {
2892
+ if (chainInfo && (_API_OPTIONS_CHAIN_GROUP.avail.includes(chainInfo.slug) || _API_OPTIONS_CHAIN_GROUP.goldberg.includes(chainInfo.slug))) {
2878
2893
  const isChainActive = this.#koniState.getChainStateByKey(chainInfo.slug).active;
2879
2894
  if (!isChainActive) {
2880
- reject(new Error('Unable to sign'));
2895
+ reject(new Error('Please active chain {{chain}} before sign'.replaceAll('{{chain}}', chainInfo.name)));
2881
2896
  return false;
2882
2897
  } else {
2883
2898
  registry = this.#koniState.getSubstrateApi(chainInfo.slug).api.registry;
@@ -3236,7 +3251,7 @@ export default class KoniExtension {
3236
3251
  }
3237
3252
  const wcId = request.request.id;
3238
3253
  const params = request.request.params;
3239
- const requiredNamespaces = params.requiredNamespaces;
3254
+ const requiredNamespaces = params.requiredNamespaces || {};
3240
3255
  const optionalNamespaces = params.optionalNamespaces || {};
3241
3256
  const availableNamespaces = {};
3242
3257
  const namespaces = {};
@@ -3746,6 +3761,8 @@ export default class KoniExtension {
3746
3761
  return this.subscribeStakingReward(id, port);
3747
3762
  case 'pri(transaction.history.getSubscription)':
3748
3763
  return await this.subscribeHistory(id, port);
3764
+ case 'pri(transaction.history.subscribe)':
3765
+ return this.subscribeHistoryByChainAndAddress(request, id, port);
3749
3766
 
3750
3767
  /* Account management */
3751
3768
  // Add account
@@ -84,6 +84,7 @@ export default class KoniState {
84
84
  sign(url: string, request: RequestSign, account: AccountJson): Promise<ResponseSigning>;
85
85
  get authSubjectV2(): BehaviorSubject<import("@subwallet/extension-base/background/types").AuthorizeRequest[]>;
86
86
  generateDefaultBalanceMap(): Record<string, BalanceItem>;
87
+ private afterChainServiceInit;
87
88
  init(): Promise<void>;
88
89
  initMantaPay(password: string): Promise<void>;
89
90
  private startSubscription;