@talismn/balances 0.0.0-pr2043-20250615092436 → 0.0.0-pr2043-20250617092446
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/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 +402 -409
- package/dist/talismn-balances.cjs.prod.js +402 -409
- package/dist/talismn-balances.esm.js +400 -399
- 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, EvmErc20TokenSchema, evmNativeTokenId, evmUniswapV2TokenId, githubTokenLogoUrl, 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-20250617092446"};
|
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,17 +1595,16 @@ 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,
|
1532
1603
|
isDefault: tokenConfig.isDefault ?? true,
|
1533
1604
|
symbol,
|
1534
1605
|
decimals,
|
1535
1606
|
name: contractName ?? symbol,
|
1536
|
-
logo: tokenConfig?.logo
|
1607
|
+
logo: tokenConfig?.logo,
|
1537
1608
|
contractAddress,
|
1538
1609
|
networkId: chainId
|
1539
1610
|
};
|
@@ -1559,7 +1630,7 @@ const EvmErc20Module = hydrate => {
|
|
1559
1630
|
const subscriptionInterval = 6_000; // 6_000ms == 6 seconds
|
1560
1631
|
const initDelay = 1_500; // 1_500ms == 1.5 seconds
|
1561
1632
|
const initialisingBalances = new Set();
|
1562
|
-
const positiveBalanceNetworks = new Set(initialBalances?.map(b => b.
|
1633
|
+
const positiveBalanceNetworks = new Set(initialBalances?.map(b => b.networkId));
|
1563
1634
|
const tokens = await getModuleTokens();
|
1564
1635
|
|
1565
1636
|
// for chains with a zero balance we only call fetchBalances once every 5 subscriptionIntervals
|
@@ -1696,20 +1767,18 @@ const fetchBalances$3 = async (evmChainConnector, tokenAddressesByNetwork, erc20
|
|
1696
1767
|
results: [],
|
1697
1768
|
errors: []
|
1698
1769
|
};
|
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[
|
1770
|
+
await Promise.all(Object.entries(tokenAddressesByNetwork).map(async ([networkId, networkParams]) => {
|
1771
|
+
const publicClient = await evmChainConnector.getPublicClientForEvmNetwork(networkId);
|
1772
|
+
if (!publicClient) throw new EvmErc20NetworkError(`Could not get rpc provider for evm network ${networkId}`, networkId);
|
1773
|
+
const balances = await getEvmTokenBalances(publicClient, networkParams, result.errors, erc20Aggregators[networkId]);
|
1703
1774
|
|
1704
1775
|
// consider only non null balances in the results
|
1705
1776
|
result.results.push(...balances.filter(isTruthy).map((free, i) => ({
|
1706
1777
|
source: "evm-erc20",
|
1707
1778
|
status: "live",
|
1708
1779
|
address: networkParams[i].address,
|
1709
|
-
multiChainId: {
|
1710
|
-
|
1711
|
-
},
|
1712
|
-
evmNetworkId,
|
1780
|
+
// multiChainId: { evmChainId: evmNetworkId },
|
1781
|
+
networkId,
|
1713
1782
|
tokenId: networkParams[i].token.id,
|
1714
1783
|
value: free
|
1715
1784
|
})));
|
@@ -1794,9 +1863,12 @@ function groupAddressesByTokenByEvmNetwork$1(addressesByToken, tokens) {
|
|
1794
1863
|
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
1864
|
|
1796
1865
|
const moduleType$6 = "evm-native";
|
1797
|
-
|
1866
|
+
|
1867
|
+
// export const evmNativeTokenId = (chainId: EvmNetworkId) =>
|
1868
|
+
// `${chainId}-evm-native`.toLowerCase().replace(/ /g, "-")
|
1869
|
+
|
1798
1870
|
const getEvmNetworkIdFromTokenId = tokenId => {
|
1799
|
-
const evmNetworkId = tokenId.split("
|
1871
|
+
const evmNetworkId = tokenId.split(":")[0];
|
1800
1872
|
if (!evmNetworkId) throw new Error(`Can't detect chainId for token ${tokenId}`);
|
1801
1873
|
return evmNetworkId;
|
1802
1874
|
};
|
@@ -1817,35 +1889,31 @@ const EvmNativeModule = hydrate => {
|
|
1817
1889
|
* This method is currently executed on [a squid](https://github.com/TalismanSociety/chaindata-squid/blob/0ee02818bf5caa7362e3f3664e55ef05ec8df078/src/steps/updateEvmNetworksFromGithub.ts#L280-L284).
|
1818
1890
|
* 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
1891
|
*/
|
1820
|
-
async fetchEvmChainMeta(
|
1821
|
-
const isTestnet = (await chaindataProvider.evmNetworkById(chainId))?.isTestnet || false
|
1822
|
-
|
1823
|
-
|
1824
|
-
|
1892
|
+
async fetchEvmChainMeta(_chainId) {
|
1893
|
+
// const isTestnet = (await chaindataProvider.evmNetworkById(chainId))?.isTestnet || false
|
1894
|
+
|
1895
|
+
// return { isTestnet }
|
1896
|
+
return undefined;
|
1825
1897
|
},
|
1826
1898
|
/**
|
1827
1899
|
* This method is currently executed on [a squid](https://github.com/TalismanSociety/chaindata-squid/blob/0ee02818bf5caa7362e3f3664e55ef05ec8df078/src/steps/updateEvmNetworksFromGithub.ts#L338-L343).
|
1828
1900
|
* 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
1901
|
*/
|
1830
|
-
async fetchEvmChainTokens(
|
1831
|
-
const {
|
1832
|
-
isTestnet
|
1833
|
-
} = chainMeta;
|
1902
|
+
async fetchEvmChainTokens(networkId, chainMeta, moduleConfig) {
|
1834
1903
|
const symbol = moduleConfig?.symbol ?? "ETH";
|
1835
1904
|
const decimals = typeof moduleConfig?.decimals === "number" ? moduleConfig.decimals : 18;
|
1836
1905
|
const name = moduleConfig?.name ?? symbol;
|
1837
|
-
const id = evmNativeTokenId(
|
1906
|
+
const id = evmNativeTokenId(networkId);
|
1838
1907
|
const nativeToken = {
|
1839
1908
|
platform: "ethereum",
|
1840
1909
|
id,
|
1841
1910
|
type: "evm-native",
|
1842
|
-
isTestnet,
|
1843
1911
|
isDefault: true,
|
1844
1912
|
symbol,
|
1845
1913
|
decimals,
|
1846
1914
|
name,
|
1847
|
-
logo: moduleConfig?.logo
|
1848
|
-
networkId
|
1915
|
+
logo: moduleConfig?.logo,
|
1916
|
+
networkId
|
1849
1917
|
};
|
1850
1918
|
if (moduleConfig?.symbol) nativeToken.symbol = moduleConfig?.symbol;
|
1851
1919
|
if (moduleConfig?.coingeckoId) nativeToken.coingeckoId = moduleConfig?.coingeckoId;
|
@@ -1880,7 +1948,7 @@ const EvmNativeModule = hydrate => {
|
|
1880
1948
|
// setup initialising balances for all active evm networks
|
1881
1949
|
const activeEvmNetworkIds = Object.keys(ethAddressesByToken).map(getEvmNetworkIdFromTokenId);
|
1882
1950
|
const initialisingBalances = new Set(activeEvmNetworkIds);
|
1883
|
-
const positiveBalanceNetworks = new Set(initialBalances?.map(b => b.
|
1951
|
+
const positiveBalanceNetworks = new Set(initialBalances?.map(b => b.networkId));
|
1884
1952
|
const poll = async () => {
|
1885
1953
|
if (!subscriptionActive) return;
|
1886
1954
|
zeroBalanceSubscriptionIntervalCounter = (zeroBalanceSubscriptionIntervalCounter + 1) % 5;
|
@@ -1907,10 +1975,10 @@ const EvmNativeModule = hydrate => {
|
|
1907
1975
|
log.error(balance.message, balance.networkId);
|
1908
1976
|
initialisingBalances.delete(balance.networkId);
|
1909
1977
|
} else {
|
1910
|
-
if (balance.
|
1911
|
-
initialisingBalances.delete(balance.
|
1978
|
+
if (balance.networkId) {
|
1979
|
+
initialisingBalances.delete(balance.networkId);
|
1912
1980
|
if (BigInt(balance.value) > 0n) {
|
1913
|
-
positiveBalanceNetworks.add(balance.
|
1981
|
+
positiveBalanceNetworks.add(balance.networkId);
|
1914
1982
|
}
|
1915
1983
|
resultBalances.push(balance);
|
1916
1984
|
}
|
@@ -1960,23 +2028,23 @@ const fetchBalances$2 = async (evmChainConnector, addressesByToken, tokens) => {
|
|
1960
2028
|
if (!evmChainConnector) throw new Error(`This module requires an evm chain connector`);
|
1961
2029
|
return Promise.all(Object.entries(addressesByToken).map(async ([tokenId, addresses]) => {
|
1962
2030
|
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 ${
|
2031
|
+
const networkId = token.networkId;
|
2032
|
+
if (!networkId) throw new Error(`Token ${token.id} has no evm network`);
|
2033
|
+
const publicClient = await evmChainConnector.getPublicClientForEvmNetwork(networkId);
|
2034
|
+
if (!publicClient) throw new Error(`Could not get rpc provider for evm network ${networkId}`);
|
1967
2035
|
|
1968
2036
|
// fetch all balances
|
1969
2037
|
const freeBalances = await getFreeBalances(publicClient, addresses);
|
1970
2038
|
const balanceResults = addresses.map((address, i) => {
|
1971
|
-
if (freeBalances[i] === "error") return new EvmNativeBalanceError("Could not fetch balance ",
|
2039
|
+
if (freeBalances[i] === "error") return new EvmNativeBalanceError("Could not fetch balance ", networkId);
|
1972
2040
|
return {
|
1973
2041
|
source: "evm-native",
|
1974
2042
|
status: "live",
|
1975
2043
|
address: address,
|
1976
2044
|
multiChainId: {
|
1977
|
-
evmChainId:
|
2045
|
+
evmChainId: networkId
|
1978
2046
|
},
|
1979
|
-
|
2047
|
+
networkId,
|
1980
2048
|
tokenId,
|
1981
2049
|
value: freeBalances[i].toString()
|
1982
2050
|
};
|
@@ -2598,7 +2666,6 @@ const uniswapV2PairAbi = [{
|
|
2598
2666
|
}];
|
2599
2667
|
|
2600
2668
|
const moduleType$5 = "evm-uniswapv2";
|
2601
|
-
const evmUniswapV2TokenId = (chainId, contractAddress) => `${chainId}-evm-uniswapv2-${contractAddress}`.toLowerCase();
|
2602
2669
|
const EvmUniswapV2Module = hydrate => {
|
2603
2670
|
const {
|
2604
2671
|
chainConnectors,
|
@@ -2608,16 +2675,15 @@ const EvmUniswapV2Module = hydrate => {
|
|
2608
2675
|
assert(chainConnector, "This module requires an evm chain connector");
|
2609
2676
|
return {
|
2610
2677
|
...DefaultBalanceModule(moduleType$5),
|
2611
|
-
async fetchEvmChainMeta(
|
2612
|
-
const isTestnet = (await chaindataProvider.evmNetworkById(chainId))?.isTestnet || false
|
2613
|
-
|
2614
|
-
|
2615
|
-
|
2678
|
+
async fetchEvmChainMeta(_chainId) {
|
2679
|
+
// const isTestnet = (await chaindataProvider.evmNetworkById(chainId))?.isTestnet || false
|
2680
|
+
|
2681
|
+
// return { isTestnet }
|
2682
|
+
return undefined;
|
2616
2683
|
},
|
2617
|
-
async fetchEvmChainTokens(chainId,
|
2618
|
-
const {
|
2619
|
-
|
2620
|
-
} = chainMeta;
|
2684
|
+
async fetchEvmChainTokens(chainId, _chainMeta, moduleConfig) {
|
2685
|
+
//const { isTestnet } = chainMeta
|
2686
|
+
|
2621
2687
|
const tokens = {};
|
2622
2688
|
for (const tokenConfig of moduleConfig?.pools ?? []) {
|
2623
2689
|
const {
|
@@ -2642,7 +2708,7 @@ const EvmUniswapV2Module = hydrate => {
|
|
2642
2708
|
id,
|
2643
2709
|
type: "evm-uniswapv2",
|
2644
2710
|
platform: "ethereum",
|
2645
|
-
isTestnet,
|
2711
|
+
// isTestnet,
|
2646
2712
|
isDefault: tokenConfig.isDefault ?? false,
|
2647
2713
|
symbol: `${symbol0 ?? "UNKNOWN"}/${symbol1 ?? "UNKNOWN"}`,
|
2648
2714
|
name: name ?? `${symbol0 ?? "UNKNOWN"}/${symbol1 ?? "UNKNOWN"}`,
|
@@ -2676,9 +2742,9 @@ const EvmUniswapV2Module = hydrate => {
|
|
2676
2742
|
const initDelay = 1_500; // 1_500ms == 1.5 seconds
|
2677
2743
|
|
2678
2744
|
const initialBalancesByNetwork = initialBalances?.reduce((result, b) => {
|
2679
|
-
if (!b.
|
2680
|
-
if (!result[b.
|
2681
|
-
result[b.
|
2745
|
+
if (!b.networkId) return result;
|
2746
|
+
if (!result[b.networkId]) result[b.networkId] = {};
|
2747
|
+
result[b.networkId][getBalanceId(b)] = b;
|
2682
2748
|
return result;
|
2683
2749
|
}, {});
|
2684
2750
|
const cache = new Map(Object.entries(initialBalancesByNetwork ?? {}));
|
@@ -2738,12 +2804,12 @@ const EvmUniswapV2Module = hydrate => {
|
|
2738
2804
|
};
|
2739
2805
|
const fetchBalances$1 = async (evmChainConnector, evmNetworks, tokens, addressesByToken) => {
|
2740
2806
|
const addressesByTokenGroupedByEvmNetwork = groupAddressesByTokenByEvmNetwork(addressesByToken, tokens);
|
2741
|
-
const balances = (await Promise.allSettled(Object.entries(addressesByTokenGroupedByEvmNetwork).map(async ([
|
2807
|
+
const balances = (await Promise.allSettled(Object.entries(addressesByTokenGroupedByEvmNetwork).map(async ([networkId, addressesByToken]) => {
|
2742
2808
|
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 ${
|
2809
|
+
const evmNetwork = evmNetworks[networkId];
|
2810
|
+
if (!evmNetwork) throw new Error(`Evm network ${networkId} not found`);
|
2811
|
+
const publicClient = await evmChainConnector.getPublicClientForEvmNetwork(networkId);
|
2812
|
+
if (!publicClient) throw new Error(`Could not get rpc provider for evm network ${networkId}`);
|
2747
2813
|
const tokensAndAddresses = Object.entries(addressesByToken).reduce((tokensAndAddresses, [tokenId, addresses]) => {
|
2748
2814
|
const token = tokens[tokenId];
|
2749
2815
|
if (!token) {
|
@@ -2765,10 +2831,7 @@ const fetchBalances$1 = async (evmChainConnector, evmNetworks, tokens, addresses
|
|
2765
2831
|
source: "evm-uniswapv2",
|
2766
2832
|
status: "live",
|
2767
2833
|
address: address,
|
2768
|
-
|
2769
|
-
evmChainId: evmNetwork.id
|
2770
|
-
},
|
2771
|
-
evmNetworkId,
|
2834
|
+
networkId,
|
2772
2835
|
tokenId: token.id,
|
2773
2836
|
values: await getPoolBalance(publicClient, token.contractAddress, address)
|
2774
2837
|
}));
|
@@ -2900,24 +2963,20 @@ async function balances(balanceModule, addressesByToken, callback) {
|
|
2900
2963
|
*/
|
2901
2964
|
const findChainMeta = (miniMetadatas, moduleType, chain) => {
|
2902
2965
|
if (!chain) return [undefined, undefined];
|
2903
|
-
if (!chain.specName) return [undefined, undefined];
|
2904
2966
|
if (!chain.specVersion) return [undefined, undefined];
|
2905
2967
|
|
2906
2968
|
// TODO: This is spaghetti to import this here, it should be injected into each balance module or something.
|
2907
2969
|
const metadataId = deriveMiniMetadataId({
|
2908
2970
|
source: moduleType,
|
2909
2971
|
chainId: chain.id,
|
2910
|
-
specName: chain.specName,
|
2911
2972
|
specVersion: chain.specVersion,
|
2912
|
-
|
2973
|
+
libVersion
|
2913
2974
|
});
|
2914
2975
|
|
2915
2976
|
// TODO: Fix this (needs to fetch miniMetadata without being async)
|
2916
2977
|
const miniMetadata = miniMetadatas.get(metadataId);
|
2917
2978
|
const chainMeta = miniMetadata ? {
|
2918
|
-
miniMetadata: miniMetadata.data
|
2919
|
-
metadataVersion: miniMetadata.version,
|
2920
|
-
...JSON.parse(miniMetadata.extra)
|
2979
|
+
miniMetadata: miniMetadata.data
|
2921
2980
|
} : undefined;
|
2922
2981
|
return [chainMeta, miniMetadata];
|
2923
2982
|
};
|
@@ -3145,7 +3204,6 @@ const decompress = data => {
|
|
3145
3204
|
};
|
3146
3205
|
|
3147
3206
|
const moduleType$4 = "substrate-assets";
|
3148
|
-
const subAssetTokenId = (chainId, assetId, tokenSymbol) => `${chainId}-substrate-assets-${assetId}-${tokenSymbol}`.toLowerCase().replace(/ /g, "-");
|
3149
3207
|
const SubAssetsModule = hydrate => {
|
3150
3208
|
const {
|
3151
3209
|
chainConnectors,
|
@@ -3179,12 +3237,9 @@ const SubAssetsModule = hydrate => {
|
|
3179
3237
|
async fetchSubstrateChainTokens(chainId, chainMeta, moduleConfig) {
|
3180
3238
|
if ((moduleConfig?.tokens ?? []).length < 1) return {};
|
3181
3239
|
const {
|
3182
|
-
|
3183
|
-
miniMetadata,
|
3184
|
-
metadataVersion
|
3240
|
+
miniMetadata
|
3185
3241
|
} = chainMeta;
|
3186
|
-
if (miniMetadata
|
3187
|
-
if (metadataVersion < 14) return {};
|
3242
|
+
if (!miniMetadata) return {};
|
3188
3243
|
const metadata = unifyMetadata(decAnyMetadata(miniMetadata));
|
3189
3244
|
const scaleBuilder = getDynamicBuilder(getLookupFn(metadata));
|
3190
3245
|
const assetCoder = scaleBuilder.buildStorage("Assets", "Asset");
|
@@ -3201,17 +3256,16 @@ const SubAssetsModule = hydrate => {
|
|
3201
3256
|
const symbol = assetsMetadata?.symbol?.asText?.() ?? "Unit";
|
3202
3257
|
const decimals = assetsMetadata?.decimals ?? 0;
|
3203
3258
|
const isFrozen = assetsMetadata?.is_frozen ?? false;
|
3204
|
-
const id = subAssetTokenId(chainId, assetId
|
3259
|
+
const id = subAssetTokenId(chainId, assetId);
|
3205
3260
|
const token = {
|
3206
3261
|
id,
|
3207
3262
|
type: "substrate-assets",
|
3208
3263
|
platform: "polkadot",
|
3209
|
-
isTestnet,
|
3210
3264
|
isDefault: tokenConfig?.isDefault ?? true,
|
3211
3265
|
symbol,
|
3212
3266
|
name: tokenConfig?.name || symbol,
|
3213
3267
|
decimals,
|
3214
|
-
logo: tokenConfig?.logo
|
3268
|
+
logo: tokenConfig?.logo,
|
3215
3269
|
existentialDeposit,
|
3216
3270
|
assetId,
|
3217
3271
|
isFrozen,
|
@@ -3219,7 +3273,7 @@ const SubAssetsModule = hydrate => {
|
|
3219
3273
|
};
|
3220
3274
|
if (tokenConfig?.symbol) {
|
3221
3275
|
token.symbol = tokenConfig?.symbol;
|
3222
|
-
token.id = subAssetTokenId(chainId, assetId
|
3276
|
+
token.id = subAssetTokenId(chainId, assetId);
|
3223
3277
|
}
|
3224
3278
|
if (tokenConfig?.coingeckoId) token.coingeckoId = tokenConfig?.coingeckoId;
|
3225
3279
|
if (tokenConfig?.mirrorOf) token.mirrorOf = tokenConfig?.mirrorOf;
|
@@ -3340,27 +3394,27 @@ async function buildQueries$3(chaindataProvider, addressesByToken) {
|
|
3340
3394
|
log.debug(`This module doesn't handle tokens of type ${token.type}`);
|
3341
3395
|
return [];
|
3342
3396
|
}
|
3343
|
-
const
|
3344
|
-
if (!
|
3397
|
+
const networkId = token.networkId;
|
3398
|
+
if (!networkId) {
|
3345
3399
|
log.warn(`Token ${tokenId} has no chain`);
|
3346
3400
|
return [];
|
3347
3401
|
}
|
3348
|
-
const chain = chains[
|
3402
|
+
const chain = chains[networkId];
|
3349
3403
|
if (!chain) {
|
3350
|
-
log.warn(`Chain ${
|
3404
|
+
log.warn(`Chain ${networkId} for token ${tokenId} not found`);
|
3351
3405
|
return [];
|
3352
3406
|
}
|
3353
3407
|
return addresses.flatMap(address => {
|
3354
|
-
const scaleCoder = chainStorageCoders.get(
|
3408
|
+
const scaleCoder = chainStorageCoders.get(networkId)?.storage;
|
3355
3409
|
const stateKey = tryEncode(scaleCoder, BigInt(token.assetId), address) ?? tryEncode(scaleCoder, token.assetId, address);
|
3356
3410
|
if (!stateKey) {
|
3357
|
-
log.warn(`Invalid assetId / address in ${
|
3411
|
+
log.warn(`Invalid assetId / address in ${networkId} storage query ${token.assetId} / ${address}`);
|
3358
3412
|
return [];
|
3359
3413
|
}
|
3360
3414
|
const decodeResult = change => {
|
3361
3415
|
/** NOTE: This type is only a hint for typescript, the chain can actually return whatever it wants to */
|
3362
3416
|
|
3363
|
-
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-assets balance on chain ${
|
3417
|
+
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-assets balance on chain ${networkId}`) ?? {
|
3364
3418
|
balance: 0n,
|
3365
3419
|
status: {
|
3366
3420
|
type: "Liquid"
|
@@ -3394,16 +3448,13 @@ async function buildQueries$3(chaindataProvider, addressesByToken) {
|
|
3394
3448
|
source: "substrate-assets",
|
3395
3449
|
status: "live",
|
3396
3450
|
address,
|
3397
|
-
|
3398
|
-
subChainId: chainId
|
3399
|
-
},
|
3400
|
-
chainId,
|
3451
|
+
networkId,
|
3401
3452
|
tokenId: token.id,
|
3402
3453
|
values: balanceValues
|
3403
3454
|
};
|
3404
3455
|
};
|
3405
3456
|
return {
|
3406
|
-
chainId,
|
3457
|
+
chainId: networkId,
|
3407
3458
|
stateKey,
|
3408
3459
|
decodeResult
|
3409
3460
|
};
|
@@ -3423,7 +3474,6 @@ const tryEncode = (scaleCoder, ...args) => {
|
|
3423
3474
|
};
|
3424
3475
|
|
3425
3476
|
const moduleType$3 = "substrate-foreignassets";
|
3426
|
-
const subForeignAssetTokenId = (chainId, tokenSymbol) => `${chainId}-substrate-foreignassets-${tokenSymbol}`.toLowerCase().replace(/ /g, "-");
|
3427
3477
|
const SubForeignAssetsModule = hydrate => {
|
3428
3478
|
const {
|
3429
3479
|
chainConnectors,
|
@@ -3434,14 +3484,12 @@ const SubForeignAssetsModule = hydrate => {
|
|
3434
3484
|
return {
|
3435
3485
|
...DefaultBalanceModule(moduleType$3),
|
3436
3486
|
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
|
-
};
|
3487
|
+
// const isTestnet = (await chaindataProvider.chainById(chainId))?.isTestnet || false
|
3488
|
+
if (metadataRpc === undefined) return {};
|
3489
|
+
// if ((moduleConfig?.tokens ?? []).length < 1) return { isTestnet }
|
3490
|
+
|
3444
3491
|
const metadataVersion = getMetadataVersion(metadataRpc);
|
3492
|
+
if (metadataVersion < 14) return {};
|
3445
3493
|
const metadata = decAnyMetadata(metadataRpc);
|
3446
3494
|
compactMetadata(metadata, [{
|
3447
3495
|
pallet: "ForeignAssets",
|
@@ -3449,20 +3497,18 @@ const SubForeignAssetsModule = hydrate => {
|
|
3449
3497
|
}]);
|
3450
3498
|
const miniMetadata = encodeMetadata(metadata);
|
3451
3499
|
return {
|
3452
|
-
|
3453
|
-
miniMetadata,
|
3454
|
-
metadataVersion
|
3500
|
+
miniMetadata
|
3455
3501
|
};
|
3456
3502
|
},
|
3457
3503
|
async fetchSubstrateChainTokens(chainId, chainMeta, moduleConfig) {
|
3458
3504
|
if ((moduleConfig?.tokens ?? []).length < 1) return {};
|
3459
3505
|
const {
|
3460
|
-
|
3461
|
-
miniMetadata,
|
3462
|
-
metadataVersion
|
3506
|
+
miniMetadata
|
3463
3507
|
} = chainMeta;
|
3464
|
-
if (miniMetadata
|
3465
|
-
if (metadataVersion
|
3508
|
+
if (!miniMetadata) return {};
|
3509
|
+
// if (miniMetadata === undefined || metadataVersion === undefined) return {}
|
3510
|
+
// if (metadataVersion < 14) return {}
|
3511
|
+
|
3466
3512
|
const metadata = decAnyMetadata(miniMetadata);
|
3467
3513
|
const unifiedMetadata = unifyMetadata(metadata);
|
3468
3514
|
const scaleBuilder = getDynamicBuilder(getLookupFn(unifiedMetadata));
|
@@ -3486,26 +3532,22 @@ const SubForeignAssetsModule = hydrate => {
|
|
3486
3532
|
const symbol = assetsMetadata?.symbol?.asText?.() ?? "Unit";
|
3487
3533
|
const decimals = assetsMetadata?.decimals ?? 0;
|
3488
3534
|
const isFrozen = assetsMetadata?.is_frozen ?? false;
|
3489
|
-
const id = subForeignAssetTokenId(chainId,
|
3535
|
+
const id = subForeignAssetTokenId(chainId, tokenConfig.onChainId);
|
3490
3536
|
const token = {
|
3491
3537
|
id,
|
3492
3538
|
type: "substrate-foreignassets",
|
3493
3539
|
platform: "polkadot",
|
3494
|
-
isTestnet,
|
3540
|
+
// isTestnet,
|
3495
3541
|
isDefault: tokenConfig?.isDefault ?? true,
|
3496
3542
|
symbol,
|
3497
3543
|
decimals,
|
3498
3544
|
name: tokenConfig?.name || symbol,
|
3499
|
-
logo: tokenConfig?.logo
|
3545
|
+
logo: tokenConfig?.logo,
|
3500
3546
|
existentialDeposit,
|
3501
3547
|
onChainId: tokenConfig.onChainId,
|
3502
3548
|
isFrozen,
|
3503
3549
|
networkId: chainId
|
3504
3550
|
};
|
3505
|
-
if (tokenConfig?.symbol) {
|
3506
|
-
token.symbol = tokenConfig?.symbol;
|
3507
|
-
token.id = subForeignAssetTokenId(chainId, token.symbol);
|
3508
|
-
}
|
3509
3551
|
if (tokenConfig?.coingeckoId) token.coingeckoId = tokenConfig?.coingeckoId;
|
3510
3552
|
if (tokenConfig?.mirrorOf) token.mirrorOf = tokenConfig?.mirrorOf;
|
3511
3553
|
tokens[token.id] = token;
|
@@ -3611,18 +3653,18 @@ async function buildQueries$2(chaindataProvider, addressesByToken) {
|
|
3611
3653
|
log.debug(`This module doesn't handle tokens of type ${token.type}`);
|
3612
3654
|
return [];
|
3613
3655
|
}
|
3614
|
-
const
|
3615
|
-
if (!
|
3656
|
+
const networkId = token.networkId;
|
3657
|
+
if (!networkId) {
|
3616
3658
|
log.warn(`Token ${tokenId} has no chain`);
|
3617
3659
|
return [];
|
3618
3660
|
}
|
3619
|
-
const chain = chains[
|
3661
|
+
const chain = chains[networkId];
|
3620
3662
|
if (!chain) {
|
3621
|
-
log.warn(`Chain ${
|
3663
|
+
log.warn(`Chain ${networkId} for token ${tokenId} not found`);
|
3622
3664
|
return [];
|
3623
3665
|
}
|
3624
3666
|
return addresses.flatMap(address => {
|
3625
|
-
const scaleCoder = chainStorageCoders.get(
|
3667
|
+
const scaleCoder = chainStorageCoders.get(networkId)?.storage;
|
3626
3668
|
const onChainId = (() => {
|
3627
3669
|
try {
|
3628
3670
|
return papiParse(token.onChainId);
|
@@ -3630,12 +3672,12 @@ async function buildQueries$2(chaindataProvider, addressesByToken) {
|
|
3630
3672
|
return token.onChainId;
|
3631
3673
|
}
|
3632
3674
|
})();
|
3633
|
-
const stateKey = encodeStateKey(scaleCoder, `Invalid address / token onChainId in ${
|
3675
|
+
const stateKey = encodeStateKey(scaleCoder, `Invalid address / token onChainId in ${networkId} storage query ${address} / ${token.onChainId}`, onChainId, address);
|
3634
3676
|
if (!stateKey) return [];
|
3635
3677
|
const decodeResult = change => {
|
3636
3678
|
/** NOTE: This type is only a hint for typescript, the chain can actually return whatever it wants to */
|
3637
3679
|
|
3638
|
-
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-foreignassets balance on chain ${
|
3680
|
+
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-foreignassets balance on chain ${networkId}`) ?? {
|
3639
3681
|
balance: 0n,
|
3640
3682
|
status: {
|
3641
3683
|
type: "Liquid"
|
@@ -3669,16 +3711,13 @@ async function buildQueries$2(chaindataProvider, addressesByToken) {
|
|
3669
3711
|
source: "substrate-foreignassets",
|
3670
3712
|
status: "live",
|
3671
3713
|
address,
|
3672
|
-
|
3673
|
-
subChainId: chainId
|
3674
|
-
},
|
3675
|
-
chainId,
|
3714
|
+
networkId,
|
3676
3715
|
tokenId: token.id,
|
3677
3716
|
values: balanceValues
|
3678
3717
|
};
|
3679
3718
|
};
|
3680
3719
|
return {
|
3681
|
-
chainId,
|
3720
|
+
chainId: networkId,
|
3682
3721
|
stateKey,
|
3683
3722
|
decodeResult
|
3684
3723
|
};
|
@@ -3935,10 +3974,7 @@ async function subscribeCrowdloans(chaindataProvider, chainConnector, addressesB
|
|
3935
3974
|
source: "substrate-native",
|
3936
3975
|
status: "live",
|
3937
3976
|
address,
|
3938
|
-
|
3939
|
-
subChainId: chainId
|
3940
|
-
},
|
3941
|
-
chainId,
|
3977
|
+
networkId: chainId,
|
3942
3978
|
tokenId,
|
3943
3979
|
values: Array.from(contributions).map(({
|
3944
3980
|
amount,
|
@@ -4221,10 +4257,7 @@ async function subscribeNompoolStaking(chaindataProvider, chainConnector, addres
|
|
4221
4257
|
source: "substrate-native",
|
4222
4258
|
status: "live",
|
4223
4259
|
address,
|
4224
|
-
|
4225
|
-
subChainId: chainId
|
4226
|
-
},
|
4227
|
-
chainId,
|
4260
|
+
networkId: chainId,
|
4228
4261
|
tokenId,
|
4229
4262
|
values: [{
|
4230
4263
|
source: "nompools-staking",
|
@@ -4468,10 +4501,7 @@ async function subscribeSubtensorStaking(chaindataProvider, chainConnector, addr
|
|
4468
4501
|
source: "substrate-native",
|
4469
4502
|
status: "live",
|
4470
4503
|
address,
|
4471
|
-
|
4472
|
-
subChainId: chainId
|
4473
|
-
},
|
4474
|
-
chainId,
|
4504
|
+
networkId: chainId,
|
4475
4505
|
tokenId,
|
4476
4506
|
values: [{
|
4477
4507
|
source: "subtensor-staking",
|
@@ -4580,8 +4610,12 @@ const getLockTitle = (lock, {
|
|
4580
4610
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
4581
4611
|
const paraId = lock.meta?.paraId;
|
4582
4612
|
if (!paraId) return "Crowdloan";
|
4583
|
-
|
4584
|
-
|
4613
|
+
|
4614
|
+
// balance?.network?.parathreads?.find(
|
4615
|
+
// (parathread) => parathread?.paraId === paraId,
|
4616
|
+
// )?.name
|
4617
|
+
|
4618
|
+
return `${`Parachain ${paraId}`} Crowdloan`;
|
4585
4619
|
}
|
4586
4620
|
if (lock.label === "nompools-staking") return "Pooled Staking";
|
4587
4621
|
if (lock.label === "nompools-unbonding") return "Pooled Staking";
|
@@ -4594,7 +4628,9 @@ const getLockTitle = (lock, {
|
|
4594
4628
|
};
|
4595
4629
|
|
4596
4630
|
const moduleType$2 = "substrate-native";
|
4597
|
-
|
4631
|
+
|
4632
|
+
// export const subNativeTokenId = (chainId: ChainId) =>
|
4633
|
+
// `${chainId}-substrate-native`.toLowerCase().replace(/ /g, "-")
|
4598
4634
|
|
4599
4635
|
/**
|
4600
4636
|
* Function to merge two 'sub sources' of the same balance together, or
|
@@ -4693,10 +4729,7 @@ async function buildQueries$1(chains, tokens, chainStorageCoders, miniMetadatas,
|
|
4693
4729
|
source: "substrate-native",
|
4694
4730
|
status: "live",
|
4695
4731
|
address,
|
4696
|
-
|
4697
|
-
subChainId: chainId
|
4698
|
-
},
|
4699
|
-
chainId,
|
4732
|
+
networkId: chainId,
|
4700
4733
|
tokenId,
|
4701
4734
|
values: []
|
4702
4735
|
};
|
@@ -5239,7 +5272,7 @@ const SubNativeModule = hydrate => {
|
|
5239
5272
|
symbol: symbol ?? DEFAULT_SYMBOL,
|
5240
5273
|
name: moduleConfig?.name ?? symbol ?? DEFAULT_SYMBOL,
|
5241
5274
|
decimals: decimals ?? DEFAULT_DECIMALS,
|
5242
|
-
logo: moduleConfig?.logo
|
5275
|
+
logo: moduleConfig?.logo,
|
5243
5276
|
existentialDeposit: existentialDeposit ?? "0",
|
5244
5277
|
networkId: chainId
|
5245
5278
|
};
|
@@ -5388,7 +5421,7 @@ const SubNativeModule = hydrate => {
|
|
5388
5421
|
const nonCurrentTokens = Object.keys(addressesByToken).filter(tokenId => !currentTokens.has(tokenId)).sort(sortChains);
|
5389
5422
|
|
5390
5423
|
// break nonCurrentTokens into chunks of POLLING_WINDOW_SIZE
|
5391
|
-
await PromisePool
|
5424
|
+
await PromisePool.withConcurrency(POLLING_WINDOW_SIZE).for(nonCurrentTokens).process(async nonCurrentTokenId => await poll({
|
5392
5425
|
[nonCurrentTokenId]: addressesByToken[nonCurrentTokenId]
|
5393
5426
|
}));
|
5394
5427
|
|
@@ -6632,7 +6665,6 @@ var psp22Abi = {
|
|
6632
6665
|
};
|
6633
6666
|
|
6634
6667
|
const moduleType$1 = "substrate-psp22";
|
6635
|
-
const subPsp22TokenId = (chainId, tokenSymbol) => `${chainId}-substrate-psp22-${tokenSymbol}`.toLowerCase().replace(/ /g, "-");
|
6636
6668
|
const SubPsp22Module = hydrate => {
|
6637
6669
|
const {
|
6638
6670
|
chainConnectors,
|
@@ -6642,16 +6674,14 @@ const SubPsp22Module = hydrate => {
|
|
6642
6674
|
assert(chainConnector, "This module requires a substrate chain connector");
|
6643
6675
|
return {
|
6644
6676
|
...DefaultBalanceModule(moduleType$1),
|
6645
|
-
async fetchSubstrateChainMeta(
|
6646
|
-
const isTestnet = (await chaindataProvider.chainById(chainId))?.isTestnet || false
|
6647
|
-
return {
|
6648
|
-
|
6649
|
-
};
|
6677
|
+
async fetchSubstrateChainMeta(_chainId) {
|
6678
|
+
// const isTestnet = (await chaindataProvider.chainById(chainId))?.isTestnet || false
|
6679
|
+
// return { isTestnet }
|
6680
|
+
return undefined;
|
6650
6681
|
},
|
6651
|
-
async fetchSubstrateChainTokens(chainId,
|
6652
|
-
const {
|
6653
|
-
|
6654
|
-
} = chainMeta;
|
6682
|
+
async fetchSubstrateChainTokens(chainId, _chainMeta, moduleConfig) {
|
6683
|
+
// const { isTestnet } = chainMeta
|
6684
|
+
|
6655
6685
|
const registry = new TypeRegistry();
|
6656
6686
|
const Psp22Abi = new Abi(psp22Abi);
|
6657
6687
|
|
@@ -6682,25 +6712,21 @@ const SubPsp22Module = hydrate => {
|
|
6682
6712
|
const decimalsData = decimalsResult.toJSON()?.result?.ok?.data;
|
6683
6713
|
decimals = typeof decimalsData === "string" && decimalsData.startsWith("0x") ? hexToNumber(decimalsData) : decimals;
|
6684
6714
|
})();
|
6685
|
-
const id = subPsp22TokenId(chainId,
|
6715
|
+
const id = subPsp22TokenId(chainId, contractAddress);
|
6686
6716
|
const token = {
|
6687
6717
|
id,
|
6688
6718
|
type: "substrate-psp22",
|
6689
6719
|
platform: "polkadot",
|
6690
|
-
isTestnet,
|
6720
|
+
// isTestnet,
|
6691
6721
|
isDefault: tokenConfig.isDefault ?? true,
|
6692
6722
|
symbol,
|
6693
6723
|
decimals,
|
6694
6724
|
name: tokenConfig?.name || symbol,
|
6695
|
-
logo: tokenConfig?.logo
|
6725
|
+
logo: tokenConfig?.logo,
|
6696
6726
|
existentialDeposit,
|
6697
6727
|
contractAddress,
|
6698
6728
|
networkId: chainId
|
6699
6729
|
};
|
6700
|
-
if (tokenConfig?.symbol) {
|
6701
|
-
token.symbol = tokenConfig?.symbol;
|
6702
|
-
token.id = subPsp22TokenId(chainId, token.symbol);
|
6703
|
-
}
|
6704
6730
|
if (tokenConfig?.coingeckoId) token.coingeckoId = tokenConfig?.coingeckoId;
|
6705
6731
|
if (tokenConfig?.mirrorOf) token.mirrorOf = tokenConfig?.mirrorOf;
|
6706
6732
|
tokens[token.id] = token;
|
@@ -6861,10 +6887,7 @@ const fetchBalances = async (chainConnector, tokens, addressesByToken) => {
|
|
6861
6887
|
source: "substrate-psp22",
|
6862
6888
|
status: "live",
|
6863
6889
|
address,
|
6864
|
-
|
6865
|
-
subChainId: token.networkId
|
6866
|
-
},
|
6867
|
-
chainId: token.networkId,
|
6890
|
+
networkId: token.networkId,
|
6868
6891
|
tokenId,
|
6869
6892
|
value: balance
|
6870
6893
|
};
|
@@ -6888,7 +6911,6 @@ const fetchBalances = async (chainConnector, tokens, addressesByToken) => {
|
|
6888
6911
|
|
6889
6912
|
const moduleType = "substrate-tokens";
|
6890
6913
|
const defaultPalletId = "Tokens";
|
6891
|
-
const subTokensTokenId = (chainId, onChainId) => `${chainId}-substrate-tokens-${compressToEncodedURIComponent(String(onChainId))}`;
|
6892
6914
|
const SubTokensModule = hydrate => {
|
6893
6915
|
const {
|
6894
6916
|
chainConnectors,
|
@@ -6899,14 +6921,8 @@ const SubTokensModule = hydrate => {
|
|
6899
6921
|
return {
|
6900
6922
|
...DefaultBalanceModule(moduleType),
|
6901
6923
|
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);
|
6924
|
+
if (metadataRpc === undefined) return {};
|
6925
|
+
if ((moduleConfig?.tokens ?? []).length < 1) return {};
|
6910
6926
|
const metadata = decAnyMetadata(metadataRpc);
|
6911
6927
|
const palletId = moduleConfig?.palletId ?? defaultPalletId;
|
6912
6928
|
compactMetadata(metadata, [{
|
@@ -6915,20 +6931,13 @@ const SubTokensModule = hydrate => {
|
|
6915
6931
|
}]);
|
6916
6932
|
const miniMetadata = encodeMetadata(metadata);
|
6917
6933
|
return palletId === defaultPalletId ? {
|
6918
|
-
|
6919
|
-
miniMetadata,
|
6920
|
-
metadataVersion
|
6934
|
+
miniMetadata
|
6921
6935
|
} : {
|
6922
|
-
isTestnet,
|
6923
6936
|
palletId,
|
6924
|
-
miniMetadata
|
6925
|
-
metadataVersion
|
6937
|
+
miniMetadata
|
6926
6938
|
};
|
6927
6939
|
},
|
6928
6940
|
async fetchSubstrateChainTokens(chainId, chainMeta, moduleConfig) {
|
6929
|
-
const {
|
6930
|
-
isTestnet
|
6931
|
-
} = chainMeta;
|
6932
6941
|
const tokens = {};
|
6933
6942
|
for (const tokenConfig of moduleConfig?.tokens ?? []) {
|
6934
6943
|
try {
|
@@ -6942,20 +6951,15 @@ const SubTokensModule = hydrate => {
|
|
6942
6951
|
id,
|
6943
6952
|
type: "substrate-tokens",
|
6944
6953
|
platform: "polkadot",
|
6945
|
-
isTestnet,
|
6946
6954
|
isDefault: tokenConfig.isDefault ?? true,
|
6947
6955
|
symbol,
|
6948
6956
|
decimals,
|
6949
6957
|
name: tokenConfig?.name ?? symbol,
|
6950
|
-
logo: tokenConfig?.logo
|
6958
|
+
logo: tokenConfig?.logo,
|
6951
6959
|
existentialDeposit,
|
6952
6960
|
onChainId,
|
6953
6961
|
networkId: chainId
|
6954
6962
|
};
|
6955
|
-
if (tokenConfig?.symbol) {
|
6956
|
-
token.symbol = tokenConfig?.symbol;
|
6957
|
-
token.id = subTokensTokenId(chainId, token.onChainId);
|
6958
|
-
}
|
6959
6963
|
if (tokenConfig?.coingeckoId) token.coingeckoId = tokenConfig?.coingeckoId;
|
6960
6964
|
if (tokenConfig?.mirrorOf) token.mirrorOf = tokenConfig?.mirrorOf;
|
6961
6965
|
tokens[token.id] = token;
|
@@ -7127,18 +7131,18 @@ async function buildQueries(chaindataProvider, addressesByToken) {
|
|
7127
7131
|
log.debug(`This module doesn't handle tokens of type ${token.type}`);
|
7128
7132
|
return [];
|
7129
7133
|
}
|
7130
|
-
const
|
7131
|
-
if (!
|
7134
|
+
const networkId = token.networkId;
|
7135
|
+
if (!networkId) {
|
7132
7136
|
log.warn(`Token ${tokenId} has no chain`);
|
7133
7137
|
return [];
|
7134
7138
|
}
|
7135
|
-
const chain = chains[
|
7139
|
+
const chain = chains[networkId];
|
7136
7140
|
if (!chain) {
|
7137
|
-
log.warn(`Chain ${
|
7141
|
+
log.warn(`Chain ${networkId} for token ${tokenId} not found`);
|
7138
7142
|
return [];
|
7139
7143
|
}
|
7140
7144
|
return addresses.flatMap(address => {
|
7141
|
-
const scaleCoder = chainStorageCoders.get(
|
7145
|
+
const scaleCoder = chainStorageCoders.get(networkId)?.storage;
|
7142
7146
|
const onChainId = (() => {
|
7143
7147
|
try {
|
7144
7148
|
return papiParse(token.onChainId);
|
@@ -7146,12 +7150,12 @@ async function buildQueries(chaindataProvider, addressesByToken) {
|
|
7146
7150
|
return token.onChainId;
|
7147
7151
|
}
|
7148
7152
|
})();
|
7149
|
-
const stateKey = encodeStateKey(scaleCoder, `Invalid address / token onChainId in ${
|
7153
|
+
const stateKey = encodeStateKey(scaleCoder, `Invalid address / token onChainId in ${networkId} storage query ${address} / ${token.onChainId}`, address, onChainId);
|
7150
7154
|
if (!stateKey) return [];
|
7151
7155
|
const decodeResult = change => {
|
7152
7156
|
/** NOTE: This type is only a hint for typescript, the chain can actually return whatever it wants to */
|
7153
7157
|
|
7154
|
-
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-tokens balance on chain ${
|
7158
|
+
const decoded = decodeScale(scaleCoder, change, `Failed to decode substrate-tokens balance on chain ${networkId}`) ?? {
|
7155
7159
|
free: 0n,
|
7156
7160
|
reserved: 0n,
|
7157
7161
|
frozen: 0n
|
@@ -7176,16 +7180,13 @@ async function buildQueries(chaindataProvider, addressesByToken) {
|
|
7176
7180
|
source: "substrate-tokens",
|
7177
7181
|
status: "live",
|
7178
7182
|
address,
|
7179
|
-
|
7180
|
-
subChainId: chainId
|
7181
|
-
},
|
7182
|
-
chainId,
|
7183
|
+
networkId,
|
7183
7184
|
tokenId: token.id,
|
7184
7185
|
values: balanceValues
|
7185
7186
|
};
|
7186
7187
|
};
|
7187
7188
|
return {
|
7188
|
-
chainId,
|
7189
|
+
chainId: networkId,
|
7189
7190
|
stateKey,
|
7190
7191
|
decodeResult
|
7191
7192
|
};
|
@@ -7198,7 +7199,7 @@ const defaultBalanceModules = [EvmErc20Module, EvmNativeModule, EvmUniswapV2Modu
|
|
7198
7199
|
/** Pulls the latest chaindata from https://github.com/TalismanSociety/chaindata */
|
7199
7200
|
const hydrateChaindataAndMiniMetadata = async (chaindataProvider, miniMetadataUpdater) => {
|
7200
7201
|
// need chains to be provisioned first, or substrate balances won't fetch on first subscription
|
7201
|
-
await chaindataProvider.
|
7202
|
+
await chaindataProvider.hydrate();
|
7202
7203
|
await Promise.all([miniMetadataUpdater.hydrateFromChaindata(), miniMetadataUpdater.hydrateCustomChains()]);
|
7203
7204
|
const chains = await chaindataProvider.chains();
|
7204
7205
|
const {
|
@@ -7216,9 +7217,9 @@ const updateCustomMiniMetadata = async (chaindataProvider, miniMetadataUpdater)
|
|
7216
7217
|
|
7217
7218
|
/** Fetches any missing Evm Tokens */
|
7218
7219
|
const updateEvmTokens = async (chaindataProvider, evmTokenFetcher) => {
|
7219
|
-
await chaindataProvider.
|
7220
|
+
await chaindataProvider.hydrate();
|
7220
7221
|
const evmNetworkIds = await chaindataProvider.evmNetworkIds();
|
7221
7222
|
await evmTokenFetcher.update(evmNetworkIds);
|
7222
7223
|
};
|
7223
7224
|
|
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,
|
7225
|
+
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 };
|