From 927c1d02f92e1b95daede7b87822901be8f95a18 Mon Sep 17 00:00:00 2001 From: Jaco Greeff Date: Wed, 15 Jul 2020 16:11:21 +0200 Subject: [PATCH] Flatten recurring events (same block) (#3201) * Flattn recurring events (same block) * Same-height event filter * Display adjust * Filter {balances, treasury}.Deposit --- .../page-explorer/src/BlockInfo/ByHash.tsx | 3 +- .../page-explorer/src/BlockInfo/Extrinsic.tsx | 2 +- .../src/BlockInfo/Extrinsics.tsx | 2 +- packages/page-explorer/src/Events.tsx | 36 ++++++++--------- packages/page-explorer/src/Main.tsx | 2 +- packages/page-explorer/src/index.tsx | 2 +- packages/react-query/src/BlockAuthors.tsx | 4 +- packages/react-query/src/Events.tsx | 40 ++++++++++--------- .../src/types.ts | 15 ++++--- 9 files changed, 55 insertions(+), 51 deletions(-) rename packages/{page-explorer => react-query}/src/types.ts (62%) diff --git a/packages/page-explorer/src/BlockInfo/ByHash.tsx b/packages/page-explorer/src/BlockInfo/ByHash.tsx index 268c237707..c511169bd0 100644 --- a/packages/page-explorer/src/BlockInfo/ByHash.tsx +++ b/packages/page-explorer/src/BlockInfo/ByHash.tsx @@ -3,7 +3,7 @@ // of the Apache-2.0 license. See the LICENSE file for details. import { EventRecord, SignedBlock } from '@polkadot/types/interfaces'; -import { KeyedEvent } from '../types'; +import { KeyedEvent } from '@polkadot/react-query/types'; import React from 'react'; import { Link } from 'react-router-dom'; @@ -29,6 +29,7 @@ function BlockByHash ({ className = '', value }: Props): React.ReactElement events.map((record, index) => ({ + indexes: [index], key: `${Date.now()}-${index}-${record.hash.toHex()}`, record })) diff --git a/packages/page-explorer/src/BlockInfo/Extrinsic.tsx b/packages/page-explorer/src/BlockInfo/Extrinsic.tsx index b4e00d6636..ec9ff9f761 100644 --- a/packages/page-explorer/src/BlockInfo/Extrinsic.tsx +++ b/packages/page-explorer/src/BlockInfo/Extrinsic.tsx @@ -3,7 +3,7 @@ // of the Apache-2.0 license. See the LICENSE file for details. import { BlockNumber, Extrinsic } from '@polkadot/types/interfaces'; -import { KeyedEvent } from '../types'; +import { KeyedEvent } from '@polkadot/react-query/types'; import React from 'react'; import styled from 'styled-components'; diff --git a/packages/page-explorer/src/BlockInfo/Extrinsics.tsx b/packages/page-explorer/src/BlockInfo/Extrinsics.tsx index c43ae5f518..2e1f3457bc 100644 --- a/packages/page-explorer/src/BlockInfo/Extrinsics.tsx +++ b/packages/page-explorer/src/BlockInfo/Extrinsics.tsx @@ -3,7 +3,7 @@ // of the Apache-2.0 license. See the LICENSE file for details. import { BlockNumber, Extrinsic } from '@polkadot/types/interfaces'; -import { KeyedEvent } from '../types'; +import { KeyedEvent } from '@polkadot/react-query/types'; import React, { useMemo } from 'react'; import { Table } from '@polkadot/react-components'; diff --git a/packages/page-explorer/src/Events.tsx b/packages/page-explorer/src/Events.tsx index ec0ffc2a0f..646fbd21ec 100644 --- a/packages/page-explorer/src/Events.tsx +++ b/packages/page-explorer/src/Events.tsx @@ -2,7 +2,7 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import { KeyedEvent } from './types'; +import { KeyedEvent } from '@polkadot/react-query/types'; import React, { useMemo } from 'react'; import { Link } from 'react-router-dom'; @@ -34,24 +34,22 @@ function Events ({ className = '', emptyLabel, eventClassName, events, label }: empty={emptyLabel || t('No events available')} header={header} > - {events && events - .filter(({ record: { event: { method, section } } }) => !!method && !!section) - .map(({ blockHash, blockNumber, index, key, record }): React.ReactNode => ( - - - - {blockNumber && ( - {formatNumber(blockNumber)}-{index} - )} - - - )) - } + {events && events.map(({ blockHash, blockNumber, indexes, key, record }): React.ReactNode => ( + + + + {blockNumber && ( +
+ {indexes.length !== 1 && ({formatNumber(indexes.length)}x) } + {formatNumber(blockNumber)}-{indexes[0]} +
+ )} + + + ))} ); } diff --git a/packages/page-explorer/src/Main.tsx b/packages/page-explorer/src/Main.tsx index e7737b0137..91d5330b54 100644 --- a/packages/page-explorer/src/Main.tsx +++ b/packages/page-explorer/src/Main.tsx @@ -2,7 +2,7 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import { KeyedEvent } from './types'; +import { KeyedEvent } from '@polkadot/react-query/types'; import React from 'react'; import { HeaderExtended } from '@polkadot/api-derive'; diff --git a/packages/page-explorer/src/index.tsx b/packages/page-explorer/src/index.tsx index 4fee999fa9..101459118a 100644 --- a/packages/page-explorer/src/index.tsx +++ b/packages/page-explorer/src/index.tsx @@ -2,7 +2,7 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import { KeyedEvent } from './types'; +import { KeyedEvent } from '@polkadot/react-query/types'; import React, { useContext, useMemo } from 'react'; import { Route, Switch } from 'react-router'; diff --git a/packages/react-query/src/BlockAuthors.tsx b/packages/react-query/src/BlockAuthors.tsx index 1f930c2fa2..579591ca21 100644 --- a/packages/react-query/src/BlockAuthors.tsx +++ b/packages/react-query/src/BlockAuthors.tsx @@ -22,7 +22,7 @@ interface Props { children: React.ReactNode; } -const MAX_HEADERS = 50; +const MAX_HEADERS = 75; const byAuthor: Record = {}; const eraPoints: Record = {}; @@ -66,7 +66,7 @@ function BlockAuthorsBase ({ children }: Props): React.ReactElement { } lastHeaders = lastHeaders - .filter((old, index): boolean => index < MAX_HEADERS && old.number.unwrap().lt(blockNumber)) + .filter((old, index) => index < MAX_HEADERS && old.number.unwrap().lt(blockNumber)) .reduce((next, header): HeaderExtended[] => { next.push(header); diff --git a/packages/react-query/src/Events.tsx b/packages/react-query/src/Events.tsx index 76e99bb020..bb08b7e63a 100644 --- a/packages/react-query/src/Events.tsx +++ b/packages/react-query/src/Events.tsx @@ -2,31 +2,20 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import { BlockNumber, EventRecord } from '@polkadot/types/interfaces'; +import { IndexedEvent, KeyedEvent } from './types'; import React, { useEffect, useState } from 'react'; import { useApi } from '@polkadot/react-hooks'; import { stringToU8a } from '@polkadot/util'; import { xxhashAsHex } from '@polkadot/util-crypto'; -interface IndexedEvent { - index: number; - record: EventRecord; -} - -interface KeyedEvent extends IndexedEvent { - blockHash: string; - blockNumber: BlockNumber; - key: string; -} - type Events = KeyedEvent[]; interface Props { children: React.ReactNode; } -const MAX_EVENTS = 50; +const MAX_EVENTS = 75; const EventsContext: React.Context = React.createContext([]); @@ -42,8 +31,20 @@ function EventsBase ({ children }: Props): React.ReactElement { api.query.system.events((records): void => { const newEvents: IndexedEvent[] = records - .map((record, index) => ({ index, record })) - .filter(({ record: { event: { section } } }) => section !== 'system'); + .map((record, index) => ({ indexes: [index], record })) + .filter(({ record: { event: { method, section } } }) => section !== 'system' && (method !== 'Deposit' || !['balances', 'treasury'].includes(section))) + .reduce((combined: IndexedEvent[], e): IndexedEvent[] => { + const prev = combined.find(({ record: { event: { method, section } } }) => e.record.event.section === section && e.record.event.method === method); + + if (prev) { + prev.indexes.push(...e.indexes); + } else { + combined.push(e); + } + + return combined; + }, []) + .reverse(); const newEventHash = xxhashAsHex(stringToU8a(JSON.stringify(newEvents))); if (newEventHash !== prevEventHash && newEvents.length) { @@ -58,14 +59,15 @@ function EventsBase ({ children }: Props): React.ReactElement { prevBlockHash = blockHash; setState((events) => [ - ...newEvents.map(({ index, record }): KeyedEvent => ({ + ...newEvents.map(({ indexes, record }): KeyedEvent => ({ blockHash, blockNumber, - index, - key: `${blockNumber.toNumber()}-${blockHash}-${index}`, + indexes, + key: `${blockNumber.toNumber()}-${blockHash}-${indexes.join('.')}`, record })), - ...events + // remove all events for the previous same-height blockNumber + ...events.filter((p) => !p.blockNumber?.eq(blockNumber)) ].slice(0, MAX_EVENTS)); } }).catch(console.error); diff --git a/packages/page-explorer/src/types.ts b/packages/react-query/src/types.ts similarity index 62% rename from packages/page-explorer/src/types.ts rename to packages/react-query/src/types.ts index 3358d5aac4..686dc1041e 100644 --- a/packages/page-explorer/src/types.ts +++ b/packages/react-query/src/types.ts @@ -1,13 +1,16 @@ -// Copyright 2017-2020 @polkadot/app-explorer authors & contributors +// Copyright 2017-2020 @polkadot/react-query 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 { BlockNumber, EventRecord } from '@polkadot/types/interfaces'; -export interface KeyedEvent { - blockHash?: string; - blockNumber?: BlockNumber; - index?: number; - key: string; +export interface IndexedEvent { + indexes: number[]; record: EventRecord; } + +export interface KeyedEvent extends IndexedEvent { + blockHash?: string; + blockNumber?: BlockNumber; + key: string; +}