Skip to content

Commit 745edaf

Browse files
michaelsbradleyjriurimatias
authored andcommitted
feat(@cockpit/explorer): implement pagination for accounts explorer
Display two accounts per page in the explorer overview. Display ten accounts per page in the accounts explorer page. Sort accounts by their api-supplied index numbers with the lowest index coming first. Change the `initBlockHeader` saga so that it triggers a re-fetch of accounts and therefore the "Tx Count" numbers of displayed accounts will reflect increased counts.
1 parent 5a502b3 commit 745edaf

File tree

5 files changed

+92
-12
lines changed

5 files changed

+92
-12
lines changed

packages/embark-ui/src/components/Accounts.js

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,17 +2,19 @@ import React from 'react';
22
import {Row, Col, Card, CardHeader, CardBody} from 'reactstrap';
33
import {Link} from 'react-router-dom';
44
import PropTypes from 'prop-types';
5+
import Pagination from './Pagination';
56

67
import CardTitleIdenticon from './CardTitleIdenticon';
78

8-
const Accounts = ({accounts}) => (
9+
const Accounts = ({accounts, changePage, currentPage, numberOfPages}) => (
910
<Row>
1011
<Col>
1112
<Card>
1213
<CardHeader>
1314
<h2>Accounts</h2>
1415
</CardHeader>
1516
<CardBody>
17+
{!accounts.length && "No accounts to display"}
1618
{accounts.map(account => (
1719
<div className="explorer-row border-top" key={account.address}>
1820
<CardTitleIdenticon id={account.address}>Account&nbsp;
@@ -34,14 +36,18 @@ const Accounts = ({accounts}) => (
3436
</Row>
3537
</div>
3638
))}
39+
{numberOfPages > 1 && <Pagination changePage={changePage} currentPage={currentPage} numberOfPages={numberOfPages}/>}
3740
</CardBody>
3841
</Card>
3942
</Col>
4043
</Row>
4144
);
4245

4346
Accounts.propTypes = {
44-
accounts: PropTypes.arrayOf(PropTypes.object)
47+
accounts: PropTypes.arrayOf(PropTypes.object),
48+
changePage: PropTypes.func,
49+
currentPage: PropTypes.number,
50+
numberOfPages: PropTypes.number
4551
};
4652

4753
export default Accounts;

packages/embark-ui/src/components/ExplorerDashboardLayout.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ const ExplorerDashboardLayout = () => (
1717
<div className="explorer-overview">
1818
<Row>
1919
<Col>
20-
<AccountsContainer overridePageHead={false} />
20+
<AccountsContainer numAccountsToDisplay={2} overridePageHead={false} />
2121
</Col>
2222
</Row>
2323
<Row>
Lines changed: 79 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,37 +1,105 @@
11
import React, {Component} from 'react';
22
import {connect} from 'react-redux';
33
import PropTypes from 'prop-types';
4-
5-
import {accounts as accountsAction} from '../actions';
4+
import {accounts as accountsAction,
5+
initBlockHeader,
6+
stopBlockHeader} from '../actions';
67
import Accounts from '../components/Accounts';
7-
import DataWrapper from "../components/DataWrapper";
88
import {getAccounts} from "../reducers/selectors";
99
import PageHead from "../components/PageHead";
1010

11+
const MAX_ACCOUNTS = 10;
12+
1113
class AccountsContainer extends Component {
14+
constructor(props) {
15+
super(props);
16+
17+
this.numAccountsToDisplay = this.props.numAccountsToDisplay || MAX_ACCOUNTS;
18+
this.state = {currentPage: 1};
19+
}
20+
1221
componentDidMount() {
1322
this.props.fetchAccounts();
23+
this.props.initBlockHeader();
24+
}
25+
26+
componentWillUnmount() {
27+
this.props.stopBlockHeader();
28+
}
29+
30+
get numberOfAccounts() {
31+
if (this._numberOfAccounts === undefined) {
32+
this._numberOfAccounts = this.props.accounts.length;
33+
}
34+
return this._numberOfAccounts;
35+
}
36+
37+
get numberOfPages() {
38+
if (this._numberOfPages === undefined) {
39+
this._numberOfPages = Math.ceil(
40+
this.numberOfAccounts / this.numAccountsToDisplay
41+
);
42+
}
43+
return this._numberOfPages;
44+
}
45+
46+
resetNums() {
47+
this._numberOfAccounts = undefined;
48+
this._numberOfPages = undefined;
49+
}
50+
51+
changePage(newPage) {
52+
if (newPage <= 0) {
53+
newPage = 1;
54+
} else if (newPage > this.numberOfPages) {
55+
newPage = this.numberOfPages;
56+
}
57+
this.setState({ currentPage: newPage });
58+
this.props.fetchAccounts();
59+
}
60+
61+
get currentAccounts() {
62+
return this.props.accounts
63+
.filter((account) => {
64+
const index = (
65+
(account.index + 1) -
66+
(this.numAccountsToDisplay * (this.state.currentPage - 1))
67+
);
68+
return index <= this.numAccountsToDisplay && index > 0;
69+
});
1470
}
1571

1672
render() {
73+
this.resetNums();
1774
return (
1875
<React.Fragment>
19-
<PageHead title="Accounts" enabled={this.props.overridePageHead} description="Summary view of the accounts configured for Embark" />
20-
<DataWrapper shouldRender={this.props.accounts.length > 0} {...this.props} render={({accounts}) => (
21-
<Accounts accounts={accounts} />
22-
)} />
76+
<PageHead
77+
title="Accounts"
78+
enabled={this.props.overridePageHead}
79+
description="Summary view of the accounts configured for Embark" />
80+
<Accounts accounts={this.currentAccounts}
81+
numberOfPages={this.numberOfPages}
82+
changePage={(newPage) => this.changePage(newPage)}
83+
currentPage={this.state.currentPage} />
2384
</React.Fragment>
2485
);
2586
}
2687
}
2788

2889
function mapStateToProps(state) {
29-
return {accounts: getAccounts(state), error: state.errorMessage, loading: state.loading};
90+
return {
91+
accounts: getAccounts(state),
92+
error: state.errorMessage,
93+
loading: state.loading
94+
};
3095
}
3196

3297
AccountsContainer.propTypes = {
3398
accounts: PropTypes.arrayOf(PropTypes.object),
3499
fetchAccounts: PropTypes.func,
100+
numAccountsToDisplay: PropTypes.number,
101+
initBlockHeader: PropTypes.func,
102+
stopBlockHeader: PropTypes.func,
35103
error: PropTypes.string,
36104
loading: PropTypes.bool,
37105
overridePageHead: PropTypes.bool
@@ -40,6 +108,8 @@ AccountsContainer.propTypes = {
40108
export default connect(
41109
mapStateToProps,
42110
{
43-
fetchAccounts: accountsAction.request
111+
fetchAccounts: accountsAction.request,
112+
initBlockHeader,
113+
stopBlockHeader
44114
},
45115
)(AccountsContainer);

packages/embark-ui/src/reducers/index.js

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,9 @@ const entitiesDefaultState = {
4141
};
4242

4343
const sorter = {
44+
accounts: function(a, b) {
45+
return a.index - b.index;
46+
},
4447
blocks: function(a, b) {
4548
return b.number - a.number;
4649
},

packages/embark-ui/src/sagas/index.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -420,6 +420,7 @@ export function *initBlockHeader() {
420420
channel.close();
421421
return;
422422
}
423+
yield put({type: actions.ACCOUNTS[actions.REQUEST]});
423424
yield put({type: actions.BLOCKS[actions.REQUEST]});
424425
yield put({type: actions.BLOCKS_FULL[actions.REQUEST], txObjects: true, txReceipts: true});
425426
yield put({type: actions.TRANSACTIONS[actions.REQUEST]});

0 commit comments

Comments
 (0)