Reputation: 2245
I am trying to extend Jest to easier get API integration tests to play along between different APIs.
I have followed this tutorial and I have it working somewhat. Here's my setup:
jest.setup.api.ts
test.apiOne = async (
name: string,
fn?: jest.ProvidesCallback,
timeout?: number
) => {
console.log(`Running test "${name}" against API 1`)
pactum.request.setBaseUrl(`${process.env.API_TEST_HOST}/one`)
test(name, fn, timeout)
}
test.apiTwo = async (
name: string,
fn?: jest.ProvidesCallback,
timeout?: number
) => {
console.log(`Running test "${name}" against API 2`)
pactum.request.setBaseUrl(`${process.env.API_TEST_HOST}/two`)
test(name, fn, timeout)
}
And I use it like this:
test.apiOne("1", async () => {
console.log("1");
})
test.apiTwo("2", async () => {
console.log("2");
})
test.apiOne("3", async () => {
console.log("3");
})
test.apiOne("4", async () => {
console.log("4");
})
When I run these tests, this is the output
console.log jest.setup.api.ts:26
Running test "1" against API 1
console.log jest.setup.api.ts:38
Running test "2" against API 2
console.log jest.setup.api.ts:26
Running test "3" against API 1
console.log jest.setup.api.ts:38
Running test "4" against API 2
console.log mytest.ts:511
1
console.log jest.setup.api.ts:26
Running test "1" against API 1
console.log jest.setup.api.ts:38
Running test "2" against API 2
console.log jest.setup.api.ts:26
Running test "3" against API 1
console.log jest.setup.api.ts:38
Running test "4" against API 2
console.log mytest.ts:511
2
console.log jest.setup.api.ts:26
Running test "1" against API 1
console.log jest.setup.api.ts:38
Running test "2" against API 2
console.log jest.setup.api.ts:26
Running test "3" against API 1
console.log jest.setup.api.ts:38
Running test "4" against API 2
console.log mytest.ts:511
3
console.log jest.setup.api.ts:26
Running test "1" against API 1
console.log jest.setup.api.ts:38
Running test "2" against API 2
console.log jest.setup.api.ts:26
Running test "3" against API 1
console.log jest.setup.api.ts:38
Running test "4" against API 2
console.log mytest.ts:511
4
So for all tests it is always the conditions for the last test within the describe that gets set. So test 1
should run against API path /one
but actually gets run against /two
.
Is there any way to achieve what I am trying do with Jest?
Upvotes: 1
Views: 463
Reputation: 222979
The article is wrong on some points.
Modifying third-party API for your own needs isn't a good practice. If there's a need for custom test helpers, there's no need to modify test
. They can be importable or global and be used the same way as test.apiOne
but with less potential problems. It's a mistake to make these functions async
. Tests should be known at the time when test run starts, so async
results in a promise that isn't used. The article uses await
yet types a function to return void
.
test.apiOne
cannot contain asynchronous operations, they will be discarded when they occur after test(...)
and they will result in missing test when they occur before. test(...)
result isn't returned, this means that a promise it returns won't be handled correctly by Jest.
console.log(`Running test "${name}" against API 1`)
mistakenly suggests that it's called when a test runs, but it's actually called when it's declared.
pactum.request.setBaseUrl
should be called inside a test it's supposed to affect. Considering that tests are asynchronous and use promises and not done
callback, a helper is:
global.testApiOne = (name, fn, timeout) => {
test(
name,
async () => {
console.log(`Running test "${name}" against API 1`)
pactum.request.setBaseUrl(`${process.env.API_TEST_HOST}/one`)
await fn();
},
timeout
)
}
Upvotes: 1