如何在启用异步验证的情况下测试 redux 表单
How to test a redux form with async validation enabled
我为我的 redux 表单中的一个字段启用了异步验证。我使用 jest 和 enzyme 来测试表单提交。
我尝试用一个简单的 resolved promise 模拟异步验证函数,表单仍然无法提交。但是我去掉了异步验证,表单可以毫无问题地提交。
...
jest.mock('../../../../../../utilities/validators');
it('should set registration info and set current step with correct values when registration form is successfully submitted', () => {
const store = createStore(
combineReducers({
form: formReducer,
}),
);
validateEmailUnique.mockImplementation(() => Promise.resolve());
const mockOnSetRegistrationInfo = jest.fn();
const mockOnSetRegistrationCurrentStep = jest.fn();
const updatedProps = {
...defaultProps,
onSetRegistrationInfo: mockOnSetRegistrationInfo,
onSetRegistrationCurrentStep: mockOnSetRegistrationCurrentStep,
};
const wrapper = mount(
<Provider store={store}>
<StepOne {...updatedProps} />
</Provider>,
);
const form = wrapper.find('form');
const businessEmailTextField = wrapper.find(
'input#business-email-text-field',
);
businessEmailTextField.simulate('change', {
target: {
value: 'business@email.com',
},
});
form.simulate('submit');
expect(mockOnSetRegistrationInfo).toHaveBeenCalled();
我希望提交表单,然后调用表单提交回调函数中的 'onSetRegistrationInfo' 函数。但是由于没有通过异步验证,所以测试时无法提交表单。
问题是 expect
运行失败时异步验证尚未完成。
根据我对您代码的了解,您似乎无法从异步验证步骤直接访问 Promise
,因此您将无法直接 await
...
...但是如果您模拟了任何 async
操作以立即解决,那么它们应该全部在 Promise
微任务队列的一个周期内完成。
如果是这种情况,那么您可以将您的断言移至 setImmediate
或 setTimeout
并使用 done
让 Jest
知道测试何时完成:
it('should set registration info...', done => { // <= use done
// ...
form.simulate('submit');
setImmediate(() => {
expect(mockOnSetRegistrationInfo).toHaveBeenCalled(); // Success!
done(); // <= now call done
});
});
我为我的 redux 表单中的一个字段启用了异步验证。我使用 jest 和 enzyme 来测试表单提交。
我尝试用一个简单的 resolved promise 模拟异步验证函数,表单仍然无法提交。但是我去掉了异步验证,表单可以毫无问题地提交。
...
jest.mock('../../../../../../utilities/validators');
it('should set registration info and set current step with correct values when registration form is successfully submitted', () => {
const store = createStore(
combineReducers({
form: formReducer,
}),
);
validateEmailUnique.mockImplementation(() => Promise.resolve());
const mockOnSetRegistrationInfo = jest.fn();
const mockOnSetRegistrationCurrentStep = jest.fn();
const updatedProps = {
...defaultProps,
onSetRegistrationInfo: mockOnSetRegistrationInfo,
onSetRegistrationCurrentStep: mockOnSetRegistrationCurrentStep,
};
const wrapper = mount(
<Provider store={store}>
<StepOne {...updatedProps} />
</Provider>,
);
const form = wrapper.find('form');
const businessEmailTextField = wrapper.find(
'input#business-email-text-field',
);
businessEmailTextField.simulate('change', {
target: {
value: 'business@email.com',
},
});
form.simulate('submit');
expect(mockOnSetRegistrationInfo).toHaveBeenCalled();
我希望提交表单,然后调用表单提交回调函数中的 'onSetRegistrationInfo' 函数。但是由于没有通过异步验证,所以测试时无法提交表单。
问题是 expect
运行失败时异步验证尚未完成。
根据我对您代码的了解,您似乎无法从异步验证步骤直接访问 Promise
,因此您将无法直接 await
...
...但是如果您模拟了任何 async
操作以立即解决,那么它们应该全部在 Promise
微任务队列的一个周期内完成。
如果是这种情况,那么您可以将您的断言移至 setImmediate
或 setTimeout
并使用 done
让 Jest
知道测试何时完成:
it('should set registration info...', done => { // <= use done
// ...
form.simulate('submit');
setImmediate(() => {
expect(mockOnSetRegistrationInfo).toHaveBeenCalled(); // Success!
done(); // <= now call done
});
});