Update AccountCard for re-use (#4350)

* Tags handle empty values

* Export AccountCard in ~/ui

* Allow ETH-only & zero display

* Use ui/Balance for balance display

* Add tests for Balance & Tags component availability

* Add className, optional handlers only

* Remove debug logging

* AccountCard UI update
This commit is contained in:
Jaco Greeff
2017-01-31 12:21:50 +01:00
committed by GitHub
parent ee906467ad
commit 223c474487
7 changed files with 234 additions and 81 deletions

View File

@@ -16,31 +16,46 @@
import BigNumber from 'bignumber.js';
import React, { Component, PropTypes } from 'react';
import { FormattedMessage } from 'react-intl';
import { connect } from 'react-redux';
import unknownImage from '../../../assets/images/contracts/unknown-64x64.png';
import unknownImage from '~/../assets/images/contracts/unknown-64x64.png';
import styles from './balance.css';
class Balance extends Component {
static contextTypes = {
api: PropTypes.object
}
};
static propTypes = {
balance: PropTypes.object,
images: PropTypes.object.isRequired
}
className: PropTypes.string,
images: PropTypes.object.isRequired,
showOnlyEth: PropTypes.bool,
showZeroValues: PropTypes.bool
};
static defaultProps = {
showOnlyEth: false,
showZeroValues: false
};
render () {
const { api } = this.context;
const { balance, images } = this.props;
const { balance, className, images, showZeroValues, showOnlyEth } = this.props;
if (!balance) {
if (!balance || !balance.tokens) {
return null;
}
let body = (balance.tokens || [])
.filter((balance) => new BigNumber(balance.value).gt(0))
let body = balance.tokens
.filter((balance) => {
const hasBalance = showZeroValues || new BigNumber(balance.value).gt(0);
const isValidToken = !showOnlyEth || (balance.token.tag || '').toLowerCase() === 'eth';
return hasBalance && isValidToken;
})
.map((balance, index) => {
const token = balance.token;
@@ -95,13 +110,16 @@ class Balance extends Component {
if (!body.length) {
body = (
<div className={ styles.empty }>
There are no balances associated with this account
<FormattedMessage
id='ui.balance.none'
defaultMessage='There are no balances associated with this account'
/>
</div>
);
}
return (
<div className={ styles.balances }>
<div className={ [styles.balances, className].join(' ') }>
{ body }
</div>
);

View File

@@ -0,0 +1,122 @@
// Copyright 2015-2017 Parity Technologies (UK) Ltd.
// This file is part of Parity.
// Parity is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
// Parity is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
// You should have received a copy of the GNU General Public License
// along with Parity. If not, see <http://www.gnu.org/licenses/>.
import { shallow } from 'enzyme';
import React from 'react';
import sinon from 'sinon';
import apiutil from '~/api/util';
import Balance from './';
const BALANCE = {
tokens: [
{ value: '122', token: { tag: 'ETH' } },
{ value: '345', token: { tag: 'GAV', format: 1 } },
{ value: '0', token: { tag: 'TST', format: 1 } }
]
};
let api;
let component;
let store;
function createApi () {
api = {
dappsUrl: 'http://testDapps:1234/',
util: apiutil
};
return api;
}
function createStore () {
store = {
dispatch: sinon.stub(),
subscribe: sinon.stub(),
getState: () => {
return {
images: {}
};
}
};
return store;
}
function render (props = {}) {
if (!props.balance) {
props.balance = BALANCE;
}
component = shallow(
<Balance
className='testClass'
{ ...props }
/>,
{
context: {
store: createStore()
}
}
).find('Balance').shallow({ context: { api: createApi() } });
return component;
}
describe('ui/Balance', () => {
beforeEach(() => {
render();
});
it('renders defaults', () => {
expect(component).to.be.ok;
});
it('passes the specified className', () => {
expect(component.hasClass('testClass')).to.be.true;
});
it('renders all the non-zero balances', () => {
expect(component.find('img')).to.have.length(2);
});
describe('render specifiers', () => {
it('renders only the single token with showOnlyEth', () => {
render({ showOnlyEth: true });
expect(component.find('img')).to.have.length(1);
});
it('renders all the tokens with showZeroValues', () => {
render({ showZeroValues: true });
expect(component.find('img')).to.have.length(3);
});
it('shows ETH with zero value with showOnlyEth & showZeroValues', () => {
render({
showOnlyEth: true,
showZeroValues: true,
balance: {
tokens: [
{ value: '0', token: { tag: 'ETH' } },
{ value: '345', token: { tag: 'GAV', format: 1 } }
]
}
});
expect(component.find('img')).to.have.length(1);
});
});
});