Hi,
I’m still (!) trying to test the error state of my mutation. I have the following setup:
Component under test:
export function SubmitForm(): React.ReactElement<HTMLFormElement> {
const [message, setMessage] = useState('');
const [submitMessage, { loading, error }] = useMutation(MESSAGE_MUTATION);
return (
<form
onSubmit={event => {
event.preventDefault();
try {
submitMessage({
variables: {
SendMessageInput: {
body: message,
threadId: '12a',
senderId: 123,
recipientId: 321,
subject: '',
},
},
});
setMessage('');
} catch {
console.log(error)
}
}
}>
{error && (
<SecondaryCalloutMessage
icon="alertTriangle"
status="error"
title="Sorry, there was a problem submitting your message"
>
<Paragraph>
Please check that all your payment details are correct
and try again.
</Paragraph>
</SecondaryCalloutMessage>
)}
<fieldset>
<label htmlFor="input">Compose message</label>
<input
type="text"
id="input"
value={message}
onChange={event => setMessage(event.target.value)}
/>
</fieldset>
<button type="submit">Send message {loading && <Spinner />}</button>
</form>
);
}
Here’s the test:
it('should render the error state UI', () => {
jest.spyOn(navigator, 'onLine', 'get').mockReturnValueOnce(false);
const mockMutation = {
request: {
query: MESSAGE_MUTATION,
variables: {
SendMessageInput: {
body: 'test',
threadId: '12a',
senderId: 123,
recipientId: 321,
},
},
},
result: null,
error: new Error('Drat'),
};
render(
<ThemeProvider theme={defaultTheme}>
<MockedProvider mocks={[mockMutation as any]}>
<SubmitForm {...mockData} />
</MockedProvider>
</ThemeProvider>
);
const inputField = screen.getByLabelText(/compose message/i);
const button = screen.getByText('Send message');
userEvent.type(inputField, mockNewMessage);
fireEvent.click(button);
setTimeout(() => {
expect(
screen.getByText(
/sorry, there was a problem submitting your message/i
)
).toBeInTheDocument();
});
}, 0);
if I don’t use setTimeout()
I get a loading spinner in the DOM, but with the test like this, I only get this error:
Warning: An update to SubmitForm inside a test was not wrapped in act(...).
I’ve also tried using an async test and waitFor()
instead of a setTimeout()
, however that tears down the environment before I can make the assertion.
I even added a dummy act(() => {}) block which didn’t return the same error, but resulted in the loading state.
Some more assistance would be much appreciated!