├── .babelrc ├── .gitignore ├── README.md ├── __mocks__ └── react-transition-group.js ├── package.json └── src ├── __tests__ ├── mock-example.js ├── mock.js ├── shallow-example.js └── shallow.js └── hidden-message.js /.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": ["babel-preset-react", "babel-preset-env"], 3 | "plugins": ["babel-plugin-transform-class-properties"] 4 | } 5 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Shallow rendering vs Jest Mocking 2 | 3 | I used this in 4 | [a DevTipsWithKent video](https://www.youtube.com/watch?v=LHUdxkThTM0&list=PLV5CVI1eNcJgCrPH_e6d57KRUTiDZgs0u). 5 | -------------------------------------------------------------------------------- /__mocks__/react-transition-group.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | CSSTransition: jest.fn(({children, in: show}) => (show ? children : null)) 3 | } 4 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "shallow-to-mock", 3 | "version": "1.0.0", 4 | "description": "Example of migrating from shallow rendering to a mock", 5 | "main": "index.js", 6 | "dependencies": { 7 | "react": "^16.4.1", 8 | "react-dom": "^16.4.1", 9 | "react-transition-group": "^2.4.0" 10 | }, 11 | "devDependencies": { 12 | "babel-core": "^6.26.3", 13 | "babel-plugin-transform-class-properties": "^6.24.1", 14 | "babel-preset-env": "^1.7.0", 15 | "babel-preset-react": "^6.24.1", 16 | "enzyme": "^3.3.0", 17 | "enzyme-adapter-react-16": "^1.1.1", 18 | "jest": "^23.2.0", 19 | "react-testing-library": "^4.0.2" 20 | }, 21 | "scripts": { 22 | "test": "jest" 23 | }, 24 | "keywords": [], 25 | "author": "Kent C. Dodds (http://kentcdodds.com/)", 26 | "license": "GPL-3.0" 27 | } 28 | -------------------------------------------------------------------------------- /src/__tests__/mock-example.js: -------------------------------------------------------------------------------- 1 | import 'react-testing-library/cleanup-after-each' 2 | import React from 'react' 3 | import {CSSTransition} from 'react-transition-group' 4 | import {render, fireEvent} from 'react-testing-library' 5 | import {HiddenMessage} from '../hidden-message' 6 | 7 | test('you can mock things with jest.mock', () => { 8 | const {getByText, queryByText, debug} = render( 9 | 10 | ) 11 | const toggleButton = getByText('Toggle') 12 | 13 | const context = expect.any(Object) 14 | const children = expect.any(Object) 15 | const defaultProps = {children, timeout: 1000, className: 'fade'} 16 | 17 | expect(CSSTransition).toHaveBeenCalledWith( 18 | {in: true, ...defaultProps}, 19 | context 20 | ) 21 | expect(getByText('Hello world')).not.toBeNull() 22 | 23 | CSSTransition.mockClear() 24 | 25 | fireEvent.click(toggleButton) 26 | 27 | expect(queryByText('Hello world')).toBeNull() 28 | expect(CSSTransition).toHaveBeenCalledWith( 29 | {in: false, ...defaultProps}, 30 | context 31 | ) 32 | }) 33 | -------------------------------------------------------------------------------- /src/__tests__/mock.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import {CSSTransition} from 'react-transition-group' 3 | import {render, fireEvent, cleanup} from 'react-testing-library' 4 | import {HiddenMessage} from '../hidden-message' 5 | 6 | afterEach(cleanup) 7 | 8 | jest.mock('react-transition-group', () => { 9 | return {CSSTransition: jest.fn(({children}) => children)} 10 | }) 11 | 12 | test('you can mock things with jest.mock', () => { 13 | const {getByText} = render() 14 | const context = expect.any(Object) 15 | const children = expect.any(Object) 16 | const defaultProps = {children, timeout: 1000, className: 'fade'} 17 | expect(CSSTransition).toHaveBeenCalledWith( 18 | {in: true, ...defaultProps}, 19 | context 20 | ) 21 | CSSTransition.mockClear() 22 | fireEvent.click(getByText(/toggle/i)) 23 | expect(CSSTransition).toHaveBeenCalledWith( 24 | {in: false, ...defaultProps}, 25 | context 26 | ) 27 | }) 28 | -------------------------------------------------------------------------------- /src/__tests__/shallow-example.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import Enzyme, {shallow} from 'enzyme' 3 | import Adapter from 'enzyme-adapter-react-16' 4 | import {HiddenMessage} from '../hidden-message' 5 | 6 | Enzyme.configure({adapter: new Adapter()}) 7 | 8 | test('shallow', () => { 9 | const wrapper = shallow() 10 | expect(wrapper.find('Fade').props()).toEqual({ 11 | in: true, 12 | children:
Hello world
13 | }) 14 | wrapper.find('button').simulate('click') 15 | expect(wrapper.find('Fade').props()).toEqual({ 16 | in: false, 17 | children:
Hello world
18 | }) 19 | }) 20 | -------------------------------------------------------------------------------- /src/__tests__/shallow.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import Enzyme, {shallow} from 'enzyme' 3 | import Adapter from 'enzyme-adapter-react-16' 4 | import {HiddenMessage} from '../hidden-message' 5 | 6 | Enzyme.configure({adapter: new Adapter()}) 7 | 8 | test('shallow', () => { 9 | const wrapper = shallow() 10 | const children = expect.any(Object) 11 | const defaultProps = {children} 12 | expect(wrapper.find('Fade').props()).toEqual({ 13 | in: true, 14 | children: expect.any(Object) 15 | }) 16 | wrapper.find('button').simulate('click') 17 | expect(wrapper.find('Fade').props()).toEqual({ 18 | in: false, 19 | children: expect.any(Object) 20 | }) 21 | }) 22 | -------------------------------------------------------------------------------- /src/hidden-message.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import {CSSTransition} from 'react-transition-group' 3 | 4 | function Fade({children, ...props}) { 5 | return ( 6 | 7 | {children} 8 | 9 | ) 10 | } 11 | 12 | class HiddenMessage extends React.Component { 13 | static defaultProps = {initialShow: false} 14 | state = {show: this.props.initialShow} 15 | toggle = () => { 16 | this.setState(({show}) => ({show: !show})) 17 | } 18 | render() { 19 | return ( 20 |
21 | 22 | 23 |
Hello world
24 |
25 |
26 | ) 27 | } 28 | } 29 | 30 | export {HiddenMessage} 31 | --------------------------------------------------------------------------------