@talismn/balances 0.0.0-pr2043-20250615092436 → 0.0.0-pr2043-20250617025844
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/dist/declarations/src/EvmTokenFetcher.d.ts +2 -2
- package/dist/declarations/src/MiniMetadataUpdater.d.ts +3 -3
- package/dist/declarations/src/libVersion.d.ts +1 -0
- package/dist/declarations/src/modules/EvmErc20Module.d.ts +4 -7
- package/dist/declarations/src/modules/EvmNativeModule.d.ts +4 -7
- package/dist/declarations/src/modules/EvmUniswapV2Module.d.ts +4 -7
- package/dist/declarations/src/modules/SubstrateAssetsModule.d.ts +2 -5
- package/dist/declarations/src/modules/SubstrateForeignAssetsModule.d.ts +2 -5
- package/dist/declarations/src/modules/SubstrateNativeModule/index.d.ts +0 -1
- package/dist/declarations/src/modules/SubstrateNativeModule/types.d.ts +2 -3
- package/dist/declarations/src/modules/SubstrateNativeModule/util/balanceLockTypes.d.ts +2 -4
- package/dist/declarations/src/modules/SubstrateNativeModule/util/buildQueries.d.ts +2 -2
- package/dist/declarations/src/modules/SubstratePsp22Module.d.ts +4 -7
- package/dist/declarations/src/modules/SubstrateTokensModule.d.ts +2 -5
- package/dist/declarations/src/modules/index.d.ts +1 -207
- package/dist/declarations/src/modules/util/buildStorageCoders.d.ts +3 -3
- package/dist/declarations/src/modules/util/findChainMeta.d.ts +2 -2
- package/dist/declarations/src/types/balances.d.ts +7 -145
- package/dist/declarations/src/types/balancetypes.d.ts +6 -16
- package/dist/declarations/src/types/minimetadatas.d.ts +4 -13
- package/dist/talismn-balances.cjs.dev.js +400 -405
- package/dist/talismn-balances.cjs.prod.js +400 -405
- package/dist/talismn-balances.esm.js +398 -395
- package/package.json +6 -7
@@ -1,8 +1,5 @@
|
|
1
|
-
import
|
2
|
-
import { fetchMiniMetadatas, fetchInitMiniMetadatas, availableTokenLogoFilenames, githubTokenLogoUrl, EvmErc20TokenSchema } from '@talismn/chaindata-provider';
|
3
|
-
import { fetchBestMetadata, getScaleApi } from '@talismn/sapi';
|
1
|
+
import { fetchInitMiniMetadatas, evmErc20TokenId as evmErc20TokenId$1, githubTokenLogoUrl, EvmErc20TokenSchema, evmNativeTokenId, evmUniswapV2TokenId, subAssetTokenId, subForeignAssetTokenId, subNativeTokenId, subPsp22TokenId, subTokensTokenId } from '@talismn/chaindata-provider';
|
4
2
|
import { Dexie, liveQuery } from 'dexie';
|
5
|
-
import isEqual from 'lodash/isEqual';
|
6
3
|
import { from, Observable, scan, share, map, switchAll, combineLatest, mergeMap, toArray, interval, startWith, exhaustMap, pipe, filter, shareReplay, combineLatestWith, distinctUntilChanged, firstValueFrom, BehaviorSubject, debounceTime, takeUntil, switchMap, withLatestFrom, concatMap } from 'rxjs';
|
7
4
|
import anylogger from 'anylogger';
|
8
5
|
import { newTokenRates } from '@talismn/token-rates';
|
@@ -12,6 +9,7 @@ import { u8aToHex, assert, stringCamelCase, u8aConcatStrict, u8aConcat, arrayChu
|
|
12
9
|
import { xxhashAsU8a, blake2AsU8a } from '@polkadot/util-crypto';
|
13
10
|
import pako from 'pako';
|
14
11
|
import { parseAbi, isHex, hexToBigInt } from 'viem';
|
12
|
+
import isEqual from 'lodash/isEqual';
|
15
13
|
import { defineMethod } from '@substrate/txwrapper-core';
|
16
14
|
import { unifyMetadata, decAnyMetadata, getDynamicBuilder, getLookupFn, getMetadataVersion, compactMetadata, encodeMetadata, decodeScale, papiParse, encodeStateKey } from '@talismn/scale';
|
17
15
|
import camelCase from 'lodash/camelCase';
|
@@ -19,11 +17,12 @@ import { Metadata, TypeRegistry } from '@polkadot/types';
|
|
19
17
|
import groupBy from 'lodash/groupBy';
|
20
18
|
import { mergeUint8, toHex } from '@polkadot-api/utils';
|
21
19
|
import { Binary, AccountId } from 'polkadot-api';
|
20
|
+
import PromisePool from '@supercharge/promise-pool';
|
22
21
|
import { ChainConnectionError } from '@talismn/chain-connector';
|
23
22
|
import { u32, u128, Struct } from 'scale-ts';
|
23
|
+
import { getScaleApi } from '@talismn/sapi';
|
24
24
|
import upperFirst from 'lodash/upperFirst';
|
25
25
|
import { Abi } from '@polkadot/api-contract';
|
26
|
-
import { compressToEncodedURIComponent } from 'lz-string';
|
27
26
|
|
28
27
|
// TODO: Document default balances module purpose/usage
|
29
28
|
const DefaultBalanceModule = type => ({
|
@@ -58,8 +57,12 @@ const DefaultBalanceModule = type => ({
|
|
58
57
|
// internal
|
59
58
|
//
|
60
59
|
|
60
|
+
// TODO yeet ?
|
61
|
+
// there is no need to construct a lit of tokens, it's done by∏ chaindata
|
62
|
+
|
61
63
|
/**
|
62
64
|
* Fetches tokens for EVM networks.
|
65
|
+
* @deprecated
|
63
66
|
*/
|
64
67
|
class EvmTokenFetcher {
|
65
68
|
#chaindataProvider;
|
@@ -68,36 +71,46 @@ class EvmTokenFetcher {
|
|
68
71
|
this.#chaindataProvider = chaindataProvider;
|
69
72
|
this.#balanceModules = balanceModules;
|
70
73
|
}
|
71
|
-
async update(
|
72
|
-
|
73
|
-
|
74
|
-
async updateEvmNetworks(evmNetworkIds) {
|
75
|
-
const evmNetworks = new Map((await this.#chaindataProvider.evmNetworks()).map(evmNetwork => [evmNetwork.id, evmNetwork]));
|
76
|
-
const allEvmTokens = {};
|
77
|
-
const evmNetworkConcurrency = 10;
|
78
|
-
await PromisePool.withConcurrency(evmNetworkConcurrency).for(evmNetworkIds).process(async evmNetworkId => {
|
79
|
-
const evmNetwork = evmNetworks.get(evmNetworkId);
|
80
|
-
if (!evmNetwork) return;
|
81
|
-
for (const mod of this.#balanceModules.filter(m => m.type.startsWith("evm-"))) {
|
82
|
-
const balancesConfig = (evmNetwork.balancesConfig ?? []).find(({
|
83
|
-
moduleType
|
84
|
-
}) => moduleType === mod.type);
|
85
|
-
const moduleConfig = balancesConfig?.moduleConfig ?? {};
|
86
|
-
|
87
|
-
// chainMeta arg only needs the isTestnet property, let's save a db roundtrip for now
|
88
|
-
const isTestnet = evmNetwork.isTestnet ?? false;
|
89
|
-
const tokens = await mod.fetchEvmChainTokens(evmNetworkId, {
|
90
|
-
isTestnet
|
91
|
-
}, moduleConfig);
|
92
|
-
for (const [tokenId, token] of Object.entries(tokens)) allEvmTokens[tokenId] = token;
|
93
|
-
}
|
94
|
-
});
|
95
|
-
await this.#chaindataProvider.updateEvmNetworkTokens(Object.values(allEvmTokens));
|
74
|
+
async update(_evmNetworkIds) {
|
75
|
+
// chaindataProvider's tokens should be in sync already
|
76
|
+
// await this.updateEvmNetworks(evmNetworkIds)
|
96
77
|
}
|
78
|
+
|
79
|
+
// private async updateEvmNetworks(evmNetworkIds: EvmNetworkId[]) {
|
80
|
+
// // feels unnecessary, chaindataProvider's tokens should be in sync already
|
81
|
+
// // const evmNetworks = new Map(
|
82
|
+
// // (await this.#chaindataProvider.evmNetworks()).map((evmNetwork) => [
|
83
|
+
// // evmNetwork.id,
|
84
|
+
// // evmNetwork,
|
85
|
+
// // ]),
|
86
|
+
// // )
|
87
|
+
// // const allEvmTokens: TokenList = {}
|
88
|
+
// // const evmNetworkConcurrency = 10
|
89
|
+
// // await PromisePool.withConcurrency(evmNetworkConcurrency)
|
90
|
+
// // .for(evmNetworkIds)
|
91
|
+
// // .process(async (evmNetworkId) => {
|
92
|
+
// // const evmNetwork = evmNetworks.get(evmNetworkId)
|
93
|
+
// // if (!evmNetwork) return
|
94
|
+
// // for (const mod of this.#balanceModules.filter((m) => m.type.startsWith("evm-"))) {
|
95
|
+
// // // const balancesConfig = (evmNetwork.balancesConfig ?? []).find(
|
96
|
+
// // // ({ moduleType }) => moduleType === mod.type,
|
97
|
+
// // // )
|
98
|
+
// // // const moduleConfig = balancesConfig?.moduleConfig ?? {}
|
99
|
+
// // // chainMeta arg only needs the isTestnet property, let's save a db roundtrip for now
|
100
|
+
// // const isTestnet = evmNetwork.isTestnet ?? false
|
101
|
+
// // const tokens = await mod.fetchEvmChainTokens(evmNetworkId, { isTestnet }, moduleConfig)
|
102
|
+
// // for (const [tokenId, token] of Object.entries(tokens)) allEvmTokens[tokenId] = token
|
103
|
+
// // }
|
104
|
+
// // })
|
105
|
+
// // await this.#chaindataProvider.updateEvmNetworkTokens(Object.values(allEvmTokens))
|
106
|
+
// }
|
97
107
|
}
|
98
108
|
|
99
109
|
var packageJson = {
|
100
|
-
name: "@talismn/balances"
|
110
|
+
name: "@talismn/balances",
|
111
|
+
version: "0.0.0-pr2043-20250617025844"};
|
112
|
+
|
113
|
+
const libVersion = packageJson.version;
|
101
114
|
|
102
115
|
var log = anylogger(packageJson.name);
|
103
116
|
|
@@ -309,15 +322,20 @@ class Balances {
|
|
309
322
|
return new SumBalancesFormatter(this);
|
310
323
|
}
|
311
324
|
}
|
312
|
-
|
325
|
+
|
326
|
+
// type BalanceJsonEvm = BalanceJson & { evmNetworkId: string }
|
327
|
+
|
328
|
+
// const isBalanceEvm = (balance: BalanceJson): balance is BalanceJsonEvm => "evmNetworkId" in balance
|
329
|
+
|
313
330
|
const getBalanceId = balance => {
|
314
331
|
const {
|
315
332
|
source,
|
316
333
|
address,
|
317
|
-
tokenId
|
334
|
+
tokenId,
|
335
|
+
networkId
|
318
336
|
} = balance;
|
319
|
-
const locationId = isBalanceEvm(balance) ? balance.evmNetworkId : balance.chainId
|
320
|
-
return [source, address,
|
337
|
+
//const locationId = isBalanceEvm(balance) ? balance.evmNetworkId : balance.chainId
|
338
|
+
return [source, address, networkId, tokenId].filter(isTruthy).join("::");
|
321
339
|
};
|
322
340
|
|
323
341
|
/**
|
@@ -379,17 +397,33 @@ class Balance {
|
|
379
397
|
get address() {
|
380
398
|
return this.#storage.address;
|
381
399
|
}
|
382
|
-
|
383
|
-
|
384
|
-
|
385
|
-
|
386
|
-
|
387
|
-
|
388
|
-
get
|
389
|
-
|
400
|
+
|
401
|
+
// /** @deprecated */
|
402
|
+
// get chainId() {
|
403
|
+
// return isBalanceEvm(this.#storage) ? undefined : this.#storage.chainId
|
404
|
+
// }
|
405
|
+
// /** @deprecated */
|
406
|
+
// get chain() {
|
407
|
+
// return (this.#db?.networks && this.networkId && this.#db?.networks[this.networkId]) || null
|
408
|
+
// }
|
409
|
+
|
410
|
+
// /** @deprecated */
|
411
|
+
// get evmNetworkId() {
|
412
|
+
// return isBalanceEvm(this.#storage) ? this.#storage.evmNetworkId : undefined
|
413
|
+
// }
|
414
|
+
// /** @deprecated */
|
415
|
+
// get evmNetwork() {
|
416
|
+
// return (
|
417
|
+
// (this.#db?.networks && this.networkId && this.#db?.networks[this.networkId]) ||
|
418
|
+
// null
|
419
|
+
// )
|
420
|
+
// }
|
421
|
+
|
422
|
+
get networkId() {
|
423
|
+
return this.#storage.networkId;
|
390
424
|
}
|
391
|
-
get
|
392
|
-
return this.#db?.
|
425
|
+
get network() {
|
426
|
+
return this.#db?.networks && this.networkId && this.#db?.networks[this.networkId] || null;
|
393
427
|
}
|
394
428
|
get tokenId() {
|
395
429
|
return this.#storage.tokenId;
|
@@ -408,9 +442,11 @@ class Balance {
|
|
408
442
|
//
|
409
443
|
// This means that those rates are always available for calculating the uniswapv2 rates,
|
410
444
|
// regardless of whether or not the underlying erc20s are actually in chaindata and enabled.
|
411
|
-
if (this.isSource("evm-uniswapv2") && this.token?.type === "evm-uniswapv2" &&
|
412
|
-
|
413
|
-
|
445
|
+
if (this.isSource("evm-uniswapv2") && this.token?.type === "evm-uniswapv2" // &&
|
446
|
+
//this.evmNetworkId
|
447
|
+
) {
|
448
|
+
const tokenId0 = evmErc20TokenId(this.networkId, this.token.tokenAddress0);
|
449
|
+
const tokenId1 = evmErc20TokenId(this.networkId, this.token.tokenAddress1);
|
414
450
|
const decimals = this.token.decimals;
|
415
451
|
const decimals0 = this.token.decimals0;
|
416
452
|
const decimals1 = this.token.decimals1;
|
@@ -845,7 +881,7 @@ const filterMirrorTokens = (balance, i, balances) => {
|
|
845
881
|
|
846
882
|
// TODO: Move this into a common module which can then be imported both here and into EvmErc20Module
|
847
883
|
// We can't import this directly from EvmErc20Module because then we'd have a circular dependency
|
848
|
-
const evmErc20TokenId
|
884
|
+
const evmErc20TokenId = (chainId, tokenContractAddress) => `${chainId}-evm-erc20-${tokenContractAddress}`.toLowerCase();
|
849
885
|
|
850
886
|
/**
|
851
887
|
* `BalanceTypes` is an automatically determined sub-selection of `PluginBalanceTypes`.
|
@@ -867,8 +903,21 @@ const evmErc20TokenId$1 = (chainId, tokenContractAddress) => `${chainId}-evm-erc
|
|
867
903
|
|
868
904
|
/** A collection of `BalanceJson` objects */
|
869
905
|
|
906
|
+
// type IBalanceBaseEvm = {
|
907
|
+
// /** WIP, use `chainId` or `evmNetworkId` for now */
|
908
|
+
// multiChainId: EvmChainId
|
909
|
+
|
910
|
+
// }
|
911
|
+
|
912
|
+
// type IBalanceBaseSubstrate = {
|
913
|
+
// multiChainId: SubChainId
|
914
|
+
|
915
|
+
// }
|
916
|
+
|
870
917
|
/** `IBalance` is a common interface which all balance types must implement. */
|
871
918
|
|
919
|
+
// & (IBalanceBaseEvm | IBalanceBaseSubstrate)
|
920
|
+
|
872
921
|
/** An unlabelled amount of a balance */
|
873
922
|
|
874
923
|
/** A labelled amount of a balance */
|
@@ -901,10 +950,9 @@ const getValueId = amount => {
|
|
901
950
|
const deriveMiniMetadataId = ({
|
902
951
|
source,
|
903
952
|
chainId,
|
904
|
-
specName,
|
905
953
|
specVersion,
|
906
|
-
|
907
|
-
}) => u8aToHex(xxhashAsU8a(new TextEncoder().encode(`${source}${chainId}${
|
954
|
+
libVersion
|
955
|
+
}) => u8aToHex(xxhashAsU8a(new TextEncoder().encode(`${source}${chainId}${specVersion}${libVersion}`), 64), undefined, false);
|
908
956
|
|
909
957
|
// for DB version 3, Wallet version 1.21.0
|
910
958
|
const upgradeRemoveSymbolFromNativeTokenId = async tx => {
|
@@ -1050,8 +1098,7 @@ class MiniMetadataUpdater {
|
|
1050
1098
|
const wantedIdsByChain = new Map(chains.flatMap(({
|
1051
1099
|
id: chainId,
|
1052
1100
|
specName,
|
1053
|
-
specVersion
|
1054
|
-
balancesConfig
|
1101
|
+
specVersion
|
1055
1102
|
}) => {
|
1056
1103
|
if (specName === null) return [];
|
1057
1104
|
if (specVersion === null) return [];
|
@@ -1059,12 +1106,9 @@ class MiniMetadataUpdater {
|
|
1059
1106
|
type: source
|
1060
1107
|
}) => deriveMiniMetadataId({
|
1061
1108
|
source,
|
1062
|
-
chainId
|
1063
|
-
|
1064
|
-
|
1065
|
-
balancesConfig: JSON.stringify((balancesConfig ?? []).find(({
|
1066
|
-
moduleType
|
1067
|
-
}) => moduleType === source)?.moduleConfig ?? {})
|
1109
|
+
chainId,
|
1110
|
+
specVersion,
|
1111
|
+
libVersion
|
1068
1112
|
}))]];
|
1069
1113
|
}));
|
1070
1114
|
const statusesByChain = new Map(Array.from(wantedIdsByChain.entries()).map(([chainId, wantedIds]) => [chainId, wantedIds.every(wantedId => ids.includes(wantedId)) ? "good" : "none"]));
|
@@ -1074,17 +1118,18 @@ class MiniMetadataUpdater {
|
|
1074
1118
|
};
|
1075
1119
|
}
|
1076
1120
|
async hydrateFromChaindata() {
|
1121
|
+
// TODO review this. feels unnecessary to fetch them all
|
1122
|
+
|
1077
1123
|
const now = Date.now();
|
1078
1124
|
if (now - this.#lastHydratedMiniMetadatasAt < minimumHydrationInterval) return false;
|
1079
1125
|
const dbHasMiniMetadatas = (await db.miniMetadatas.count()) > 0;
|
1080
1126
|
try {
|
1081
1127
|
try {
|
1082
|
-
|
1083
|
-
// so that we don't have a circular import between `@talismn/balances` and `@talismn/chaindata-provider`.
|
1084
|
-
var miniMetadatas = await fetchMiniMetadatas(); // eslint-disable-line no-var
|
1128
|
+
var miniMetadatas = await this.#chaindataProvider.miniMetadatas(); // eslint-disable-line no-var
|
1085
1129
|
if (miniMetadatas.length <= 0) throw new Error("Ignoring empty chaindata miniMetadatas response");
|
1086
1130
|
} catch (error) {
|
1087
1131
|
if (dbHasMiniMetadatas) throw error;
|
1132
|
+
log.warn("Failed to fetch miniMetadatas from chaindata", error);
|
1088
1133
|
// On first start-up (db is empty), if we fail to fetch miniMetadatas then we should
|
1089
1134
|
// initialize the DB with the list of miniMetadatas inside our init/mini-metadatas.json file.
|
1090
1135
|
// This data will represent a relatively recent copy of what's in chaindata,
|
@@ -1100,127 +1145,156 @@ class MiniMetadataUpdater {
|
|
1100
1145
|
}
|
1101
1146
|
}
|
1102
1147
|
async hydrateCustomChains() {
|
1103
|
-
|
1104
|
-
|
1105
|
-
|
1106
|
-
const
|
1107
|
-
const
|
1108
|
-
|
1109
|
-
|
1110
|
-
|
1111
|
-
|
1112
|
-
|
1113
|
-
|
1114
|
-
|
1115
|
-
|
1116
|
-
|
1117
|
-
|
1118
|
-
|
1119
|
-
|
1120
|
-
|
1121
|
-
|
1122
|
-
|
1123
|
-
|
1124
|
-
|
1125
|
-
|
1126
|
-
|
1127
|
-
|
1128
|
-
|
1129
|
-
|
1130
|
-
|
1131
|
-
|
1132
|
-
|
1133
|
-
|
1134
|
-
|
1135
|
-
|
1136
|
-
|
1137
|
-
|
1138
|
-
|
1148
|
+
// TODO
|
1149
|
+
// const now = Date.now()
|
1150
|
+
// if (now - this.#lastHydratedCustomChainsAt < minimumHydrationInterval) return false
|
1151
|
+
// const chains = await this.#chaindataProvider.chains()
|
1152
|
+
// const customChains = chains.filter(
|
1153
|
+
// (chain): chain is CustomChain => "isCustom" in chain && chain.isCustom,
|
1154
|
+
// )
|
1155
|
+
// const updatedCustomChains: Array<CustomChain> = []
|
1156
|
+
// const concurrency = 4
|
1157
|
+
// ;(
|
1158
|
+
// await PromisePool.withConcurrency(concurrency)
|
1159
|
+
// .for(customChains)
|
1160
|
+
// .process(async (customChain) => {
|
1161
|
+
// const send = (method: string, params: unknown[]) =>
|
1162
|
+
// this.#chainConnectors.substrate?.send(customChain.id, method, params)
|
1163
|
+
// const [genesisHash, runtimeVersion, chainName, chainType] = await Promise.all([
|
1164
|
+
// send("chain_getBlockHash", [0]),
|
1165
|
+
// send("state_getRuntimeVersion", []),
|
1166
|
+
// send("system_chain", []),
|
1167
|
+
// send("system_chainType", []),
|
1168
|
+
// ])
|
1169
|
+
// // deconstruct rpc data
|
1170
|
+
// const { specName, implName } = runtimeVersion
|
1171
|
+
// const specVersion = String(runtimeVersion.specVersion)
|
1172
|
+
// const changed =
|
1173
|
+
// customChain.genesisHash !== genesisHash ||
|
1174
|
+
// customChain.chainName !== chainName ||
|
1175
|
+
// !isEqual(customChain.chainType, chainType) ||
|
1176
|
+
// customChain.implName !== implName ||
|
1177
|
+
// customChain.specName !== specName ||
|
1178
|
+
// customChain.specVersion !== specVersion
|
1179
|
+
// if (!changed) return
|
1180
|
+
// customChain.genesisHash = genesisHash
|
1181
|
+
// customChain.chainName = chainName
|
1182
|
+
// customChain.chainType = chainType
|
1183
|
+
// customChain.implName = implName
|
1184
|
+
// customChain.specName = specName
|
1185
|
+
// customChain.specVersion = specVersion
|
1186
|
+
// updatedCustomChains.push(customChain)
|
1187
|
+
// })
|
1188
|
+
// ).errors.forEach((error) => log.error("Error hydrating custom chains", error))
|
1189
|
+
// if (updatedCustomChains.length > 0) {
|
1190
|
+
// await this.#chaindataProvider.transaction("rw", ["chains"], async () => {
|
1191
|
+
// for (const updatedCustomChain of updatedCustomChains) {
|
1192
|
+
// await this.#chaindataProvider.removeCustomChain(updatedCustomChain.id)
|
1193
|
+
// await this.#chaindataProvider.addCustomChain(updatedCustomChain)
|
1194
|
+
// }
|
1195
|
+
// })
|
1196
|
+
// }
|
1197
|
+
// if (updatedCustomChains.length > 0) this.#lastHydratedCustomChainsAt = now
|
1198
|
+
// return true
|
1139
1199
|
}
|
1140
|
-
async updateSubstrateChains(
|
1141
|
-
const chains = new Map(
|
1142
|
-
|
1143
|
-
|
1144
|
-
const
|
1145
|
-
|
1146
|
-
|
1147
|
-
|
1148
|
-
|
1149
|
-
//
|
1150
|
-
|
1151
|
-
const
|
1152
|
-
|
1153
|
-
|
1154
|
-
|
1155
|
-
|
1156
|
-
}
|
1157
|
-
const needUpdates = Array.from(statusesByChain.entries())
|
1158
|
-
|
1159
|
-
|
1160
|
-
|
1161
|
-
|
1162
|
-
|
1163
|
-
|
1164
|
-
|
1165
|
-
|
1166
|
-
|
1167
|
-
|
1168
|
-
|
1169
|
-
|
1170
|
-
|
1171
|
-
|
1172
|
-
|
1173
|
-
|
1174
|
-
|
1175
|
-
|
1176
|
-
|
1177
|
-
|
1178
|
-
|
1179
|
-
|
1180
|
-
|
1181
|
-
|
1182
|
-
|
1183
|
-
|
1184
|
-
|
1185
|
-
|
1186
|
-
|
1187
|
-
|
1188
|
-
|
1189
|
-
|
1190
|
-
|
1191
|
-
|
1192
|
-
|
1193
|
-
|
1194
|
-
|
1195
|
-
|
1196
|
-
|
1197
|
-
|
1198
|
-
|
1199
|
-
|
1200
|
-
|
1201
|
-
|
1202
|
-
|
1203
|
-
|
1204
|
-
|
1205
|
-
|
1206
|
-
|
1207
|
-
|
1208
|
-
|
1209
|
-
|
1210
|
-
|
1211
|
-
|
1212
|
-
|
1213
|
-
|
1214
|
-
|
1215
|
-
|
1216
|
-
|
1217
|
-
|
1218
|
-
|
1219
|
-
|
1220
|
-
|
1221
|
-
|
1222
|
-
|
1223
|
-
|
1200
|
+
async updateSubstrateChains(_chainIds) {
|
1201
|
+
// const chains = new Map(
|
1202
|
+
// (await this.#chaindataProvider.chains()).map((chain) => [chain.id, chain]),
|
1203
|
+
// )
|
1204
|
+
// const filteredChains = chainIds.flatMap((chainId) => chains.get(chainId) ?? [])
|
1205
|
+
// const ids = await balancesDb.miniMetadatas.orderBy("id").primaryKeys()
|
1206
|
+
// const { wantedIdsByChain, statusesByChain } = await this.statuses(filteredChains)
|
1207
|
+
// // clean up store
|
1208
|
+
// const wantedIds = Array.from(wantedIdsByChain.values()).flatMap((ids) => ids)
|
1209
|
+
// const unwantedIds = ids.filter((id) => !wantedIds.includes(id))
|
1210
|
+
// if (unwantedIds.length > 0) {
|
1211
|
+
// const chainIds = Array.from(
|
1212
|
+
// new Set((await balancesDb.miniMetadatas.bulkGet(unwantedIds)).map((m) => m?.chainId)),
|
1213
|
+
// )
|
1214
|
+
// log.info(`Pruning ${unwantedIds.length} miniMetadatas on chains ${chainIds.join(", ")}`)
|
1215
|
+
// await balancesDb.miniMetadatas.bulkDelete(unwantedIds)
|
1216
|
+
// }
|
1217
|
+
// const needUpdates = Array.from(statusesByChain.entries())
|
1218
|
+
// .filter(([, status]) => status !== "good")
|
1219
|
+
// .map(([chainId]) => chainId)
|
1220
|
+
// if (needUpdates.length > 0)
|
1221
|
+
// log.info(`${needUpdates.length} miniMetadatas need updates (${needUpdates.join(", ")})`)
|
1222
|
+
// const availableTokenLogos = await availableTokenLogoFilenames().catch((error) => {
|
1223
|
+
// log.error("Failed to fetch available token logos", error)
|
1224
|
+
// return []
|
1225
|
+
// })
|
1226
|
+
// const concurrency = 12
|
1227
|
+
// ;(
|
1228
|
+
// await PromisePool.withConcurrency(concurrency)
|
1229
|
+
// .for(needUpdates)
|
1230
|
+
// .process(async (chainId) => {
|
1231
|
+
// log.info(`Updating metadata for chain ${chainId}`)
|
1232
|
+
// const chain = chains.get(chainId)
|
1233
|
+
// if (!chain) return
|
1234
|
+
// const { specName, specVersion } = chain
|
1235
|
+
// if (specName === null) return
|
1236
|
+
// if (specVersion === null) return
|
1237
|
+
// const fetchMetadata = async () => {
|
1238
|
+
// try {
|
1239
|
+
// return await fetchBestMetadata(
|
1240
|
+
// (method, params, isCacheable) => {
|
1241
|
+
// if (!this.#chainConnectors.substrate)
|
1242
|
+
// throw new Error("Substrate connector is not available")
|
1243
|
+
// return this.#chainConnectors.substrate.send(chainId, method, params, isCacheable)
|
1244
|
+
// },
|
1245
|
+
// true, // allow v14 fallback
|
1246
|
+
// )
|
1247
|
+
// } catch (err) {
|
1248
|
+
// log.warn(`Failed to fetch metadata for chain ${chainId}`)
|
1249
|
+
// return undefined
|
1250
|
+
// }
|
1251
|
+
// }
|
1252
|
+
// const [metadataRpc, systemProperties] = await Promise.all([
|
1253
|
+
// fetchMetadata(),
|
1254
|
+
// this.#chainConnectors.substrate?.send(chainId, "system_properties", []),
|
1255
|
+
// ])
|
1256
|
+
// for (const mod of this.#balanceModules.filter((m) => m.type.startsWith("substrate-"))) {
|
1257
|
+
// const balancesConfig = (chain.balancesConfig ?? []).find(
|
1258
|
+
// ({ moduleType }) => moduleType === mod.type,
|
1259
|
+
// )
|
1260
|
+
// const moduleConfig = balancesConfig?.moduleConfig ?? {}
|
1261
|
+
// const chainMeta = await mod.fetchSubstrateChainMeta(
|
1262
|
+
// chainId,
|
1263
|
+
// moduleConfig,
|
1264
|
+
// metadataRpc,
|
1265
|
+
// systemProperties,
|
1266
|
+
// )
|
1267
|
+
// const tokens = await mod.fetchSubstrateChainTokens(chainId, chainMeta, moduleConfig)
|
1268
|
+
// // update tokens in chaindata
|
1269
|
+
// await this.#chaindataProvider.updateChainTokens(
|
1270
|
+
// chainId,
|
1271
|
+
// mod.type,
|
1272
|
+
// Object.values(tokens),
|
1273
|
+
// availableTokenLogos,
|
1274
|
+
// )
|
1275
|
+
// // update miniMetadatas
|
1276
|
+
// const { miniMetadata: data, metadataVersion: version, ...extra } = chainMeta ?? {}
|
1277
|
+
// await balancesDb.miniMetadatas.put({
|
1278
|
+
// id: deriveMiniMetadataId({
|
1279
|
+
// source: mod.type,
|
1280
|
+
// chainId,
|
1281
|
+
// specName,
|
1282
|
+
// specVersion,
|
1283
|
+
// balancesConfig: JSON.stringify(moduleConfig),
|
1284
|
+
// }),
|
1285
|
+
// source: mod.type,
|
1286
|
+
// chainId,
|
1287
|
+
// specName,
|
1288
|
+
// specVersion,
|
1289
|
+
// balancesConfig: JSON.stringify(moduleConfig),
|
1290
|
+
// // TODO: Standardise return value from `fetchSubstrateChainMeta`
|
1291
|
+
// version,
|
1292
|
+
// data,
|
1293
|
+
// extra: JSON.stringify(extra),
|
1294
|
+
// })
|
1295
|
+
// }
|
1296
|
+
// })
|
1297
|
+
// ).errors.forEach((error) => log.error("Error updating chain metadata", error))
|
1224
1298
|
}
|
1225
1299
|
}
|
1226
1300
|
|
@@ -1455,7 +1529,6 @@ const erc20Abi = [{
|
|
1455
1529
|
const erc20BalancesAggregatorAbi = parseAbi(["struct AccountToken {address account; address token;}", "function balances(AccountToken[] memory accountTokens) public view returns (uint256[] memory)"]);
|
1456
1530
|
|
1457
1531
|
const moduleType$7 = "evm-erc20";
|
1458
|
-
const evmErc20TokenId = (chainId, tokenContractAddress) => `${chainId}-evm-erc20-${tokenContractAddress}`.toLowerCase();
|
1459
1532
|
const EvmErc20Module = hydrate => {
|
1460
1533
|
const {
|
1461
1534
|
chainConnectors,
|
@@ -1483,7 +1556,7 @@ const EvmErc20Module = hydrate => {
|
|
1483
1556
|
};
|
1484
1557
|
const getErc20Aggregators = async () => {
|
1485
1558
|
const evmNetworks = await chaindataProvider.evmNetworks();
|
1486
|
-
return Object.fromEntries(evmNetworks.filter(n => n.
|
1559
|
+
return Object.fromEntries(evmNetworks.filter(n => n.contracts?.Erc20Aggregator).map(n => [n.id, n.contracts.Erc20Aggregator]));
|
1487
1560
|
};
|
1488
1561
|
return {
|
1489
1562
|
...DefaultBalanceModule(moduleType$7),
|
@@ -1491,20 +1564,19 @@ const EvmErc20Module = hydrate => {
|
|
1491
1564
|
* This method is currently executed on [a squid](https://github.com/TalismanSociety/chaindata-squid/blob/0ee02818bf5caa7362e3f3664e55ef05ec8df078/src/steps/updateEvmNetworksFromGithub.ts#L280-L284).
|
1492
1565
|
* In a future version of the balance libraries, we may build some kind of async scheduling system which will keep the chainmeta for each chain up to date without relying on a squid.
|
1493
1566
|
*/
|
1494
|
-
async fetchEvmChainMeta(
|
1495
|
-
|
1496
|
-
|
1497
|
-
|
1498
|
-
}
|
1567
|
+
async fetchEvmChainMeta(_chainId) {
|
1568
|
+
return undefined;
|
1569
|
+
// const isTestnet = (await chaindataProvider.evmNetworkById(chainId))?.isTestnet || false
|
1570
|
+
|
1571
|
+
// return { isTestnet }
|
1499
1572
|
},
|
1500
1573
|
/**
|
1501
1574
|
* This method is currently executed on [a squid](https://github.com/TalismanSociety/chaindata-squid/blob/0ee02818bf5caa7362e3f3664e55ef05ec8df078/src/steps/updateEvmNetworksFromGithub.ts#L338-L343).
|
1502
1575
|
* In a future version of the balance libraries, we may build some kind of async scheduling system which will keep the list of tokens for each chain up to date without relying on a squid.
|
1503
1576
|
*/
|
1504
|
-
async fetchEvmChainTokens(chainId,
|
1505
|
-
const {
|
1506
|
-
|
1507
|
-
} = chainMeta;
|
1577
|
+
async fetchEvmChainTokens(chainId, _chainMeta, moduleConfig) {
|
1578
|
+
//const { isTestnet } = chainMeta
|
1579
|
+
|
1508
1580
|
const chainTokens = {};
|
1509
1581
|
for (const tokenConfig of moduleConfig?.tokens ?? []) {
|
1510
1582
|
const {
|
@@ -1523,12 +1595,12 @@ const EvmErc20Module = hydrate => {
|
|
1523
1595
|
const symbol = tokenConfig?.symbol ?? contractSymbol ?? "ETH";
|
1524
1596
|
const decimals = typeof tokenConfig?.decimals === "number" ? tokenConfig.decimals : typeof contractDecimals === "number" ? contractDecimals : 18;
|
1525
1597
|
if (!symbol || typeof decimals !== "number") continue;
|
1526
|
-
const id = evmErc20TokenId(chainId, contractAddress);
|
1598
|
+
const id = evmErc20TokenId$1(chainId, contractAddress);
|
1527
1599
|
const token = {
|
1528
1600
|
id,
|
1529
1601
|
type: "evm-erc20",
|
1530
1602
|
platform: "ethereum",
|
1531
|
-
isTestnet,
|
1603
|
+
//isTestnet,
|
1532
1604
|
isDefault: tokenConfig.isDefault ?? true,
|
1533
1605
|
symbol,
|
1534
1606
|
decimals,
|
@@ -1559,7 +1631,7 @@ const EvmErc20Module = hydrate => {
|
|
1559
1631
|
const subscriptionInterval = 6_000; // 6_000ms == 6 seconds
|
1560
1632
|
const initDelay = 1_500; // 1_500ms == 1.5 seconds
|
1561
1633
|
const initialisingBalances = new Set();
|
1562
|
-
const positiveBalanceNetworks = new Set(initialBalances?.map(b => b.
|
1634
|
+
const positiveBalanceNetworks = new Set(initialBalances?.map(b => b.networkId));
|
1563
1635
|
const tokens = await getModuleTokens();
|
1564
1636
|
|
1565
1637
|
// for chains with a zero balance we only call fetchBalances once every 5 subscriptionIntervals
|
@@ -1696,20 +1768,18 @@ const fetchBalances$3 = async (evmChainConnector, tokenAddressesByNetwork, erc20
|
|
1696
1768
|
results: [],
|
1697
1769
|
errors: []
|
1698
1770
|
};
|
1699
|
-
await Promise.all(Object.entries(tokenAddressesByNetwork).map(async ([
|
1700
|
-
const publicClient = await evmChainConnector.getPublicClientForEvmNetwork(
|
1701
|
-
if (!publicClient) throw new EvmErc20NetworkError(`Could not get rpc provider for evm network ${
|
1702
|
-
const balances = await getEvmTokenBalances(publicClient, networkParams, result.errors, erc20Aggregators[
|
1771
|
+
await Promise.all(Object.entries(tokenAddressesByNetwork).map(async ([networkId, networkParams]) => {
|
1772
|
+
const publicClient = await evmChainConnector.getPublicClientForEvmNetwork(networkId);
|
1773
|
+
if (!publicClient) throw new EvmErc20NetworkError(`Could not get rpc provider for evm network ${networkId}`, networkId);
|
1774
|
+
const balances = await getEvmTokenBalances(publicClient, networkParams, result.errors, erc20Aggregators[networkId]);
|
1703
1775
|
|
1704
1776
|
// consider only non null balances in the results
|
1705
1777
|
result.results.push(...balances.filter(isTruthy).map((free, i) => ({
|
1706
1778
|
source: "evm-erc20",
|
1707
1779
|
status: "live",
|
1708
1780
|
address: networkParams[i].address,
|
1709
|
-
multiChainId: {
|
1710
|
-
|
1711
|
-
},
|
1712
|
-
evmNetworkId,
|
1781
|
+
// multiChainId: { evmChainId: evmNetworkId },
|
1782
|
+
networkId,
|
1713
1783
|
tokenId: networkParams[i].token.id,
|
1714
1784
|
value: free
|
1715
1785
|
})));
|
@@ -1794,9 +1864,12 @@ function groupAddressesByTokenByEvmNetwork$1(addressesByToken, tokens) {
|
|
1794
1864
|
const abiMulticall = parseAbi(["struct Call { address target; bytes callData; }", "struct Call3 { address target; bool allowFailure; bytes callData; }", "struct Call3Value { address target; bool allowFailure; uint256 value; bytes callData; }", "struct Result { bool success; bytes returnData; }", "function aggregate(Call[] calldata calls) public payable returns (uint256 blockNumber, bytes[] memory returnData)", "function aggregate3(Call3[] calldata calls) public payable returns (Result[] memory returnData)", "function aggregate3Value(Call3Value[] calldata calls) public payable returns (Result[] memory returnData)", "function blockAndAggregate(Call[] calldata calls) public payable returns (uint256 blockNumber, bytes32 blockHash, Result[] memory returnData)", "function getBasefee() view returns (uint256 basefee)", "function getBlockHash(uint256 blockNumber) view returns (bytes32 blockHash)", "function getBlockNumber() view returns (uint256 blockNumber)", "function getChainId() view returns (uint256 chainid)", "function getCurrentBlockCoinbase() view returns (address coinbase)", "function getCurrentBlockDifficulty() view returns (uint256 difficulty)", "function getCurrentBlockGasLimit() view returns (uint256 gaslimit)", "function getCurrentBlockTimestamp() view returns (uint256 timestamp)", "function getEthBalance(address addr) view returns (uint256 balance)", "function getLastBlockHash() view returns (bytes32 blockHash)", "function tryAggregate(bool requireSuccess, Call[] calldata calls) public payable returns (Result[] memory returnData)", "function tryBlockAndAggregate(bool requireSuccess, Call[] calldata calls) public payable returns (uint256 blockNumber, bytes32 blockHash, Result[] memory returnData)"]);
|
1795
1865
|
|
1796
1866
|
const moduleType$6 = "evm-native";
|
1797
|
-
|
1867
|
+
|
1868
|
+
// export const evmNativeTokenId = (chainId: EvmNetworkId) =>
|
1869
|
+
// `${chainId}-evm-native`.toLowerCase().replace(/ /g, "-")
|
1870
|
+
|
1798
1871
|
const getEvmNetworkIdFromTokenId = tokenId => {
|
1799
|
-
const evmNetworkId = tokenId.split("
|
1872
|
+
const evmNetworkId = tokenId.split(":")[0];
|
1800
1873
|
if (!evmNetworkId) throw new Error(`Can't detect chainId for token ${tokenId}`);
|
1801
1874
|
return evmNetworkId;
|
1802
1875
|
};
|
@@ -1817,35 +1890,31 @@ const EvmNativeModule = hydrate => {
|
|
1817
1890
|
* This method is currently executed on [a squid](https://github.com/TalismanSociety/chaindata-squid/blob/0ee02818bf5caa7362e3f3664e55ef05ec8df078/src/steps/updateEvmNetworksFromGithub.ts#L280-L284).
|
1818
1891
|
* In a future version of the balance libraries, we may build some kind of async scheduling system which will keep the chainmeta for each chain up to date without relying on a squid.
|
1819
1892
|
*/
|
1820
|
-
async fetchEvmChainMeta(
|
1821
|
-
const isTestnet = (await chaindataProvider.evmNetworkById(chainId))?.isTestnet || false
|
1822
|
-
|
1823
|
-
|
1824
|
-
|
1893
|
+
async fetchEvmChainMeta(_chainId) {
|
1894
|
+
// const isTestnet = (await chaindataProvider.evmNetworkById(chainId))?.isTestnet || false
|
1895
|
+
|
1896
|
+
// return { isTestnet }
|
1897
|
+
return undefined;
|
1825
1898
|
},
|
1826
1899
|
/**
|
1827
1900
|
* This method is currently executed on [a squid](https://github.com/TalismanSociety/chaindata-squid/blob/0ee02818bf5caa7362e3f3664e55ef05ec8df078/src/steps/updateEvmNetworksFromGithub.ts#L338-L343).
|
1828
1901
|
* In a future version of the balance libraries, we may build some kind of async scheduling system which will keep the list of tokens for each chain up to date without relying on a squid.
|
1829
1902
|
*/
|
1830
|
-
async fetchEvmChainTokens(
|
1831
|
-
const {
|
1832
|
-
isTestnet
|
1833
|
-
} = chainMeta;
|
1903
|
+
async fetchEvmChainTokens(networkId, chainMeta, moduleConfig) {
|
1834
1904
|
const symbol = moduleConfig?.symbol ?? "ETH";
|
1835
1905
|
const decimals = typeof moduleConfig?.decimals === "number" ? moduleConfig.decimals : 18;
|
1836
1906
|
const name = moduleConfig?.name ?? symbol;
|
1837
|
-
const id = evmNativeTokenId(
|
1907
|
+
const id = evmNativeTokenId(networkId);
|
1838
1908
|
const nativeToken = {
|
1839
1909
|
platform: "ethereum",
|
1840
1910
|
id,
|
1841
1911
|
type: "evm-native",
|
1842
|
-
isTestnet,
|
1843
1912
|
isDefault: true,
|
1844
1913
|
symbol,
|
1845
1914
|
decimals,
|
1846
1915
|
name,
|
1847
1916
|
logo: moduleConfig?.logo || githubTokenLogoUrl(id),
|
1848
|
-
networkId
|
1917
|
+
networkId
|
1849
1918
|
};
|
1850
1919
|
if (moduleConfig?.symbol) nativeToken.symbol = moduleConfig?.symbol;
|
1851
1920
|
if (moduleConfig?.coingeckoId) nativeToken.coingeckoId = moduleConfig?.coingeckoId;
|
@@ -1880,7 +1949,7 @@ const EvmNativeModule = hydrate => {
|
|
1880
1949
|
// setup initialising balances for all active evm networks
|
1881
1950
|
const activeEvmNetworkIds = Object.keys(ethAddressesByToken).map(getEvmNetworkIdFromTokenId);
|
1882
1951
|
const initialisingBalances = new Set(activeEvmNetworkIds);
|
1883
|
-
const positiveBalanceNetworks = new Set(initialBalances?.map(b => b.
|
1952
|
+
const positiveBalanceNetworks = new Set(initialBalances?.map(b => b.networkId));
|
1884
1953
|
const poll = async () => {
|
1885
1954
|
if (!subscriptionActive) return;
|
1886
1955
|
zeroBalanceSubscriptionIntervalCounter = (zeroBalanceSubscriptionIntervalCounter + 1) % 5;
|
@@ -1907,10 +1976,10 @@ const EvmNativeModule = hydrate => {
|
|
1907
1976
|
log.error(balance.message, balance.networkId);
|
1908
1977
|
initialisingBalances.delete(balance.networkId);
|
1909
1978
|
} else {
|
1910
|
-
if (balance.
|
1911
|
-
initialisingBalances.delete(balance.
|
1979
|
+
if (balance.networkId) {
|
1980
|
+
initialisingBalances.delete(balance.networkId);
|
1912
1981
|
if (BigInt(balance.value) > 0n) {
|
1913
|
-
positiveBalanceNetworks.add(balance.
|
1982
|
+
positiveBalanceNetworks.add(balance.networkId);
|
1914
1983
|
}
|
1915
1984
|
resultBalances.push(balance);
|
1916
1985
|
}
|
@@ -1960,23 +2029,23 @@ const fetchBalances$2 = async (evmChainConnector, addressesByToken, tokens) => {
|
|
1960
2029
|
if (!evmChainConnector) throw new Error(`This module requires an evm chain connector`);
|
1961
2030
|
return Promise.all(Object.entries(addressesByToken).map(async ([tokenId, addresses]) => {
|
1962
2031
|
const token = tokens[tokenId];
|
1963
|
-
const
|
1964
|
-
if (!
|
1965
|
-
const publicClient = await evmChainConnector.getPublicClientForEvmNetwork(
|
1966
|
-
if (!publicClient) throw new Error(`Could not get rpc provider for evm network ${
|
2032
|
+
const networkId = token.networkId;
|
2033
|
+
if (!networkId) throw new Error(`Token ${token.id} has no evm network`);
|
2034
|
+
const publicClient = await evmChainConnector.getPublicClientForEvmNetwork(networkId);
|
2035
|
+
if (!publicClient) throw new Error(`Could not get rpc provider for evm network ${networkId}`);
|
1967
2036
|
|
1968
2037
|
// fetch all balances
|
1969
2038
|
const freeBalances = await getFreeBalances(publicClient, addresses);
|
1970
2039
|
const balanceResults = addresses.map((address, i) => {
|
1971
|
-
if (freeBalances[i] === "error") return new EvmNativeBalanceError("Could not fetch balance ",
|
2040
|
+
if (freeBalances[i] === "error") return new EvmNativeBalanceError("Could not fetch balance ", networkId);
|
1972
2041
|
return {
|
1973
2042
|
source: "evm-native",
|
1974
2043
|
status: "live",
|
1975
2044
|
address: address,
|
1976
2045
|
multiChainId: {
|
1977
|
-
evmChainId:
|
2046
|
+
evmChainId: networkId
|
1978
2047
|
},
|
1979
|
-
|
2048
|
+
networkId,
|
1980
2049
|
tokenId,
|
1981
2050
|
value: freeBalances[i].toString()
|
1982
2051
|
};
|
@@ -2598,7 +2667,6 @@ const uniswapV2PairAbi = [{
|
|
2598
2667
|
}];
|
2599
2668
|
|
2600
2669
|
const moduleType$5 = "evm-uniswapv2";
|
2601
|
-
const evmUniswapV2TokenId = (chainId, contractAddress) => `${chainId}-evm-uniswapv2-${contractAddress}`.toLowerCase();
|
2602
2670
|
const EvmUniswapV2Module = hydrate => {
|
2603
2671
|
const {
|
2604
2672
|
chainConnectors,
|
@@ -2608,16 +2676,15 @@ const EvmUniswapV2Module = hydrate => {
|
|
2608
2676
|
assert(chainConnector, "This module requires an evm chain connector");
|
2609
2677
|
return {
|
2610
2678
|
...DefaultBalanceModule(moduleType$5),
|
2611
|
-
async fetchEvmChainMeta(
|
2612
|
-
const isTestnet = (await chaindataProvider.evmNetworkById(chainId))?.isTestnet || false
|
2613
|
-
|
2614
|
-
|
2615
|
-
|
2679
|
+
async fetchEvmChainMeta(_chainId) {
|
2680
|
+
// const isTestnet = (await chaindataProvider.evmNetworkById(chainId))?.isTestnet || false
|
2681
|
+
|
2682
|
+
// return { isTestnet }
|
2683
|
+
return undefined;
|
2616
2684
|
},
|
2617
|
-
async fetchEvmChainTokens(chainId,
|
2618
|
-
const {
|
2619
|
-
|
2620
|
-
} = chainMeta;
|
2685
|
+
async fetchEvmChainTokens(chainId, _chainMeta, moduleConfig) {
|
2686
|
+
//const { isTestnet } = chainMeta
|
2687
|
+
|
2621
2688
|
const tokens = {};
|
2622
2689
|
for (const tokenConfig of moduleConfig?.pools ?? []) {
|
2623
2690
|
const {
|
@@ -2642,7 +2709,7 @@ const EvmUniswapV2Module = hydrate => {
|
|
2642
2709
|
id,
|
2643
2710
|
type: "evm-uniswapv2",
|
2644
2711
|
platform: "ethereum",
|
2645
|
-
isTestnet,
|
2712
|
+
// isTestnet,
|
2646
2713
|
isDefault: tokenConfig.isDefault ?? false,
|
2647
2714
|
symbol: `${symbol0 ?? "UNKNOWN"}/${symbol1 ?? "UNKNOWN"}`,
|
2648
2715
|
name: name ?? `${symbol0 ?? "UNKNOWN"}/${symbol1 ?? "UNKNOWN"}`,
|
@@ -2676,9 +2743,9 @@ const EvmUniswapV2Module = hydrate => {
|
|
2676
2743
|
const initDelay = 1_500; // 1_500ms == 1.5 seconds
|
2677
2744
|
|
2678
2745
|
const initialBalancesByNetwork = initialBalances?.reduce((result, b) => {
|
2679
|
-
if (!b.
|
2680
|
-
if (!result[b.
|
2681
|
-
result[b.
|
2746
|
+
if (!b.networkId) return result;
|
2747
|
+
if (!result[b.networkId]) result[b.networkId] = {};
|
2748
|
+
result[b.networkId][getBalanceId(b)] = b;
|
2682
2749
|
return result;
|
2683
2750
|
}, {});
|
2684
2751
|
const cache = new Map(Object.entries(initialBalancesByNetwork ?? {}));
|
@@ -2738,12 +2805,12 @@ const EvmUniswapV2Module = hydrate => {
|
|
2738
2805
|
};
|
2739
2806
|
const fetchBalances$1 = async (evmChainConnector, evmNetworks, tokens, addressesByToken) => {
|
2740
2807
|
const addressesByTokenGroupedByEvmNetwork = groupAddressesByTokenByEvmNetwork(addressesByToken, tokens);
|
2741
|
-
const balances = (await Promise.allSettled(Object.entries(addressesByTokenGroupedByEvmNetwork).map(async ([
|
2808
|
+
const balances = (await Promise.allSettled(Object.entries(addressesByTokenGroupedByEvmNetwork).map(async ([networkId, addressesByToken]) => {
|
2742
2809
|
if (!evmChainConnector) throw new Error(`This module requires an evm chain connector`);
|
2743
|
-
const evmNetwork = evmNetworks[
|
2744
|
-
if (!evmNetwork) throw new Error(`Evm network ${
|
2745
|
-
const publicClient = await evmChainConnector.getPublicClientForEvmNetwork(
|
2746
|
-
if (!publicClient) throw new Error(`Could not get rpc provider for evm network ${
|
2810
|
+
const evmNetwork = evmNetworks[networkId];
|
2811
|
+
if (!evmNetwork) throw new Error(`Evm network ${networkId} not found`);
|
2812
|
+
const publicClient = await evmChainConnector.getPublicClientForEvmNetwork(networkId);
|
2813
|
+
if (!publicClient) throw new Error(`Could not get rpc provider for evm network ${networkId}`);
|
2747
2814
|
const tokensAndAddresses = Object.entries(addressesByToken).reduce((tokensAndAddresses, [tokenId, addresses]) => {
|
2748
2815
|
const token = tokens[tokenId];
|
2749
2816
|
if (!token) {
|
@@ -2765,10 +2832,7 @@ const fetchBalances$1 = async (evmChainConnector, evmNetworks, tokens, addresses
|
|
2765
2832
|
source: "evm-uniswapv2",
|
2766
2833
|
status: "live",
|
2767
2834
|
address: address,
|
2768
|
-
|
2769
|
-
evmChainId: evmNetwork.id
|
2770
|
-
},
|
2771
|
-
evmNetworkId,
|
2835
|
+
networkId,
|
2772
2836
|
tokenId: token.id,
|
2773
2837
|
values: await getPoolBalance(publicClient, token.contractAddress, address)
|
2774
2838
|
}));
|
@@ -2900,24 +2964,20 @@ async function balances(balanceModule, addressesByToken, callback) {
|
|
2900
2964
|
*/
|
2901
2965
|
const findChainMeta = (miniMetadatas, moduleType, chain) => {
|
2902
2966
|
if (!chain) return [undefined, undefined];
|
2903
|
-
if (!chain.specName) return [undefined, undefined];
|
2904
2967
|
if (!chain.specVersion) return [undefined, undefined];
|
2905
2968
|
|
2906
2969
|
// TODO: This is spaghetti to import this here, it should be injected into each balance module or something.
|
2907
2970
|
const metadataId = deriveMiniMetadataId({
|
2908
2971
|
source: moduleType,
|
2909
2972
|
chainId: chain.id,
|
2910
|
-
specName: chain.specName,
|
2911
2973
|
specVersion: chain.specVersion,
|
2912
|
-
|
2974
|
+
libVersion
|
2913
2975
|
});
|
2914
2976
|
|
2915
2977
|
// TODO: Fix this (needs to fetch miniMetadata without being async)
|
2916
2978
|
const miniMetadata = miniMetadatas.get(metadataId);
|
2917
2979
|
const chainMeta = miniMetadata ? {
|
2918
|
-
miniMetadata: miniMetadata.data
|
2919
|
-
metadataVersion: miniMetadata.version,
|
2920
|
-
...JSON.parse(miniMetadata.extra)
|
2980
|
+
miniMetadata: miniMetadata.data
|
2921
2981
|
} : undefined;
|
2922
2982
|
return [chainMeta, miniMetadata];
|
2923
2983
|
};
|
@@ -3145,7 +3205,6 @@ const decompress = data => {
|
|
3145
3205
|
};
|
3146
3206
|
|
3147
3207
|
const moduleType$4 = "substrate-assets";
|
3148
|
-
const subAssetTokenId = (chainId, assetId, tokenSymbol) => `${chainId}-substrate-assets-${assetId}-${tokenSymbol}`.toLowerCase().replace(/ /g, "-");
|
3149
3208
|
const SubAssetsModule = hydrate => {
|
3150
3209
|
const {
|
3151
3210
|
chainConnectors,
|
@@ -3179,12 +3238,9 @@ const SubAssetsModule = hydrate => {
|
|
3179
3238
|
async fetchSubstrateChainTokens(chainId, chainMeta, moduleConfig) {
|
3180
3239
|
if ((moduleConfig?.tokens ?? []).length < 1) return {};
|
3181
3240
|
const {
|
3182
|
-
|
3183
|
-
miniMetadata,
|
3184
|
-
metadataVersion
|
3241
|
+
miniMetadata
|
3185
3242
|
} = chainMeta;
|
3186
|
-
if (miniMetadata
|
3187
|
-
if (metadataVersion < 14) return {};
|
3243
|
+
if (!miniMetadata) return {};
|
3188
3244
|
const metadata = unifyMetadata(decAnyMetadata(miniMetadata));
|
3189
3245
|
const scaleBuilder = getDynamicBuilder(getLookupFn(metadata));
|
3190
3246
|
const assetCoder = scaleBuilder.buildStorage("Assets", "Asset");
|
@@ -3201,12 +3257,11 @@ const SubAssetsModule = hydrate => {
|
|
3201
3257
|
const symbol = assetsMetadata?.symbol?.asText?.() ?? "Unit";
|
3202
3258
|
const decimals = assetsMetadata?.decimals ?? 0;
|
3203
3259
|
const isFrozen = assetsMetadata?.is_frozen ?? false;
|
3204
|
-
const id = subAssetTokenId(chainId, assetId
|
3260
|
+
const id = subAssetTokenId(chainId, assetId);
|
3205
3261
|
const token = {
|
3206
3262
|
id,
|
3207
3263
|
type: "substrate-assets",
|
3208
3264
|
platform: "polkadot",
|
3209
|
-
isTestnet,
|
3210
3265
|
isDefault: tokenConfig?.isDefault ?? true,
|
3211
3266
|
symbol,
|
3212
3267
|
name: tokenConfig?.name || symbol,
|
@@ -3219,7 +3274,7 @@ const SubAssetsModule = hydrate => {
|
|
3219
3274
|
};
|
3220
3275
|
if (tokenConfig?.symbol) {
|
3221
3276
|
token.symbol = tokenConfig?.symbol;
|
3222
|
-
token.id = subAssetTokenId(chainId, assetId
|
3277
|
+
token.id = subAssetTokenId(chainId, assetId);
|
3223
3278
|
}
|
3224
3279
|
if (tokenConfig?.coingeckoId) token.coingeckoId = tokenConfig?.coingeckoId;
|
3225
3280
|
if (tokenConfig?.mirrorOf) token.mirrorOf = tokenConfig?.mirrorOf;
|
@@ -3340,27 +3395,27 @@ async function buildQueries$3(chaindataProvider, addressesByToken) {
|
|
3340
3395
|
log.debug(`This module doesn't handle tokens of type ${token.type}`);
|
3341
3396
|
return [];
|
3342
3397
|
}
|
3343
|
-
const
|
3344
|
-
if (!
|
3398
|
+
const networkId = token.networkId;
|
3399
|
+
if (!networkId) {
|
3345
3400
|
log.warn(`Token ${tokenId} has no chain`);
|
3346
3401
|
return [];
|
3347
3402
|
}
|
3348
|
-
const chain = chains[
|
3403
|
+
const chain = chains[networkId];
|
3349
3404
|
if (!chain) {
|
3350
|
-
log.warn(`Chain ${
|
3405
|
+
log.warn(`Chain ${networkId} for token ${tokenId} not found`);
|
3351
3406
|
return [];
|
3352
3407
|
}
|
3353
3408
|
return addresses.flatMap(address => {
|
3354
|
-
const scaleCoder = chainStorageCoders.get(
|
3409
|
+
const scaleCoder = chainStorageCoders.get(networkId)?.storage;
|
3355
3410
|
const stateKey = tryEncode(scaleCoder, BigInt(token.assetId), address) ?? tryEncode(scaleCoder, token.assetId, address);
|
3356
3411
|
if (!stateKey) {
|
3357
|
-
log.warn(`Invalid assetId / address in ${
|
3412
|
+
log.warn(`Invalid assetId / address in ${networkId} storage query ${token.assetId} / ${address}`);
|
3358
3413
|
return [];
|
3359
3414
|
}
|
3360
3415
|
const decodeResult = change => {
|
3361
3416
|
/** NOTE: This type is only a hint for typescript, the chain can actually return whatever it wants to */
|
3362
3417
|
|
3363
|
-
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-assets balance on chain ${
|
3418
|
+
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-assets balance on chain ${networkId}`) ?? {
|
3364
3419
|
balance: 0n,
|
3365
3420
|
status: {
|
3366
3421
|
type: "Liquid"
|
@@ -3394,16 +3449,13 @@ async function buildQueries$3(chaindataProvider, addressesByToken) {
|
|
3394
3449
|
source: "substrate-assets",
|
3395
3450
|
status: "live",
|
3396
3451
|
address,
|
3397
|
-
|
3398
|
-
subChainId: chainId
|
3399
|
-
},
|
3400
|
-
chainId,
|
3452
|
+
networkId,
|
3401
3453
|
tokenId: token.id,
|
3402
3454
|
values: balanceValues
|
3403
3455
|
};
|
3404
3456
|
};
|
3405
3457
|
return {
|
3406
|
-
chainId,
|
3458
|
+
chainId: networkId,
|
3407
3459
|
stateKey,
|
3408
3460
|
decodeResult
|
3409
3461
|
};
|
@@ -3423,7 +3475,6 @@ const tryEncode = (scaleCoder, ...args) => {
|
|
3423
3475
|
};
|
3424
3476
|
|
3425
3477
|
const moduleType$3 = "substrate-foreignassets";
|
3426
|
-
const subForeignAssetTokenId = (chainId, tokenSymbol) => `${chainId}-substrate-foreignassets-${tokenSymbol}`.toLowerCase().replace(/ /g, "-");
|
3427
3478
|
const SubForeignAssetsModule = hydrate => {
|
3428
3479
|
const {
|
3429
3480
|
chainConnectors,
|
@@ -3434,14 +3485,12 @@ const SubForeignAssetsModule = hydrate => {
|
|
3434
3485
|
return {
|
3435
3486
|
...DefaultBalanceModule(moduleType$3),
|
3436
3487
|
async fetchSubstrateChainMeta(chainId, moduleConfig, metadataRpc) {
|
3437
|
-
const isTestnet = (await chaindataProvider.chainById(chainId))?.isTestnet || false
|
3438
|
-
if (metadataRpc === undefined) return {
|
3439
|
-
|
3440
|
-
|
3441
|
-
if ((moduleConfig?.tokens ?? []).length < 1) return {
|
3442
|
-
isTestnet
|
3443
|
-
};
|
3488
|
+
// const isTestnet = (await chaindataProvider.chainById(chainId))?.isTestnet || false
|
3489
|
+
if (metadataRpc === undefined) return {};
|
3490
|
+
// if ((moduleConfig?.tokens ?? []).length < 1) return { isTestnet }
|
3491
|
+
|
3444
3492
|
const metadataVersion = getMetadataVersion(metadataRpc);
|
3493
|
+
if (metadataVersion < 14) return {};
|
3445
3494
|
const metadata = decAnyMetadata(metadataRpc);
|
3446
3495
|
compactMetadata(metadata, [{
|
3447
3496
|
pallet: "ForeignAssets",
|
@@ -3449,20 +3498,18 @@ const SubForeignAssetsModule = hydrate => {
|
|
3449
3498
|
}]);
|
3450
3499
|
const miniMetadata = encodeMetadata(metadata);
|
3451
3500
|
return {
|
3452
|
-
|
3453
|
-
miniMetadata,
|
3454
|
-
metadataVersion
|
3501
|
+
miniMetadata
|
3455
3502
|
};
|
3456
3503
|
},
|
3457
3504
|
async fetchSubstrateChainTokens(chainId, chainMeta, moduleConfig) {
|
3458
3505
|
if ((moduleConfig?.tokens ?? []).length < 1) return {};
|
3459
3506
|
const {
|
3460
|
-
|
3461
|
-
miniMetadata,
|
3462
|
-
metadataVersion
|
3507
|
+
miniMetadata
|
3463
3508
|
} = chainMeta;
|
3464
|
-
if (miniMetadata
|
3465
|
-
if (metadataVersion
|
3509
|
+
if (!miniMetadata) return {};
|
3510
|
+
// if (miniMetadata === undefined || metadataVersion === undefined) return {}
|
3511
|
+
// if (metadataVersion < 14) return {}
|
3512
|
+
|
3466
3513
|
const metadata = decAnyMetadata(miniMetadata);
|
3467
3514
|
const unifiedMetadata = unifyMetadata(metadata);
|
3468
3515
|
const scaleBuilder = getDynamicBuilder(getLookupFn(unifiedMetadata));
|
@@ -3486,12 +3533,12 @@ const SubForeignAssetsModule = hydrate => {
|
|
3486
3533
|
const symbol = assetsMetadata?.symbol?.asText?.() ?? "Unit";
|
3487
3534
|
const decimals = assetsMetadata?.decimals ?? 0;
|
3488
3535
|
const isFrozen = assetsMetadata?.is_frozen ?? false;
|
3489
|
-
const id = subForeignAssetTokenId(chainId,
|
3536
|
+
const id = subForeignAssetTokenId(chainId, tokenConfig.onChainId);
|
3490
3537
|
const token = {
|
3491
3538
|
id,
|
3492
3539
|
type: "substrate-foreignassets",
|
3493
3540
|
platform: "polkadot",
|
3494
|
-
isTestnet,
|
3541
|
+
// isTestnet,
|
3495
3542
|
isDefault: tokenConfig?.isDefault ?? true,
|
3496
3543
|
symbol,
|
3497
3544
|
decimals,
|
@@ -3502,10 +3549,6 @@ const SubForeignAssetsModule = hydrate => {
|
|
3502
3549
|
isFrozen,
|
3503
3550
|
networkId: chainId
|
3504
3551
|
};
|
3505
|
-
if (tokenConfig?.symbol) {
|
3506
|
-
token.symbol = tokenConfig?.symbol;
|
3507
|
-
token.id = subForeignAssetTokenId(chainId, token.symbol);
|
3508
|
-
}
|
3509
3552
|
if (tokenConfig?.coingeckoId) token.coingeckoId = tokenConfig?.coingeckoId;
|
3510
3553
|
if (tokenConfig?.mirrorOf) token.mirrorOf = tokenConfig?.mirrorOf;
|
3511
3554
|
tokens[token.id] = token;
|
@@ -3611,18 +3654,18 @@ async function buildQueries$2(chaindataProvider, addressesByToken) {
|
|
3611
3654
|
log.debug(`This module doesn't handle tokens of type ${token.type}`);
|
3612
3655
|
return [];
|
3613
3656
|
}
|
3614
|
-
const
|
3615
|
-
if (!
|
3657
|
+
const networkId = token.networkId;
|
3658
|
+
if (!networkId) {
|
3616
3659
|
log.warn(`Token ${tokenId} has no chain`);
|
3617
3660
|
return [];
|
3618
3661
|
}
|
3619
|
-
const chain = chains[
|
3662
|
+
const chain = chains[networkId];
|
3620
3663
|
if (!chain) {
|
3621
|
-
log.warn(`Chain ${
|
3664
|
+
log.warn(`Chain ${networkId} for token ${tokenId} not found`);
|
3622
3665
|
return [];
|
3623
3666
|
}
|
3624
3667
|
return addresses.flatMap(address => {
|
3625
|
-
const scaleCoder = chainStorageCoders.get(
|
3668
|
+
const scaleCoder = chainStorageCoders.get(networkId)?.storage;
|
3626
3669
|
const onChainId = (() => {
|
3627
3670
|
try {
|
3628
3671
|
return papiParse(token.onChainId);
|
@@ -3630,12 +3673,12 @@ async function buildQueries$2(chaindataProvider, addressesByToken) {
|
|
3630
3673
|
return token.onChainId;
|
3631
3674
|
}
|
3632
3675
|
})();
|
3633
|
-
const stateKey = encodeStateKey(scaleCoder, `Invalid address / token onChainId in ${
|
3676
|
+
const stateKey = encodeStateKey(scaleCoder, `Invalid address / token onChainId in ${networkId} storage query ${address} / ${token.onChainId}`, onChainId, address);
|
3634
3677
|
if (!stateKey) return [];
|
3635
3678
|
const decodeResult = change => {
|
3636
3679
|
/** NOTE: This type is only a hint for typescript, the chain can actually return whatever it wants to */
|
3637
3680
|
|
3638
|
-
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-foreignassets balance on chain ${
|
3681
|
+
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-foreignassets balance on chain ${networkId}`) ?? {
|
3639
3682
|
balance: 0n,
|
3640
3683
|
status: {
|
3641
3684
|
type: "Liquid"
|
@@ -3669,16 +3712,13 @@ async function buildQueries$2(chaindataProvider, addressesByToken) {
|
|
3669
3712
|
source: "substrate-foreignassets",
|
3670
3713
|
status: "live",
|
3671
3714
|
address,
|
3672
|
-
|
3673
|
-
subChainId: chainId
|
3674
|
-
},
|
3675
|
-
chainId,
|
3715
|
+
networkId,
|
3676
3716
|
tokenId: token.id,
|
3677
3717
|
values: balanceValues
|
3678
3718
|
};
|
3679
3719
|
};
|
3680
3720
|
return {
|
3681
|
-
chainId,
|
3721
|
+
chainId: networkId,
|
3682
3722
|
stateKey,
|
3683
3723
|
decodeResult
|
3684
3724
|
};
|
@@ -3935,10 +3975,7 @@ async function subscribeCrowdloans(chaindataProvider, chainConnector, addressesB
|
|
3935
3975
|
source: "substrate-native",
|
3936
3976
|
status: "live",
|
3937
3977
|
address,
|
3938
|
-
|
3939
|
-
subChainId: chainId
|
3940
|
-
},
|
3941
|
-
chainId,
|
3978
|
+
networkId: chainId,
|
3942
3979
|
tokenId,
|
3943
3980
|
values: Array.from(contributions).map(({
|
3944
3981
|
amount,
|
@@ -4221,10 +4258,7 @@ async function subscribeNompoolStaking(chaindataProvider, chainConnector, addres
|
|
4221
4258
|
source: "substrate-native",
|
4222
4259
|
status: "live",
|
4223
4260
|
address,
|
4224
|
-
|
4225
|
-
subChainId: chainId
|
4226
|
-
},
|
4227
|
-
chainId,
|
4261
|
+
networkId: chainId,
|
4228
4262
|
tokenId,
|
4229
4263
|
values: [{
|
4230
4264
|
source: "nompools-staking",
|
@@ -4468,10 +4502,7 @@ async function subscribeSubtensorStaking(chaindataProvider, chainConnector, addr
|
|
4468
4502
|
source: "substrate-native",
|
4469
4503
|
status: "live",
|
4470
4504
|
address,
|
4471
|
-
|
4472
|
-
subChainId: chainId
|
4473
|
-
},
|
4474
|
-
chainId,
|
4505
|
+
networkId: chainId,
|
4475
4506
|
tokenId,
|
4476
4507
|
values: [{
|
4477
4508
|
source: "subtensor-staking",
|
@@ -4571,17 +4602,22 @@ const filterBaseLocks = locks => {
|
|
4571
4602
|
};
|
4572
4603
|
|
4573
4604
|
// TODO: Make these titles translatable
|
4574
|
-
const getLockTitle = (lock
|
4575
|
-
|
4576
|
-
|
4605
|
+
const getLockTitle = (lock
|
4606
|
+
// {
|
4607
|
+
// // balance
|
4608
|
+
// }: { balance?: Balance } = {},
|
4609
|
+
) => {
|
4577
4610
|
if (!lock.label) return lock.label;
|
4578
4611
|
if (lock.label === "democracy") return "Governance";
|
4579
4612
|
if (lock.label === "crowdloan") {
|
4580
4613
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
4581
4614
|
const paraId = lock.meta?.paraId;
|
4582
4615
|
if (!paraId) return "Crowdloan";
|
4583
|
-
|
4584
|
-
|
4616
|
+
// balance?.network?.parathreads?.find(
|
4617
|
+
// (parathread) => parathread?.paraId === paraId,
|
4618
|
+
// )?.name
|
4619
|
+
|
4620
|
+
return `${`Parachain ${paraId}`} Crowdloan`;
|
4585
4621
|
}
|
4586
4622
|
if (lock.label === "nompools-staking") return "Pooled Staking";
|
4587
4623
|
if (lock.label === "nompools-unbonding") return "Pooled Staking";
|
@@ -4594,7 +4630,9 @@ const getLockTitle = (lock, {
|
|
4594
4630
|
};
|
4595
4631
|
|
4596
4632
|
const moduleType$2 = "substrate-native";
|
4597
|
-
|
4633
|
+
|
4634
|
+
// export const subNativeTokenId = (chainId: ChainId) =>
|
4635
|
+
// `${chainId}-substrate-native`.toLowerCase().replace(/ /g, "-")
|
4598
4636
|
|
4599
4637
|
/**
|
4600
4638
|
* Function to merge two 'sub sources' of the same balance together, or
|
@@ -4693,10 +4731,7 @@ async function buildQueries$1(chains, tokens, chainStorageCoders, miniMetadatas,
|
|
4693
4731
|
source: "substrate-native",
|
4694
4732
|
status: "live",
|
4695
4733
|
address,
|
4696
|
-
|
4697
|
-
subChainId: chainId
|
4698
|
-
},
|
4699
|
-
chainId,
|
4734
|
+
networkId: chainId,
|
4700
4735
|
tokenId,
|
4701
4736
|
values: []
|
4702
4737
|
};
|
@@ -5388,7 +5423,7 @@ const SubNativeModule = hydrate => {
|
|
5388
5423
|
const nonCurrentTokens = Object.keys(addressesByToken).filter(tokenId => !currentTokens.has(tokenId)).sort(sortChains);
|
5389
5424
|
|
5390
5425
|
// break nonCurrentTokens into chunks of POLLING_WINDOW_SIZE
|
5391
|
-
await PromisePool
|
5426
|
+
await PromisePool.withConcurrency(POLLING_WINDOW_SIZE).for(nonCurrentTokens).process(async nonCurrentTokenId => await poll({
|
5392
5427
|
[nonCurrentTokenId]: addressesByToken[nonCurrentTokenId]
|
5393
5428
|
}));
|
5394
5429
|
|
@@ -6632,7 +6667,6 @@ var psp22Abi = {
|
|
6632
6667
|
};
|
6633
6668
|
|
6634
6669
|
const moduleType$1 = "substrate-psp22";
|
6635
|
-
const subPsp22TokenId = (chainId, tokenSymbol) => `${chainId}-substrate-psp22-${tokenSymbol}`.toLowerCase().replace(/ /g, "-");
|
6636
6670
|
const SubPsp22Module = hydrate => {
|
6637
6671
|
const {
|
6638
6672
|
chainConnectors,
|
@@ -6642,16 +6676,14 @@ const SubPsp22Module = hydrate => {
|
|
6642
6676
|
assert(chainConnector, "This module requires a substrate chain connector");
|
6643
6677
|
return {
|
6644
6678
|
...DefaultBalanceModule(moduleType$1),
|
6645
|
-
async fetchSubstrateChainMeta(
|
6646
|
-
const isTestnet = (await chaindataProvider.chainById(chainId))?.isTestnet || false
|
6647
|
-
return {
|
6648
|
-
|
6649
|
-
};
|
6679
|
+
async fetchSubstrateChainMeta(_chainId) {
|
6680
|
+
// const isTestnet = (await chaindataProvider.chainById(chainId))?.isTestnet || false
|
6681
|
+
// return { isTestnet }
|
6682
|
+
return undefined;
|
6650
6683
|
},
|
6651
|
-
async fetchSubstrateChainTokens(chainId,
|
6652
|
-
const {
|
6653
|
-
|
6654
|
-
} = chainMeta;
|
6684
|
+
async fetchSubstrateChainTokens(chainId, _chainMeta, moduleConfig) {
|
6685
|
+
// const { isTestnet } = chainMeta
|
6686
|
+
|
6655
6687
|
const registry = new TypeRegistry();
|
6656
6688
|
const Psp22Abi = new Abi(psp22Abi);
|
6657
6689
|
|
@@ -6682,12 +6714,12 @@ const SubPsp22Module = hydrate => {
|
|
6682
6714
|
const decimalsData = decimalsResult.toJSON()?.result?.ok?.data;
|
6683
6715
|
decimals = typeof decimalsData === "string" && decimalsData.startsWith("0x") ? hexToNumber(decimalsData) : decimals;
|
6684
6716
|
})();
|
6685
|
-
const id = subPsp22TokenId(chainId,
|
6717
|
+
const id = subPsp22TokenId(chainId, contractAddress);
|
6686
6718
|
const token = {
|
6687
6719
|
id,
|
6688
6720
|
type: "substrate-psp22",
|
6689
6721
|
platform: "polkadot",
|
6690
|
-
isTestnet,
|
6722
|
+
// isTestnet,
|
6691
6723
|
isDefault: tokenConfig.isDefault ?? true,
|
6692
6724
|
symbol,
|
6693
6725
|
decimals,
|
@@ -6697,10 +6729,6 @@ const SubPsp22Module = hydrate => {
|
|
6697
6729
|
contractAddress,
|
6698
6730
|
networkId: chainId
|
6699
6731
|
};
|
6700
|
-
if (tokenConfig?.symbol) {
|
6701
|
-
token.symbol = tokenConfig?.symbol;
|
6702
|
-
token.id = subPsp22TokenId(chainId, token.symbol);
|
6703
|
-
}
|
6704
6732
|
if (tokenConfig?.coingeckoId) token.coingeckoId = tokenConfig?.coingeckoId;
|
6705
6733
|
if (tokenConfig?.mirrorOf) token.mirrorOf = tokenConfig?.mirrorOf;
|
6706
6734
|
tokens[token.id] = token;
|
@@ -6861,10 +6889,7 @@ const fetchBalances = async (chainConnector, tokens, addressesByToken) => {
|
|
6861
6889
|
source: "substrate-psp22",
|
6862
6890
|
status: "live",
|
6863
6891
|
address,
|
6864
|
-
|
6865
|
-
subChainId: token.networkId
|
6866
|
-
},
|
6867
|
-
chainId: token.networkId,
|
6892
|
+
networkId: token.networkId,
|
6868
6893
|
tokenId,
|
6869
6894
|
value: balance
|
6870
6895
|
};
|
@@ -6888,7 +6913,6 @@ const fetchBalances = async (chainConnector, tokens, addressesByToken) => {
|
|
6888
6913
|
|
6889
6914
|
const moduleType = "substrate-tokens";
|
6890
6915
|
const defaultPalletId = "Tokens";
|
6891
|
-
const subTokensTokenId = (chainId, onChainId) => `${chainId}-substrate-tokens-${compressToEncodedURIComponent(String(onChainId))}`;
|
6892
6916
|
const SubTokensModule = hydrate => {
|
6893
6917
|
const {
|
6894
6918
|
chainConnectors,
|
@@ -6899,14 +6923,8 @@ const SubTokensModule = hydrate => {
|
|
6899
6923
|
return {
|
6900
6924
|
...DefaultBalanceModule(moduleType),
|
6901
6925
|
async fetchSubstrateChainMeta(chainId, moduleConfig, metadataRpc) {
|
6902
|
-
|
6903
|
-
if (
|
6904
|
-
isTestnet
|
6905
|
-
};
|
6906
|
-
if ((moduleConfig?.tokens ?? []).length < 1) return {
|
6907
|
-
isTestnet
|
6908
|
-
};
|
6909
|
-
const metadataVersion = getMetadataVersion(metadataRpc);
|
6926
|
+
if (metadataRpc === undefined) return {};
|
6927
|
+
if ((moduleConfig?.tokens ?? []).length < 1) return {};
|
6910
6928
|
const metadata = decAnyMetadata(metadataRpc);
|
6911
6929
|
const palletId = moduleConfig?.palletId ?? defaultPalletId;
|
6912
6930
|
compactMetadata(metadata, [{
|
@@ -6915,20 +6933,13 @@ const SubTokensModule = hydrate => {
|
|
6915
6933
|
}]);
|
6916
6934
|
const miniMetadata = encodeMetadata(metadata);
|
6917
6935
|
return palletId === defaultPalletId ? {
|
6918
|
-
|
6919
|
-
miniMetadata,
|
6920
|
-
metadataVersion
|
6936
|
+
miniMetadata
|
6921
6937
|
} : {
|
6922
|
-
isTestnet,
|
6923
6938
|
palletId,
|
6924
|
-
miniMetadata
|
6925
|
-
metadataVersion
|
6939
|
+
miniMetadata
|
6926
6940
|
};
|
6927
6941
|
},
|
6928
6942
|
async fetchSubstrateChainTokens(chainId, chainMeta, moduleConfig) {
|
6929
|
-
const {
|
6930
|
-
isTestnet
|
6931
|
-
} = chainMeta;
|
6932
6943
|
const tokens = {};
|
6933
6944
|
for (const tokenConfig of moduleConfig?.tokens ?? []) {
|
6934
6945
|
try {
|
@@ -6942,7 +6953,6 @@ const SubTokensModule = hydrate => {
|
|
6942
6953
|
id,
|
6943
6954
|
type: "substrate-tokens",
|
6944
6955
|
platform: "polkadot",
|
6945
|
-
isTestnet,
|
6946
6956
|
isDefault: tokenConfig.isDefault ?? true,
|
6947
6957
|
symbol,
|
6948
6958
|
decimals,
|
@@ -6952,10 +6962,6 @@ const SubTokensModule = hydrate => {
|
|
6952
6962
|
onChainId,
|
6953
6963
|
networkId: chainId
|
6954
6964
|
};
|
6955
|
-
if (tokenConfig?.symbol) {
|
6956
|
-
token.symbol = tokenConfig?.symbol;
|
6957
|
-
token.id = subTokensTokenId(chainId, token.onChainId);
|
6958
|
-
}
|
6959
6965
|
if (tokenConfig?.coingeckoId) token.coingeckoId = tokenConfig?.coingeckoId;
|
6960
6966
|
if (tokenConfig?.mirrorOf) token.mirrorOf = tokenConfig?.mirrorOf;
|
6961
6967
|
tokens[token.id] = token;
|
@@ -7127,18 +7133,18 @@ async function buildQueries(chaindataProvider, addressesByToken) {
|
|
7127
7133
|
log.debug(`This module doesn't handle tokens of type ${token.type}`);
|
7128
7134
|
return [];
|
7129
7135
|
}
|
7130
|
-
const
|
7131
|
-
if (!
|
7136
|
+
const networkId = token.networkId;
|
7137
|
+
if (!networkId) {
|
7132
7138
|
log.warn(`Token ${tokenId} has no chain`);
|
7133
7139
|
return [];
|
7134
7140
|
}
|
7135
|
-
const chain = chains[
|
7141
|
+
const chain = chains[networkId];
|
7136
7142
|
if (!chain) {
|
7137
|
-
log.warn(`Chain ${
|
7143
|
+
log.warn(`Chain ${networkId} for token ${tokenId} not found`);
|
7138
7144
|
return [];
|
7139
7145
|
}
|
7140
7146
|
return addresses.flatMap(address => {
|
7141
|
-
const scaleCoder = chainStorageCoders.get(
|
7147
|
+
const scaleCoder = chainStorageCoders.get(networkId)?.storage;
|
7142
7148
|
const onChainId = (() => {
|
7143
7149
|
try {
|
7144
7150
|
return papiParse(token.onChainId);
|
@@ -7146,12 +7152,12 @@ async function buildQueries(chaindataProvider, addressesByToken) {
|
|
7146
7152
|
return token.onChainId;
|
7147
7153
|
}
|
7148
7154
|
})();
|
7149
|
-
const stateKey = encodeStateKey(scaleCoder, `Invalid address / token onChainId in ${
|
7155
|
+
const stateKey = encodeStateKey(scaleCoder, `Invalid address / token onChainId in ${networkId} storage query ${address} / ${token.onChainId}`, address, onChainId);
|
7150
7156
|
if (!stateKey) return [];
|
7151
7157
|
const decodeResult = change => {
|
7152
7158
|
/** NOTE: This type is only a hint for typescript, the chain can actually return whatever it wants to */
|
7153
7159
|
|
7154
|
-
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-tokens balance on chain ${
|
7160
|
+
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-tokens balance on chain ${networkId}`) ?? {
|
7155
7161
|
free: 0n,
|
7156
7162
|
reserved: 0n,
|
7157
7163
|
frozen: 0n
|
@@ -7176,16 +7182,13 @@ async function buildQueries(chaindataProvider, addressesByToken) {
|
|
7176
7182
|
source: "substrate-tokens",
|
7177
7183
|
status: "live",
|
7178
7184
|
address,
|
7179
|
-
|
7180
|
-
subChainId: chainId
|
7181
|
-
},
|
7182
|
-
chainId,
|
7185
|
+
networkId,
|
7183
7186
|
tokenId: token.id,
|
7184
7187
|
values: balanceValues
|
7185
7188
|
};
|
7186
7189
|
};
|
7187
7190
|
return {
|
7188
|
-
chainId,
|
7191
|
+
chainId: networkId,
|
7189
7192
|
stateKey,
|
7190
7193
|
decodeResult
|
7191
7194
|
};
|
@@ -7198,7 +7201,7 @@ const defaultBalanceModules = [EvmErc20Module, EvmNativeModule, EvmUniswapV2Modu
|
|
7198
7201
|
/** Pulls the latest chaindata from https://github.com/TalismanSociety/chaindata */
|
7199
7202
|
const hydrateChaindataAndMiniMetadata = async (chaindataProvider, miniMetadataUpdater) => {
|
7200
7203
|
// need chains to be provisioned first, or substrate balances won't fetch on first subscription
|
7201
|
-
await chaindataProvider.
|
7204
|
+
await chaindataProvider.hydrate();
|
7202
7205
|
await Promise.all([miniMetadataUpdater.hydrateFromChaindata(), miniMetadataUpdater.hydrateCustomChains()]);
|
7203
7206
|
const chains = await chaindataProvider.chains();
|
7204
7207
|
const {
|
@@ -7216,9 +7219,9 @@ const updateCustomMiniMetadata = async (chaindataProvider, miniMetadataUpdater)
|
|
7216
7219
|
|
7217
7220
|
/** Fetches any missing Evm Tokens */
|
7218
7221
|
const updateEvmTokens = async (chaindataProvider, evmTokenFetcher) => {
|
7219
|
-
await chaindataProvider.
|
7222
|
+
await chaindataProvider.hydrate();
|
7220
7223
|
const evmNetworkIds = await chaindataProvider.evmNetworkIds();
|
7221
7224
|
await evmTokenFetcher.update(evmNetworkIds);
|
7222
7225
|
};
|
7223
7226
|
|
7224
|
-
export { Balance, BalanceFormatter, BalanceValueGetter, Balances, Change24hCurrencyFormatter, DefaultBalanceModule, EvmErc20Module, EvmNativeModule, EvmTokenFetcher, EvmUniswapV2Module, FiatSumBalancesFormatter, MiniMetadataUpdater, ONE_ALPHA_TOKEN, PlanckSumBalancesFormatter, RpcStateQueryHelper, SCALE_FACTOR, SUBTENSOR_MIN_STAKE_AMOUNT_PLANK, SUBTENSOR_ROOT_NETUID, SubAssetsModule, SubForeignAssetsModule, SubNativeModule, SubPsp22Module, SubTokensModule, SumBalancesFormatter, TalismanBalancesDatabase, abiMulticall, balances, buildStorageCoders, calculateAlphaPrice, calculateTaoAmountFromAlpha, calculateTaoFromDynamicInfo, compress, configureStore, db, decodeOutput, decompress, defaultBalanceModules, deriveMiniMetadataId, detectTransferMethod, erc20Abi, erc20BalancesAggregatorAbi,
|
7227
|
+
export { Balance, BalanceFormatter, BalanceValueGetter, Balances, Change24hCurrencyFormatter, DefaultBalanceModule, EvmErc20Module, EvmNativeModule, EvmTokenFetcher, EvmUniswapV2Module, FiatSumBalancesFormatter, MiniMetadataUpdater, ONE_ALPHA_TOKEN, PlanckSumBalancesFormatter, RpcStateQueryHelper, SCALE_FACTOR, SUBTENSOR_MIN_STAKE_AMOUNT_PLANK, SUBTENSOR_ROOT_NETUID, SubAssetsModule, SubForeignAssetsModule, SubNativeModule, SubPsp22Module, SubTokensModule, SumBalancesFormatter, TalismanBalancesDatabase, abiMulticall, balances, buildStorageCoders, calculateAlphaPrice, calculateTaoAmountFromAlpha, calculateTaoFromDynamicInfo, compress, configureStore, db, decodeOutput, decompress, defaultBalanceModules, deriveMiniMetadataId, detectTransferMethod, erc20Abi, erc20BalancesAggregatorAbi, excludeFromFeePayableLocks, excludeFromTransferableAmount, filterBaseLocks, filterMirrorTokens, findChainMeta, getBalanceId, getLockTitle, getUniqueChainIds, getValueId, hydrateChaindataAndMiniMetadata, includeInTotalExtraAmount, makeContractCaller, uniswapV2PairAbi, updateCustomMiniMetadata, updateEvmTokens };
|