如何创建模拟 POST 请求来测试页面是否已更改
How to create a mock POST request to test if page has changed
我有一个 App.js 文件,其中包含一个表单,提交后会触发状态更改以呈现新页面。我正在尝试创建一个执行以下步骤的模拟 Jest 测试:
- 获取模拟数据
- 像 addInfo 一样发送 POST 请求
- 检查“DONE WITH FORM”是否呈现在屏幕上。
我也有一个想法,我们可以只填写一个包含 valid_address 和 valid_number 的表单,然后单击一个按钮触发 addInfo 函数到 运行传入的信息但是我不确定该方法,它导致我出现 CORS 错误。
从我在网上看到的情况来看,我认为使用 Jest 模拟这个 addInfo 然后测试呈现的内容是最好的方法,但是我完全坚持构建这个测试。
这是我的 App.js
const addInfo = async (formInfo) => {
try {
let data = {
valid_number: formInfo.validNumber,
valid_address: formInfo.validAddress
}
let addUserUrl = process.env.REACT_APP_URL +'/verify'
let addUserData = await fetch(
addUserUrl,
{
method: "POST",
headers: {
"Content-type": "application/json",
"x-api-key": process.env.REACT_APP_KEY
},
body: JSON.stringify(data)
}
)
if (addUserData.status !== 200) {
throw 'Error adding User'
}
let addUserDataJson = addUserData.json()
let ret = {
added: true,
}
return ret
} catch (error) {
console.log('Error')
let ret = {
added: false,
}
return ret
}
}
const onFinish = async (values: any) => {
console.log('Transaction verified');
let addStatus = await addInfo({
validNumber: "123434",
validAddress: "D74DS8JDSF",
})
if (promoStatus.added) {
setState({
...state,
showPage: false
})
} else {
setState({
...state,
showPage: true
})
}
};
return (
{!state.showPage &&
<>
<div>
<p>
DONE WITH FORM
</p>
<div>
</>
}
)
这是我在 App.test.js 中尝试过的:
it('DONE WITH FORM APPEARS', async() =>{
// Render App
const { getByPlaceholderText, queryByText, getByText } = render(<App />);
// Entering Valid Number
const validNumberInputBox = getByText('Enter Valid Number);
fireEvent.change(validNumberInputBox, { target: { value: "123434" } });
expect(validNumberInputBox).toHaveValue("123434");
// Entering Valid Address
const validAddressInputBox = getByText('Enter Valid Address');
fireEvent.change(validAddressInputBox, { target: { value: "D74DS8JDSF" } });
expect(validAddressInputBox).toHaveValue("D74DS8JDSF");
// Button Click
userEvent.click(screen.getByRole('button', {name: /Submit/i}));
//Check if the DONE WITH FORM is shown
expect(await waitFor(() => getByText('DONE WITH FORM'))).toBeInTheDocument();
});
我已经尝试了通过其他堆栈溢出帖子和网络文章找到的几乎所有内容。所以我非常感谢任何有关如何实施此单元测试的帮助。
第一步是模拟执行 POST 请求 (addInfo) 的异步函数。您永远不想在单元测试中尝试真正的 HTTP 请求(这是行不通的,因为 Jest 运行在未实现 fetch 或 XMLHttpRequest API 的 Node 环境中)。除此之外,component/unit 测试应该独立于任何其他系统,例如后端公开 API。
为此,你的异步函数应该在一个单独的文件中(所以是一个 JS 模块),然后你可以使用 Jest 模拟这个模块:
// api.js
export const addInfo = () => {...}
// App.test.js
import * as Api from 'api.js';
// here you can define what your mock will return for this test suite
const addInfoSpy = jest.spyOn(Api, 'addInfo').mockResolvedValue({ ret: true });
describe('...', () => {
test('...', async () => {
// perform user interactions that should trigger an API call
expect(addInfoSpy).toHaveBeenCalledWith('expected addInfos parameter');
// now you can test that your component displays "DONE WITH FORM" or whatever
// UI it should be displaying after a successful form submission
});
});
我有一个 App.js 文件,其中包含一个表单,提交后会触发状态更改以呈现新页面。我正在尝试创建一个执行以下步骤的模拟 Jest 测试:
- 获取模拟数据
- 像 addInfo 一样发送 POST 请求
- 检查“DONE WITH FORM”是否呈现在屏幕上。
我也有一个想法,我们可以只填写一个包含 valid_address 和 valid_number 的表单,然后单击一个按钮触发 addInfo 函数到 运行传入的信息但是我不确定该方法,它导致我出现 CORS 错误。
从我在网上看到的情况来看,我认为使用 Jest 模拟这个 addInfo 然后测试呈现的内容是最好的方法,但是我完全坚持构建这个测试。
这是我的 App.js
const addInfo = async (formInfo) => {
try {
let data = {
valid_number: formInfo.validNumber,
valid_address: formInfo.validAddress
}
let addUserUrl = process.env.REACT_APP_URL +'/verify'
let addUserData = await fetch(
addUserUrl,
{
method: "POST",
headers: {
"Content-type": "application/json",
"x-api-key": process.env.REACT_APP_KEY
},
body: JSON.stringify(data)
}
)
if (addUserData.status !== 200) {
throw 'Error adding User'
}
let addUserDataJson = addUserData.json()
let ret = {
added: true,
}
return ret
} catch (error) {
console.log('Error')
let ret = {
added: false,
}
return ret
}
}
const onFinish = async (values: any) => {
console.log('Transaction verified');
let addStatus = await addInfo({
validNumber: "123434",
validAddress: "D74DS8JDSF",
})
if (promoStatus.added) {
setState({
...state,
showPage: false
})
} else {
setState({
...state,
showPage: true
})
}
};
return (
{!state.showPage &&
<>
<div>
<p>
DONE WITH FORM
</p>
<div>
</>
}
)
这是我在 App.test.js 中尝试过的:
it('DONE WITH FORM APPEARS', async() =>{
// Render App
const { getByPlaceholderText, queryByText, getByText } = render(<App />);
// Entering Valid Number
const validNumberInputBox = getByText('Enter Valid Number);
fireEvent.change(validNumberInputBox, { target: { value: "123434" } });
expect(validNumberInputBox).toHaveValue("123434");
// Entering Valid Address
const validAddressInputBox = getByText('Enter Valid Address');
fireEvent.change(validAddressInputBox, { target: { value: "D74DS8JDSF" } });
expect(validAddressInputBox).toHaveValue("D74DS8JDSF");
// Button Click
userEvent.click(screen.getByRole('button', {name: /Submit/i}));
//Check if the DONE WITH FORM is shown
expect(await waitFor(() => getByText('DONE WITH FORM'))).toBeInTheDocument();
});
我已经尝试了通过其他堆栈溢出帖子和网络文章找到的几乎所有内容。所以我非常感谢任何有关如何实施此单元测试的帮助。
第一步是模拟执行 POST 请求 (addInfo) 的异步函数。您永远不想在单元测试中尝试真正的 HTTP 请求(这是行不通的,因为 Jest 运行在未实现 fetch 或 XMLHttpRequest API 的 Node 环境中)。除此之外,component/unit 测试应该独立于任何其他系统,例如后端公开 API。
为此,你的异步函数应该在一个单独的文件中(所以是一个 JS 模块),然后你可以使用 Jest 模拟这个模块:
// api.js
export const addInfo = () => {...}
// App.test.js
import * as Api from 'api.js';
// here you can define what your mock will return for this test suite
const addInfoSpy = jest.spyOn(Api, 'addInfo').mockResolvedValue({ ret: true });
describe('...', () => {
test('...', async () => {
// perform user interactions that should trigger an API call
expect(addInfoSpy).toHaveBeenCalledWith('expected addInfos parameter');
// now you can test that your component displays "DONE WITH FORM" or whatever
// UI it should be displaying after a successful form submission
});
});