Reputation: 5172
This is my form:
import { useState } from "react"
import { Form, Button, Row, Col } from "react-bootstrap"
import { actions as parametersActions } from "../../actions/ParametersActions"
import { connect } from "react-redux"
export const Parameters = props => {
const [birthdate, setBirthdate] = useState("")
const [height, setHeight] = useState("")
const handleForm = (e) => {
if (e.target.id === 'birthdate') {
setBirthdate(e.target.value)
}
if (e.target.id === 'height') {
setHeight(e.target.value)
}
}
const handleSubmit = (e) => {
e.preventDefault()
const payload = {
birthdate: birthdate,
height: height
}
props.post(payload)
}
return (
<Row className="justify-content-md-center">
<Col xs lg="4">
<Form>
<Form.Group controlId="birthdate">
<Form.Label>Data di nascita</Form.Label>
<Form.Control type="text" placeholder="Inserisci data di nascita" value={birthdate} onChange={handleForm} />
</Form.Group>
<Form.Group controlId="height">
<Form.Label>Altezza</Form.Label>
<Form.Control type="text" placeholder="Altezza" value={height} onChange={handleForm} />
</Form.Group>
<div className="d-grid gap-2">
<Button variant="primary" onClick={handleSubmit}>
Salva
</Button>
</div>
</Form>
</Col>
</Row>
)
}
export const mapStateToProps = (state) => {
return {
isLoading: state.parameters.isLoading
}
}
export const mapDispatchToProps = (dispatch) => {
return {
post: (data) => dispatch(parametersActions.post(data))
}
}
export default connect(
mapStateToProps,
mapDispatchToProps
)(Parameters)
And this is my test:
import { render, screen, fireEvent } from '@testing-library/react'
import thunk from 'redux-thunk'
import configureMockStore from 'redux-mock-store'
import Parameters from '../../../presentationals/forms/Parameters'
import { action as parametersActions } from '../../../actions/ParametersActions'
describe('Parameters form', () => {
it('Can store new parameters', async () => {
const middlewares = [thunk]
const mockStore = configureMockStore(middlewares)
const initialState = {
parameters: {
isLoading: false,
},
post: (data) => dispatch(parametersActions.post(data))
}
const store = mockStore(initialState)
render(<Parameters store={store} />)
const birthdate = screen.getByText(/nascita/i)
expect(birthdate).toBeInTheDocument()
const height = screen.getByText(/altezza/i)
expect(height).toBeInTheDocument()
fireEvent.change(screen.getByLabelText(/nascita/i), {
target: {value: '1990-12-31'},
})
fireEvent.change(screen.getByLabelText(/altezza/i), {
target: {value: '170'},
})
fireEvent.click(screen.getByText(/salva/i))
// how can I test here?
})
})
I want to test that
handleSubmit
is calledprops.post()
is calledHow can I add that test?
Upvotes: 0
Views: 148
Reputation: 202605
When using React-Testing-Library don't test internal implementation details, but rather the API of the component, in this case, the post
prop callback function.
post
prop functionpost
prop function was called (toHaveBeenCalled)Code:
import { render, screen, fireEvent } from '@testing-library/react';
import { Parameters } from '../../../presentationals/forms/Parameters'
import { action as parametersActions } from '../../../actions/ParametersActions';
describe('Parameters form', () => {
it('Can store new parameters', async () => {
const postMock = jest.fn(); // <-- create mock callback
render(<Parameters post={postMock} />); // <-- pass mock as prop
...
fireEvent.click(screen.getByText(/salva/i));
expect(postMock).toHaveBeenCalled(); // <-- assert mock was called
});
});
If required you can use toHaveBeenCalledWith to assert specific values were passed to the callback.
expect(postMock).toHaveBeenCalledWith({
birthdate: '1990-12-31',
height: '170',
});
Upvotes: 1
Reputation: 1454
Instead of testing if the handleSubmit has been called, you should test the result of triggering the submit event. Which in this case could mean verifying that the dispatch is made.
Upvotes: 0