Quarantining failing tests with Jest
Sometimes a test fails because a subsystem isn’t yet ready, the test is valid but failing. When that happens it sucks to have to comment out the test in order to keep the build green whilst fixing the subsystem. I’d rather be able to mark the test as “known failing” and then carry on.
Bamboo allows for this with the concept of “quarantined” tests which works really well… on a build server.
But that doesn’t help at all when it’s a test on your local dev system đ
Jest allows tests to be marked as ‘skipped‘ which prevents them from running, so at least progress can be made with a “known broken” test. However, should you actually succeed in fixing the subsystem nothing will let you know that that broken test is now working. If you’re like me there’s every chance you’ll commit your now working subsystem but forget to go back and re-enable the skipped test.
You can also mark a test as ‘todo‘ and get a nice little indication in your test output that there is still work to be done, but that test can’t have any code đ¤
Given that there is an outstanding feature request in the jest issue tracker, I’m clearly not the only one that wants such a thing (phew! it’s good not to be too weird).
So, in order to keep working, I came up with a suitably hacky workaround đ
I created a ‘quarantine’ function that can be appended to test/it that makes the test show up as a todo as long as it is failing, and show up as a failure if it unexpectedly passes.
jest-quarantine.js
test.quarantine = function (description, func) {
describe("in quarantine", () => {
try {
func()
test(description, () => {
const e = new Error("[" + description + "] was expected to fail, but it passed")
e.name = 'Quarantine Escape'
throw e
})
} catch (e) {
test.todo('fix ' + description)
}
})
}
Then I added this to my jest config like so
jest.config.js
export default {
...
setupFilesAfterEnv: [
'<rootDir>/jest-quarantine.js',
],
}
which of course is included in the jest command line as
"jest  --config=./jest.config.js“
And now I can just write
test.quarantine('this test is not ready yet, () => {
expect(true).toBe(false)
})
And get Bamboo-like quarantine behaviour on my local dev box.
Ideal? no. Great code? also no. Useful? For me it is đ maybe it will be for you too.