使用Enzyme&Jest测试关于状态的IF语句不起作用

时间:2019-03-10 11:31:05

标签: reactjs jestjs enzyme

我正在尝试测试该方法,该方法负责编辑,但是能够用新标题和正文替换旧标题旧正文的行

它位于IF部分。下面是实现编辑的代码:

onEditNote = event => {
  const {
    target: { value: id }
  } = event;
  const obj = {
    title: this.state.title,
    body: this.state.body
  };

  // clear the errors while submitting

  this.setState({ titleError: "", bodyError: "" });

  if (obj.title === "") {
    this.setState({ titleError: "Title empty, please add title" });
  } else if (obj.body === "") {
    this.setState({ bodyError: "Body empty, please add body" });
  } else if (obj.title.length > 20) {
    this.setState({ titleError: "Title is too long." });
  } else {
    this.setState(state => {
      const list = state.notesArray.map(item => {
        if (item.id === id) {
          // eslint-disable-next-line no-param-reassign
          item.title = obj.title;
          // eslint-disable-next-line no-param-reassign
          item.body = obj.body;
        }
        return item;
      });

      localStorage.setItem("items", JSON.stringify(list));

      // eslint-disable-next-line no-undef
      $("#editModal").modal("close");
      this.onSuccessToast("Noted edited successfully.");
      return {
        list,
        title: "",
        body: ""
      };
    });
  }
};

这些是上面代码中的行,这些行未包含在我实现的测试中:

if (item.id === id) {
  // eslint-disable-next-line no-param-reassign
  item.title = obj.title;
  // eslint-disable-next-line no-param-reassign
  item.body = obj.body;
}

下面是我正在执行的测试,该测试没有涵盖IF语句,但我看到我已经涵盖了它:

it("should edit a Note.", () => {
  wrapper = shallow(<App />);
  $.fn.modal = jest.fn();
  wrapper.instance().onEditNote({ target: { value: "0" } });

  wrapper.instance().setState({
    title: "huxy 12",
    body: "hey huxy this is not great.",
    notesArray: [{ title: "hey", body: "its good", id: "0" }]
  });

  wrapper.instance().setState(state => {
    state.notesArray.map(item => {
      if (item.id === "0") {
        // eslint-disable-next-line no-param-reassign
        item.title = state.title;
        // eslint-disable-next-line no-param-reassign
        item.body = state.body;
      }
      return item;
    });
  });
});

我的考试中缺少什么?

编辑 这是我使用 Jest Matchers 编辑过的测试,无法正常工作。

it('should edit a Note.', () => {
    wrapper = shallow(<App />);
    $.fn.modal = jest.fn();
    wrapper.instance().onEditNote({ target: { value: '0' } });

    wrapper.instance().setState({
      title: 'huxy 12',
      body: 'hey huxy this is not great.',
      notesArray: [{ title: 'hey', body: 'its good', id: '0' }],
    });

    wrapper.instance().setState((state) => {
      state.notesArray.map((item) => {
        if (item.id === '0') {
          // eslint-disable-next-line no-param-reassign
          item.title = state.title;
          expect(item.title).toBe(state.title);
          expect(item.title).not.toBeNull();
          // eslint-disable-next-line no-param-reassign
          item.body = state.body;
        }
        return item;
      });
    });

    wrapper.instance().onEditNote({ target: { value: 0 } });
  });

这是完整状态:

constructor(props) {
    super(props, props, props);
    this.state = {
      notesArray: [],
      id: '',
      title: '',
      body: '',
      search: '',
      titleDisplay: '',
      bodyDisplay: '',
      titleError: '',
      bodyError: '',
    };
    this.onHandleSubmit = this.onHandleSubmit.bind(this);
    this.onHandleChange = this.onHandleChange.bind(this);
  }

2 个答案:

答案 0 :(得分:1)

不应将断言放在setState回调中。 setState应该在酶包装而不是实例上调用。分支机构应根据分支条件一一测试。

应该是这样的:

wrapper = shallow(<App />);
// mock $(...).modal and localStorage.setItem
wrapper.setState({ title: '' });
wrapper.instance().onEditNote({ target: { value: '0' } });
expect(wrapper.state.titleError).toEqual({ title: '', titleError: ... );

wrapper = shallow(<App />);
// mock $(...).modal and localStorage.setItem
wrapper.setState({ title: '' });
wrapper.instance().onEditNote({ target: { value: '0' } });
expect(wrapper.state.titleError).toEqual({ body '', bodyError: ... );

// etc.

一般不应该通过分配jest.fn()来嘲笑全局变量,因为这可能会阻止清理它们,模拟$(...).modal的一种更好的方法是jest.spy

localStorage.setItem也需要被模拟。

答案 1 :(得分:1)

I enhanced the following code  to test for 
const regex = /[^a-zA-Z0-9.\s-]+/;

接受逗号,-和BackSpace字符

stringGenerator = (length) => {
  let result = '';
  const characters = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789?:"}{}+,~&^$.\\||$3#@%&()';
  const charactersLength = characters.length;
  for (let i = 0; i < length; i += 1) {
    result += characters.charAt(Math.floor(Math.random() * charactersLength));
  }
  return result;
};

regex.test(stringGenerator(7))