haoxins / react-flatpickr

flatpickr for React
MIT License
598 stars 102 forks source link

Issues testing with Jest and Enzyme #92

Closed EpsApps closed 2 years ago

EpsApps commented 5 years ago

I'm having issues testing this component with Jest and Enzyme.

When I find DateTimePicker and run debug(), this is the output: <DateTimePicker options={{...}} value={{...}} onChange={[Function]} onDayCreate={[Function]}><input defaultValue={[undefined]} /></DateTimePicker>

DateTimePicker is mounted as a child of a component I've build that I'm using mount() with.

After researching I think the problem could be that while the flatpickr is being inserted into the dom, it is not being inserted into the virtual dom.

These are the dependencies in the project, although I've used your latest version and the problem persisted: "dependencies": { "@babel/runtime": "^7.4.3", "await-delay": "1.0.0", "bowser": "^1.9.3", "core-js": "2.5.3", "express": "^4.16.2", "flatpickr": "4.3.2", "jest-dom": "^1.11.0", "lodash": "4.17.5", "material-ui": "0.19.4", "material-ui-next": "@material-ui/core", "moment-timezone": "0.5.14", "node-sass-chokidar": "1.2.2", "npm-run-all": "4.1.3", "rc-slider": "8.6.0", "react": "16.2.0", "react-block-ui": "1.1.1", "react-breadcrumbs-dynamic": "1.0.13", "react-color": "^2.17.0", "react-datepicker": "^2.0.0", "react-dual-listbox": "1.3.2", "react-measure": "2.0.2", "react-rangeslider": "2.2.0", "react-router": "4.2.0", "react-router-redux": "4.0.8", "react-slick": "^0.23.1", "react-test-renderer": "^16.4.2", "react-title-component": "1.0.1", "react-tooltip": "3.4.0", "recharts": "1.0.0-beta.10", "redux-form": "7.2.3", "redux-local": "0.1.3", "slick-carousel": "^1.8.1", "source-map-explorer": "1.5.0", "uuid": "3.2.1", "validate.js": "^0.12.0", "vega": "4.0.0", "vega-tooltip": "0.5.1", "vega-view": "2.2.0", "with-query": "1.0.2" }, "devDependencies": { "@storybook/addon-actions": "^3.2.13", "@storybook/addon-centered": "^3.2.13", "@storybook/addon-events": "^3.2.13", "@storybook/addon-info": "^3.2.13", "@storybook/addon-knobs": "^3.2.13", "@storybook/addon-links": "^3.2.13", "@storybook/addon-notes": "^3.2.13", "@storybook/addon-options": "^3.2.13", "@storybook/addons": "^3.2.13", "@storybook/react": "^3.2.13", "babel-eslint": "^8.0.1", "babel-plugin-transform-decorators-legacy": "^1.3.4", "babel-preset-es2015": "^6.24.1", "babel-preset-react": "^6.24.1", "babel-preset-stage-0": "^6.24.1", "cross-env": "^5.1.1", "d3": "^4.11.0", "enzyme": "^3.3.0", "enzyme-adapter-react-16": "^1.1.1", "eslint-plugin-flowtype": "^2.39.1", "eslint-plugin-import": "^2.8.0", "eslint-plugin-jsx-a11y": "^6.0.2", "flexbox-react": "^4.4.0", "history": "^4.7.2", "http-proxy-middleware": "^0.17.4", "jest": "^21.2.1", "jmespath": "^0.15.0", "moment": "^2.19.1", "raf": "^3.4.0", "react-big-calendar": "0.18.0", "react-c3js": "0.1.20", "react-cookie": "2.1.2", "react-dom": "16.2.0", "react-fa": "5.0.0", "react-flatpickr": "3.6.3", "react-flexbox-grid": "1.1.5", "react-redux": "5.0.7", "react-router-dom": "4.2.2", "react-scripts": "1.1.1", "react-styled-flexboxgrid": "2.2.0", "react-swipeable-views": "0.12.12", "react-toastify": "2.2.2", "react-ultimate-pagination": "1.2.0", "redux": "3.7.2", "redux-auth-wrapper": "2.0.2", "redux-devtools": "3.4.1", "redux-devtools-dock-monitor": "1.1.3", "redux-devtools-extension": "2.13.2", "redux-devtools-log-monitor": "1.4.0", "redux-mock-store": "1.5.1", "redux-thunk": "2.2.0", "storybook-addon-material-ui": "^0.8.2", "styled-components": "^2.2.1", "universal-cookie": "^2.1.0" },

Thanks!

EmmaB commented 4 years ago

We're also unable to test the onChange event using Jest and React DOM testing library. Here's some of a failing test, showing our general approach:

    const onChange = jest.fn()

    const { getByText, getByLabelText } = renderComponent({ onChange })

    fireEvent.click(getByLabelText("Valid from"))
    userEvent.type(getByLabelText("Valid from"), "today")
    // fireEvent.click(getByText("12")) // this doesn't work either, though the datepicker is in document.body at this stage
    fireEvent.keyDown(getByLabelText("Valid from"), { key: "Enter", code: 13, charCode: 13 })

    await wait() // for superstitious reasons

    expect(getByLabelText("Valid from").value).toBe("13 Dec 2019")
    expect(onChange).toHaveBeenCalled() 
craig-jennings commented 4 years ago

I think I found a way to trigger a date select, here's a snippet of my code:

const onChange = jest.fn();

const { getByLabelText } = render(<DateTimePicker value={new Date('01/01/1970')} onChange={onChange} />);

fireEvent.mouseDown(getByLabelText('01/05/1970'), { which: 1 }); // 'which' is important here

jest.runAllTimers(); // Required to fast-forward all setTimeouts, etc.

expect(onChange).toHaveBeenCalledTimes(1);
sashahavia commented 3 years ago

This has worked for me

const { queryByTestId, getByLabelText } = render(<MyComponent {...props} />);
const date = new Date();
fireEvent.keyDown(queryByTestId('date-pickr-input'), { key: 'Enter', code: 13, charCode: 13 });
fireEvent.click(getByLabelText(moment(date).format('LL')));

expect(props.myFunction).toHaveBeenCalled();