英文:
2 different instance of axios mock having returning an error of axios.default is not a function
问题
在名为eventController的函数中,有两种不同的方式实现了axios调用。第一种方式如下:
axios.post(
`${url}/API1`,
{
data: 'data for API1'
}
)
然后第二种方式如下:
await axios({
method: 'POST',
url: `${url}/API2`,
data: {
data: 'data for API2'
}
})
在一个函数或控制器中有两个不同的axios调用。
我被分配了使用Jest和TypeScript来为此编写单元测试,到目前为止我所做的是:
jest.mock('axios', () => ({
post: jest
.fn()
.mockResolvedValueOnce({ status: 200 })
}));
it("should work", async () => {
const req = {body: {
data: 'data for API'
}}
const response = await eventController(req);
expect(response.status).toBe(200);
});
我使用.post
方法来模拟第一个axios调用,但是当使用默认的axios模块进行第二个axios调用时,我收到了以下错误:
TypeError: (0 , axios_1.default) is not a function
我尝试过以下两种方式,但都似乎不起作用:
方式一:
jest.mock('axios', () => ({
__esModule: true,
default: jest.fn(),
post: jest
.fn()
.mockResolvedValueOnce({ status: 200 })
}));
方式二:
jest.mock('axios', () => ({
__esModule: true,
default: {
post: jest
.fn()
.mockResolvedValueOnce({ status: 200 })
},
}));
希望有人能帮助我解决这个问题。这是我目前正在使用的库版本:
- "jest": "^27.0.6"
- "babel-jest": "^27.0.6"
- "axios": "^0.21.4",
- "@types/jest": "^27.0.0",
- "ts-jest": "^27.0.4"
英文:
In my function named eventController. An axios call has implemented in two ways
The 1st one is on this code
axios.post(
`${url}/API1`,
{
data:'data for API1'
}
)
Then this is the 2nd
await axios({
method: 'POST',
url: `${url}/API2`,
data: {
data:'data for API2'
}
})
2 different axios calls in one function/controller
I'm assigned in implementing a unit test for this using jest in typescript
So what I did so far is this
jest.mock('axios', () => ({
post: jest
.fn()
.mockResolvedValueOnce({ status: 200 })
}));
it("should work", async () => {
const req = {body: {
data: 'data for API'
}}
const response = await eventController(req);
expect(response.status).toBe(200);
});
I mock the 1st axios call with .post method but when doing it w/ the second one using the default axios module I have received this error
TypeError: (0 , axios_1.default) is not a function
I've tried to implement this way also but both don't seem to work
This:
jest.mock('axios', () => ({
__esModule: true,
default: jest.fn(),
post: jest
.fn()
.mockResolvedValueOnce({ status: 200 })
}));
and this:
jest.mock('axios', () => ({
__esModule: true,
default: {
post: jest
.fn()
.mockResolvedValueOnce({ status: 200 })
},
}));
Hoping someone can help me on this one. This is the versions of the library I'm currently using
- "jest": "^27.0.6"
- babel-jest": "^27.0.6"
- "axios": "^0.21.4",
- @types/jest": "^27.0.0",
- "ts-jest": "^27.0.4",
答案1
得分: 0
使用 jest.mock(moduleName, factory, options)
,并且不传递 factory
参数,让 jest 自动模拟一个模块的版本。此外,没有 __mocks__
目录。
在模拟后,你需要处理 axios
函数和 axios.get()
方法的TS类型,可以使用类型转换来实现。
注意:我使用一个简单的字符串作为模拟的解析值,这个值不匹配AxiosResponse
接口。
示例:
main.ts
:
import axios from 'axios';
const url = 'http://localhost:3000';
export async function main() {
const res1 = await axios.post(`${url}/API1`, {
data: 'data for API1',
});
console.log('res1: ', res1);
const res2 = await axios({
method: 'POST',
url: `${url}/API2`,
data: {
data: 'data for API2',
},
});
console.log('res2: ', res2);
}
main.test.ts
:
import { main } from './main';
import axios from 'axios';
jest.mock('axios');
const axiosMock = axios as jest.MockedFunction<typeof axios>;
const axiosPostMock = axios.post as jest.MockedFunction<typeof axios.post>;
test('should pass', async () => {
expect(jest.isMockFunction(axios)).toBe(true);
expect(jest.isMockFunction(axios.post)).toBe(true);
axiosPostMock.mockResolvedValueOnce('fake data 1');
axiosMock.mockResolvedValueOnce('fake data 2' as any);
await main();
});
测试结果:
PASS stackoverflow/76407602/main.test.ts (38.236 s)
✓ should pass (48 ms)
console.log
res1: fake data 1
at stackoverflow/76407602/main.ts:8:11
console.log
res2: fake data 2
at stackoverflow/76407602/main.ts:16:11
Test Suites: 1 passed, 1 total
Tests: 1 passed, 1 total
Snapshots: 0 total
Time: 41.384 s
英文:
Just use jest.mock(moduleName, factory, options)
and without passing the factory
argument, let the jest mocks a module with an auto-mocked version. And, there is no __mocks__
directory.
You need to handle the TS types for axios
function and axios.get()
method after mocking, use type cast to do this.
Note: I use a simple string as the mock resolved value which does not match the AxiosResponse
interface.
E.g.
main.ts
:
import axios from 'axios';
const url = 'http://localhost:3000';
export async function main() {
const res1 = await axios.post(`${url}/API1`, {
data: 'data for API1',
});
console.log('res1: ', res1);
const res2 = await axios({
method: 'POST',
url: `${url}/API2`,
data: {
data: 'data for API2',
},
});
console.log('res2: ', res2);
}
main.test.ts
:
import { main } from './main';
import axios from 'axios';
jest.mock('axios');
const axiosMock = axios as jest.MockedFunction<typeof axios>;
const axiosPostMock = axios.post as jest.MockedFunction<typeof axios.post>;
test('should pass', async () => {
expect(jest.isMockFunction(axios)).toBe(true);
expect(jest.isMockFunction(axios.post)).toBe(true);
axiosPostMock.mockResolvedValueOnce('fake data 1');
axiosMock.mockResolvedValueOnce('fake data 2' as any);
await main();
});
Test result:
PASS stackoverflow/76407602/main.test.ts (38.236 s)
✓ should pass (48 ms)
console.log
res1: fake data 1
at stackoverflow/76407602/main.ts:8:11
console.log
res2: fake data 2
at stackoverflow/76407602/main.ts:16:11
Test Suites: 1 passed, 1 total
Tests: 1 passed, 1 total
Snapshots: 0 total
Time: 41.384 s
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论