簡體   English   中英

開玩笑/酶測試:this.props.showOverlay不是函數

[英]jest/enzyme test: this.props.showOverlay is not a function

我有一個模擬點擊的小型測試(希望對測試做更多的工作,但這是到目前為止的問題):

import React from 'react';
import Enzyme, { mount } from 'enzyme';
import Adapter from 'enzyme-adapter-react-16';
import HamburgerIcon from './HamburgerIcon';

Enzyme.configure({ adapter: new Adapter() });

test('hamburger icon changes class and state on click', () => {
  const wrapper = mount(<HamburgerIcon />);
  const hamburgerIcon = wrapper.find('div#mobile-nav');

  hamburgerIcon.simulate('click');
});

運行此測試時,出現錯誤:

TypeError:this.props.showOverlay不是一個函數

經過一番閱讀之后,我意識到這是行不通的,因為模擬的點擊會調用一個比正在測試的組件( HamburgerIcon )高兩級的函數。

當我第一次嘗試運行此函數時,我使用的是Enzyme的shallow ,后來我將其更改為mount以為這將使測試可以訪問showOverlay函數,但我錯了。

然后我讀到,這可能是一個模擬函數的好用例,並且我嘗試着開始實現這一點:

...

const showOverlay = jest.fn();
// how to set this.props.ShowOverlay to the const above??

test('has div with class .closed', () => {
  const wrapper = mount(<HamburgerIcon />);
  const hamburgerIcon = wrapper.find('div#mobile-nav');

  hamburgerIcon.simulate('click');
});

這就是我迷失的地方-我不確定模擬函數在這里是否是正確的方向,我也不確定設置模擬函數的語法將如何工作。

如果只是對單個組件進行單元測試,請繼續shallow 如果該組件是嵌套的,並且您正在針對子節點進行測試,則將mount父組件。

就是說,您在使用模擬功能的正確道路上。 只需將其傳遞到組件中即可,如下所示:

<HamburgerIcon showOverlay={showOverlay} />

例如:

const showOverlay = jest.fn();

test('shows an overlay', () => {
  const wrapper = mount(<HamburgerIcon showOverlay={showOverlay} />);
  const hamburgerIcon = wrapper.find('div#mobile-nav');

  hamburgerIcon.simulate('click');
  expect(showOverlay).toHaveBeenCalled();
});

如果您有多個道具,那么我想做一些更具說明性的事情:

// define props here if you want an easy way check if they've been 
// called (since we're defining at the top-level, all tests have access
// to this function)
const showOverlay = jest.fn();

// then include them in an "initialProps" object (you can also just define
// them within this object as well, but you'll have to use 
// "initialProps.nameOfFunction" to check if they're called -- kind of 
// repetitive if you have a lot of props that you're checking against)
const initialProps = {
  showOverlay,
  someOtherFunction: jest.fn()
}

// use the spread syntax to pass all the props in the "initialProps" object
// to the component
test('shows an overlay', () => {
  const wrapper = mount(<HamburgerIcon { ...initialProps } />);
  const hamburgerIcon = wrapper.find('div#mobile-nav');

  hamburgerIcon.simulate('click');

  expect(showOverlay).toHaveBeenCalled(); // here we can just use the mock function name
  expect(initialProps.someOtherFunction).toHaveBeenCalledTimes(0); // here we'll have to use "initialProps.property" because it has been scoped to the object
});

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM