Extract getHistory query (re-use) (#1877)

This commit is contained in:
Jaco Greeff 2019-11-13 15:34:31 +01:00 committed by GitHub
parent fd8427d3b5
commit 5e19af9810
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 80 additions and 36 deletions

View File

@ -3,12 +3,13 @@
// of the Apache-2.0 license. See the LICENSE file for details.
import { I18nProps } from '@polkadot/react-components/types';
import { BlockNumber, Exposure, Hash, SessionIndex } from '@polkadot/types/interfaces';
import { BlockNumber, Exposure, SessionIndex } from '@polkadot/types/interfaces';
import BN from 'bn.js';
import React, { useContext, useEffect, useState } from 'react';
import { Chart, Columar, Column } from '@polkadot/react-components';
import { ApiContext, withCalls } from '@polkadot/react-api';
import { getHistoric } from '@polkadot/react-api/util';
import { formatBalance, formatNumber } from '@polkadot/util';
import translate from '../translate';
@ -47,42 +48,23 @@ function Validator ({ blockCounts, className, currentIndex, startNumber, t, vali
const [stakeChart, setStateChart] = useState<LineData | undefined>();
useEffect((): void => {
const numbers: BN[] = [];
const checkLength = (api.consts.babe
? api.consts.babe.epochDuration as BlockNumber
: new BN(500)).muln(2).divn(3);
const divisor = new BN('1'.padEnd(formatBalance.getDefaults().decimals + 1, '0'));
api.isReady.then(async (): Promise<void> => {
const divisor = new BN('1'.padEnd(formatBalance.getDefaults().decimals + 1, '0'));
const values = await getHistoric<Exposure>(api, 'staking.stakers', [validatorId], {
interval: (api.consts.babe?.epochDuration as BlockNumber || new BN(500)).muln(2).divn(3),
max: SESSIONS,
startNumber
});
api.isReady.then((): void => {
let currentNumber: BN = startNumber;
// here we end up with more-or-less 6.66 days
while (startNumber.gtn(0) && numbers.length < SESSIONS) {
numbers.unshift(currentNumber);
currentNumber = currentNumber.sub(checkLength);
}
setStakeLabels(numbers.map((bn): string => formatNumber(bn)));
Promise
.all(numbers.map((at): Promise<Hash> =>
api.rpc.chain.getBlockHash(at as any)
))
.then((hashes): Promise<Exposure[]> =>
Promise.all(hashes.map((hash): Promise<Exposure> =>
api.query.staking.stakers.at(hash, validatorId) as Promise<Exposure>
))
)
.then((exposures): void => {
setStateChart([
exposures.map(({ total }): BN =>
total.unwrap().div(divisor))
// exposures.map(({ own }): BN =>
// own.unwrap().div(divisor)),
// exposures.map(({ others }): BN =>
// others.reduce((total, { value }): BN => total.add(value.unwrap()), new BN(0)).div(divisor))
]);
});
setStakeLabels(values.map(([bn]): string => formatNumber(bn)));
setStateChart([
values.map(([,, { total }]): BN =>
total.unwrap().div(divisor))
// exposures.map(({ own }): BN =>
// own.unwrap().div(divisor)),
// exposures.map(({ others }): BN =>
// others.reduce((total, { value }): BN => total.add(value.unwrap()), new BN(0)).div(divisor))
]);
});
}, []);

View File

@ -0,0 +1,33 @@
// Copyright 2017-2019 @polkadot/react-api authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import { Hash } from '@polkadot/types/interfaces';
import BN from 'bn.js';
import ApiPromise from '@polkadot/api/promise';
import { bnToBn } from '@polkadot/util';
export interface HashesOptions {
interval: BN | number;
max: number;
startNumber: BN;
}
export default async function getHashes (api: ApiPromise, { interval, max, startNumber }: HashesOptions): Promise<[BN, Hash][]> {
const numbers: BN[] = [];
const _interval = bnToBn(interval);
let currentNumber: BN = startNumber;
while (numbers.length < max && currentNumber.gtn(0)) {
numbers.unshift(currentNumber);
currentNumber = currentNumber.sub(_interval);
}
const hashes = await Promise.all(
numbers.map((at): Promise<Hash> => api.rpc.chain.getBlockHash(at as any))
);
return numbers.map((bn, index): [BN, Hash] => [bn, hashes[index]]);
}

View File

@ -0,0 +1,25 @@
// Copyright 2017-2019 @polkadot/react-api authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import { Hash } from '@polkadot/types/interfaces';
import { Codec } from '@polkadot/types/types';
import BN from 'bn.js';
import ApiPromise from '@polkadot/api/promise';
import getHashes, { HashesOptions } from './hashes';
export default async function getHistory <T extends Codec> (api: ApiPromise, endpoint: string, params: any[], options: HashesOptions): Promise<[BN, Hash, T][]> {
const [mod, fn] = endpoint.split('.');
const numbers = await getHashes(api, options);
const results = await Promise.all(numbers.map(([, hash]): Promise<T> =>
api.query[mod][fn].at(hash, ...params) as Promise<T>
));
return results.map((value, index): [BN, Hash, T] => [
numbers[index][0],
numbers[index][1],
value
]);
}

View File

@ -2,11 +2,15 @@
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import getHashes from './hashes';
import getHistoric from './historic';
import intervalObservable from './intervalObservable';
import isEqual from './isEqual';
import triggerChange from './triggerChange';
export {
getHashes,
getHistoric,
intervalObservable,
isEqual,
triggerChange