应该调用React Enzyme Jest错误jest.fn()

时间:2017-12-06 07:24:30

标签: javascript reactjs react-redux jestjs enzyme

我的组件如下

import React from 'react';
import { connect } from 'react-redux';
import { Button } from 'react-bootstrap';

import UserActions from '../../../actions/sampleUserAction';
import UserForm from '../../../views/sample/userForm';
import UsersList from '../../../views/sample/usersList';

@connect(store => ({
    users: store.sampleUserReducer.users,
}))

export default class UserComponent extends React.Component {
    constructor(props) {
        super(props);

        this.state = {
            displayForm: false,
            user: { id: '', fName: '', lName: '' },
            isCreationMode: true,
        };

        this.addNewUser = this.addNewUser.bind(this);
        this.handleChange = this.handleChange.bind(this);
        this.submitForm = this.submitForm.bind(this);
        this.editUser = this.editUser.bind(this);
        this.deleteUser = this.deleteUser.bind(this);
    }

    addNewUser() {
        this.setState({
            displayForm: !this.state.displayForm,
            isCreationMode: true,
            user: { id: '', fName: '', lName: '' },
        });
    }

    createUser(users) {
        users.push({
            id: users.length + 1,
            fName: this.state.user.fName,
            lName: this.state.user.lName,
        });
        return users;
    }

    updateUser(users) {
        users.forEach((user) => {
            if (user.id === this.state.user.id) {
                user.fName = this.state.user.fName;
                user.lName = this.state.user.lName;
            }
        });
        return users;
    }

    submitForm(e) {
        e.preventDefault();
        let { users } = this.props;

        if (this.state.isCreationMode) {
            users = this.createUser(users);
        } else if (!this.state.isCreationMode) {
            users = this.updateUser(users);
        }
        this.addNewUser();
        this.props.dispatch(UserActions.listUsers(users));
    }

    handleChange(e) {
        const { id } = this.state.user;
        let { fName, lName } = this.state.user;
        if (e.target.name === 'fName') {
            fName = e.target.value;
        }

        if (e.target.name === 'lName') {
            lName = e.target.value;
        }

        this.setState({ user: { id, fName, lName } });
    }

    editUser(e, id) {
        const { users } = this.props;
        let user = users.filter(obj => obj.id === id);
        user = user.length > 0 ? user[0] : null;
        if (user != null) {
            this.setState({
                displayForm: true,
                isCreationMode: false,
                user: { id: user.id, fName: user.fName, lName: user.lName },
            });
        }
    }

    deleteUser(e, id) {
        let { users } = this.props;
        users = users.filter(user => user.id !== id);
        this.props.dispatch(UserActions.listUsers(users));
    }

    render() {
        console.log(this.state.displayForm);
        return (
            <div className="container-fluid">
                <div className="well">
                    Sample Users App With Redux
                </div>
                <UserForm
                  displayForm={this.state.displayForm}
                  isCreationMode={this.state.isCreationMode}
                  submitForm={this.submitForm}
                  handleChange={this.handleChange}
                  user={this.state.user}
                  addNewUser={this.addNewUser}
                />
                <UsersList
                  users={this.props.users}
                  editUser={this.editUser}
                  deleteUser={this.deleteUser}
                />
                <div className="clearfix">
                    <Button bsStyle="primary" onClick={this.addNewUser}>Add User</Button>
                </div>
            </div>
        );
    }
}

和测试文件如下

import React from 'react';
import { createMockStore } from 'redux-test-utils';
import { shallowWithStore } from 'enzyme-redux';
import { Button } from 'react-bootstrap';

import UserComponent from '../../../../src/components/containers/sample/userComponent';
import UserForm from '../../../../src/views/sample/userForm';
import UsersList from '../../../../src/views/sample/usersList';


describe('UsersComponent', () => {
    let store;
    let container;
    const props = {
        submitForm: jest.fn(),
        addNewUser: jest.fn(),
    };

    beforeEach(() => {
        const defaultState = { sampleUserReducer: { users: [] } };
        store = createMockStore(defaultState);
        container = shallowWithStore(<UserComponent />, store);
    });

    it('should work', () => {
        expect(true).toEqual(true);
    });

    it('container should have UserForm component', () => {
        expect(container.dive().find(UserForm)).toHaveLength(1);
    });

    it('container should have UsersList component', () => {
        expect(container.dive().find(UsersList)).toHaveLength(1);
    });

    it('should have add new user button', () => {
        expect(container.dive().find(Button)).toHaveLength(1);
        expect(container.dive().find(Button).dive().text()).toEqual('Add User');
    });

    it('On click add user button', () => {
        container.dive().find(Button).simulate('click');
        expect(props.addNewUser).toHaveBeenCalled();
    });
});

我使用了jest,酶,酶-rexx。我是新的反应单元测试。最后一个测试用例给出了如下错误。反应版本是16.x.在上一个测试用例中,我尝试在按钮点击时调用模拟的jest函数。对于使用react-bootstrap内置Button组件的按钮

期望(jest.fn())。toHaveBeenCalled() 预期的模拟函数已被调用。

3 个答案:

答案 0 :(得分:0)

您可能需要添加<template> <div class="customInput"> <input v-model="value" type="text"> <label>First Name</label> <script> export default { name: 'CustomInput', data() { return { value: '', }; }, watch: { value: function(val, oldVal) { this.$emit('onChangeValue', this.value); } }, }; </script> ,这会在点击等外部输入后强制重新渲染。

http://airbnb.io/enzyme/docs/api/ShallowWrapper/update.html

答案 1 :(得分:0)

有时container.update()不起作用,在这种情况下,请单击container.instance().forceUpdate(),然后单击测试,以在状态更改后更新组件。

答案 2 :(得分:0)

另一种选择是使用玩笑的间谍来断言addNewUser被呼叫了。

const spy = jest.spyOn(container.instance(), 'addNewUser');
container.dive().find(Button).simulate('click');
expect(spy).toBeCalled();