我试图创建一个react的基本集成示例,d3与jest测试。我已经创建了一个饼图和表格组件——我渴望将数据从主应用程序推送到表格和饼图组件中。只有当用户单击表格时,才会填充饼图。
--沙箱
https://codesandbox.io/s/react-d3-pie-chart-2-ezq6y?file=/src/index.js
-我想出了这个例子
6月9日——当前的整合。
数据看起来有点像这样
[
{
"Country": "Afghanistan",
"TotalConfirmed": 20917,
"TotalDeaths": 369,
"TotalRecovered": 2171,
},
{
"Country": "Albania",
"TotalConfirmed": 1263,
"TotalDeaths": 34,
"TotalRecovered": 945,
},
{
"Country": "Algeria",
"TotalConfirmed": 10265,
"TotalDeaths": 715,
"TotalRecovered": 6799,
}
]
-
我在重新分析道具上的数据时遇到了问题。我将不得不将饼图数据重构为标签、值格式——但我也不确定这方面的jest测试。
//应用程序。js
import React from 'react';
import Pie from './Pie/Pie';
import Table from './Table/Table';
import './App.css';
class App extends React.Component {
componentDidMount() {
//get data
}
render() {
const data = [
{
"Country": "Afghanistan",
"TotalConfirmed": 20917,
"TotalDeaths": 369,
"TotalRecovered": 2171,
},
{
"Country": "Albania",
"TotalConfirmed": 1263,
"TotalDeaths": 34,
"TotalRecovered": 945,
},
{
"Country": "Algeria",
"TotalConfirmed": 10265,
"TotalDeaths": 715,
"TotalRecovered": 6799,
}
];
const piedata =[
{
label: 'Jam',
value: 50,
},
{
label: 'Coconut',
value: 10,
},
{
label: 'Nutmeg',
value: 20,
},
{
label: 'Tumeric',
value: 20,
},
];
return (
<div className="App">
<div className="row">
<div className="col col-6">
<Table data={data} />
</div>
<div className="col col-6">
<Pie
data={piedata}
width="300"
height="300"
r="110"
ir="0"
/>
</div>
</div>
</div>
);
}
}
export default App;
//派。js
import React from 'react';
import * as d3 from "d3";
import ReactDOM from 'react-dom';
import $ from 'jquery';
import './Pie.css';
class Pie extends React.Component {
constructor(props) {
super(props);
this.myRef = React.createRef();
}
componentDidMount() {
var $this = $(this.myRef.current);
const data = this.props.data;
const width = parseInt(this.props.width,10),
height = parseInt(this.props.height,10),
radius = parseInt(this.props.r,10),
innerradius = parseInt(this.props.ir,10);
var color = d3.scaleOrdinal().range(["#f0cf85", "#e7f0c3", "#a4d4ae", "#32afa9"]);
var arc = d3.arc()
.outerRadius(radius - 10)
.innerRadius(innerradius);
data.forEach(function(d) {
d.total = +d.value;
});
var pie = d3.pie()
.sort(null)
.value(function(d) { return d.total; });
var svg = d3.select($this[0])
.append("svg")
.attr("width", width)
.attr("height", height)
.append("g")
.attr('class', 'piechart')
.attr("transform", "translate(" + width / 2 + "," + height / 2 + ")");
var segments = svg.append('g').attr('class', 'segments');
var slices = segments.selectAll(".arc")
.data(pie(data))
.enter().append("g")
.attr("class", "arc");
slices.append("path")
.attr("d", arc)
.attr('fill', function(d, i) {
return color(i);
})
}
render() {
return (
<div
ref={this.myRef}
className="Pie"
/>
);
}
}
export default Pie;
//桌子。js
import React from 'react';
import ReactDOM from 'react-dom';
import $ from 'jquery';
import './Table.css';
class Table extends React.Component {
constructor(props) {
super(props);
this.myRef = React.createRef();
}
componentDidMount() {
var $this = $(this.myRef.current);
}
rows(data) {
return (data.map((listValue, index) => {
return (
<tr key={index}>
<td>{listValue.Country}</td>
<td>{listValue.TotalConfirmed}</td>
<td>{listValue.TotalDeaths}</td>
<td>{listValue.TotalRecovered}</td>
</tr>
);
}));
}
render() {
return (
<div
ref={this.myRef}
className="Table"
>
<table>
<thead>
<tr>
{Object.keys(this.props.data[0]).map((key, index) => {
return (<th key={index}>{key}</th>);
})}
</tr>
</thead>
<tbody>
{this.rows(this.props.data)}
</tbody>
</table>
</div>
);
}
}
export default Table;
这些测试正确吗?
应用程序。测验js
import React from 'react';
import { shallow } from 'enzyme';
import App from './App';
import Table from './Table/Table';
import Pie from './Pie/Pie';
import allData from './data.json';
fetch = jest.fn().mockImplementation(() => {
const data = allData;
data.json = jest.fn().mockImplementation(() => Promise.resolve(data));
return Promise.resolve(data);
});
describe('App', () => {
const wrapper = shallow(<App />);
it('initial render', () => {
expect(wrapper.find(Table).prop('cols')).toHaveLength(4);
expect(wrapper.find(Pie).prop('data')).toEqual([
{
label: '',
value: 100,
},
]);
});
it('should update pie data when row is selected', () => {
const row = wrapper.state('data')[0];
const pieDataRefactor = wrapper.instance().pieDataRefactor(row);
console.log(pieDataRefactor);
wrapper.instance().rowSelected(row);
expect(wrapper.find(Pie).prop('data')).toEqual(pieDataRefactor);
});
});
桌子测验js
import React from 'react';
import Table from './Table';
import allData from '../data.json';
import { shallow } from 'enzyme';
const columns = [
'Country',
'CountryCode',
'Slug',
'NewConfirmed',
'TotalConfirmed',
'NewDeaths',
'TotalDeaths',
'NewRecovered',
'TotalRecovered',
'Date',
];
describe('Table', () => {
const defaultProps = {
cols: columns,
data: allData.Countries,
rowSelected: jest.fn(),
};
const wrapper = shallow(<Table {...defaultProps} />);
it('should render table', () => {
expect(wrapper.find('.Table th')).toHaveLength(10);
expect(wrapper.find('.Table tbody tr')).toHaveLength(allData.Countries.length);
});
it('should call rowSelected', () => {
const row = wrapper.find('.Table tbody tr').at(0);
row.simulate('click');
expect(defaultProps.rowSelected).toHaveBeenCalled();
expect(defaultProps.rowSelected).toHaveBeenCalledWith(allData.Countries[0]);
});
});
馅饼测验js
import React from 'react';
import Pie from './Pie';
import $ from 'jquery';
import * as d3 from 'd3';
import { mount } from 'enzyme';
describe('Pie', () => {
const defaultProps = {
data: [
{ label: 'TotalConfirmed', value: 20917 },
{ label: 'TotalDeaths', value: 369 },
{ label: 'TotalRecovered', value: 2171 },
],
height: 200,
width: 200,
r: 30,
ir: 10,
};
// const wrapper = mount(<Pie {...defaultProps} />);
it('should render Pie', () => {
const arcSpy = jest.spyOn(d3, 'arc');
const selectSpy = jest.spyOn(d3, 'select');
const scaleOrdinalSpy = jest.spyOn(d3, 'scaleOrdinal');
const pieSpy = jest.spyOn(d3, 'pie');
const wrapper = mount(<Pie {...defaultProps} />);
expect(wrapper.find('.Pie')).toHaveLength(1);
expect(arcSpy).toHaveBeenCalled();
expect(pieSpy).toHaveBeenCalled();
expect(selectSpy).toHaveBeenCalled();
expect(scaleOrdinalSpy).toHaveBeenCalled();
});
});