Make test name available in beforeEach() and afterEach()
🚀 Feature Proposal
Make test name available in beforeEach() and afterEach().
Motivation
When running Selenium tests it's helpful to take a screenshot after every test. Best name for those files would be the test name. Now I use url and timestamp, which are not that good.
For further logging purposes beforeEach() could use the test name too, to log when that test starts. It makes easier to search server logs from the same time.
Example
afterEach(async (testName) => {
await saveScreenshot(testName);
log(`Test '${testName}' ended at ${getTime()}`);
});
Interesting suggestion, thanks! If this is implemented, the argument should probably be an object literal to make it easy to pass in more things to the function without a breaking change.
Sounds cool. This will be possible once we get rid of done and replace it with generic purpose object, like AVA does :)
That won't happen any time soon though - in the meantime you can use jest-image-snapshot - the snapshot file will get the test's name automatically. If that doesn't fit, I'd look into implementing it in some other way using jest's snapshot features so that you get the name included
just wanted to add that this would be super useful when using an XHR vcr like nock back. Right now I have to do this in each test
const { nockDone } = await nockBack('fixtureName.json')
// the actual test
nockDone()
it would be awesome to just do something like
let nockDone
beforeEach(() => {
const result = await nockBack(testName + '.json')
nockDone = result.nockDone
})
afterEach(() => {
nockDone()
})
in case this is helpful, mocha keeps a whole suite of helpers in the befores' this scope. Would it make sense to pass some sort of class instance, instead of an object literal, so we can pave the way for things like .skip() programmatically?
https://mochajs.org/api/suite#fullTitle
describe('test suite', () => {
beforeEach(function () {
console.log(this.currentTest.fullTitle())
// test suite nested names are included too
}
describe('nested names are', () => {
it('included too', () => {
})
})
})
My current solution.
File: jest.config.js:
module.exports = {
setupFilesAfterEnv: ['./jest.setup.js'],
.................
};
File jest.setup.js:
// Patch tests
jasmine.getEnv().addReporter({
specStarted: result => jasmine.currentTest = result,
specDone: result => jasmine.currentTest = result,
});
File any-test.spec.ts
describe('Test description', () => {
beforeEach(() => console.log('Before test', jasmine['currentTest'].fullName));
afterEach(() => console.log(
'Test',
jasmine['currentTest'].fullName,
'failed',
!!jasmine['currentTest'].failedExpectations.length
));
it('example', () => expect(1).toBe(1));
});
I hope it helps somebody.
This would be handy simply because I'm using jest to run long integration tests with lots of logging. It's nice to see which test is being run before the setup in the before* hooks start.
@optimistex 's solution still works today, so that's nice. Here's the types, so you don't have to do the ['currentTest'] and force it into an any type:
declare namespace jasmine {
const currentTest: {
id: string;
description: string;
fullName: string;
failedExpectations: {
actual: string;
error: Error;
expected: string;
matcherName: string;
message: string;
passed: boolean;
stack: string;
}[];
passedExpectations: unknown[];
pendingReason: string;
testPath: string;
};
}
Note I made passedExpectations an unkown[], as it was always an empty array for me. Not sure if it ever contains something.
Just a quick note: The last bits of Jasmine remaining in Jest are supposed to be phased out soon, as jest-circus becomes the default test runner implementation. This does not mean using Jasmine-specific APIs will no longer be possible, just that you may miss out on any new features / fixes specific to jest-circus. See https://jestjs.io/blog/2020/05/05/jest-26 for a timeline.
In jest-circus, I noticed that when I console.log the event.test inside handleTestEvent, I get a recursive test type (something like test -> parent -> parent -> ROOT_DESCRIBE_BLOCK):
console.log({
type: 'test',
asyncError: "ErrorWithStack: etc...",
duration: null,
errors: [],
fn: [Function (anonymous)],
invocations: 1,
mode: undefined,
name: 'first it',
parent: {
type: 'describeBlock',
children: [ [Circular *1], [Object] ],
hooks: [],
mode: undefined,
name: 'first describe',
parent: {
type: 'describeBlock',
children: [Array],
hooks: [Array],
mode: undefined,
name: 'ROOT_DESCRIBE_BLOCK',
parent: undefined,
tests: []
},
tests: [ [Circular *1] ]
},
startedAt: 1591598218051,
status: null,
timeout: undefined
})
I was wondering if there is an equivalent function to jasmine['currentTest'].fullName?
EDIT: In the meantime this is what I did to get the full test name:
if (event.name === "test_start") {
let testNames = [];
let currentTest = event.test;
while (currentTest) {
testNames.push(currentTest.name);
currentTest = currentTest.parent;
}
this.global.testName = testNames
.slice(0, testNames.length - 1)
.reverse()
.map((name) => name.replace(/\W/g, "-"))
.join("-");
}
Bumping this if there is any clear update or expectation on this feature.
I stumbled across the following which may be of interest to others.
beforeEach(() => {
console.log(expect.getState().currentTestName);
})
afterEach(() => {
console.log(expect.getState().currentTestName);
})
I stumbled across the following which may be of interest to others.
beforeEach(() => { console.log(expect.getState().currentTestName); }) afterEach(() => { console.log(expect.getState().currentTestName); })
Very nice, It works on [email protected]. Thanks!
Despite being undocumented, expect.getState().currentTestName still works in Jest v26.6.3, including in test blocks, but it returns the full name of the describe -> describe -> ... -> test, with space separators between the path components :man_facepalming:. That may make it confusing to figure out what the test name is, vs. the describe name, especially in nested describes.
Anyway, I've added this method as my #1 answer to this StackOverflow question about accessing the test name.
This kind of logging should be done by jest itself (like junit) and there is no need to make this information in another way available.
Using jest-circus and a custom environment, we use handleTestEvent to essentially keep state of the test name in these different events. Our use case was to instrument our test suites... the output is something like this:

Thanks @billyvg for your answer. The linked code gave me an idea and wrote an answer on SO.
Is there a way we can get the testStatus afterEach?
Based in the @aesyondu snippet and with hours of console.logs I achieved to get the describeName, testName and status
This is my CustomNodeEnvironment.js
const NodeEnvironment = require('jest-environment-node');
class CustomNodeEnvironment extends NodeEnvironment {
async setup() {
await super.setup();
}
async handleTestEvent(event, state) {
if (event.name === "test_start") {
let testNames = [];
let currentTest = event.test;
while (currentTest) {
testNames.push(currentTest.name);
currentTest = currentTest.parent;
}
this.global.describeName = testNames[1]
this.global.testName = testNames[0]
}
if (event.name === "test_fn_failure") {
this.global.testStatus = "failure"
}else if (event.name === "test_fn_success") {
this.global.testStatus = "success"
}
}
}
module.exports = CustomNodeEnvironment
This my test
describe(`Im the describe`, () => {
let driver;
it(`Im the first test`, async () => {
expect(3).toBe(3);
});
it('Im the second test', async () => {
expect(3).toBe(4);
});
afterEach(() => {
console.log({testStatus:testStatus, testName:testName, describeName:describeName});
})
});
An my jest.config.js
const { defaults } = require("jest-config");
module.exports = {
testEnvironment: './src/helpers/CustomNodeEnvironment.js',
};
An this is the log in which I have access to the detail of each test after its execution

I will try to improve the while to get the describe and test names.
Hello guys! Is there still no way to get running test suite/test file name in Jest 29.4.1? i mean the Jest way
Bump, it was so easy with Jasmine...
Based in the @aesyondu snippet and with hours of console.logs I achieved to get the describeName, testName and status
This is my CustomNodeEnvironment.js
const NodeEnvironment = require('jest-environment-node'); class CustomNodeEnvironment extends NodeEnvironment { async setup() { await super.setup(); } async handleTestEvent(event, state) { if (event.name === "test_start") { let testNames = []; let currentTest = event.test; while (currentTest) { testNames.push(currentTest.name); currentTest = currentTest.parent; } this.global.describeName = testNames[1] this.global.testName = testNames[0] } if (event.name === "test_fn_failure") { this.global.testStatus = "failure" }else if (event.name === "test_fn_success") { this.global.testStatus = "success" } } } module.exports = CustomNodeEnvironmentThis my test
describe(`Im the describe`, () => { let driver; it(`Im the first test`, async () => { expect(3).toBe(3); }); it('Im the second test', async () => { expect(3).toBe(4); }); afterEach(() => { console.log({testStatus:testStatus, testName:testName, describeName:describeName}); }) });An my jest.config.js
const { defaults } = require("jest-config"); module.exports = { testEnvironment: './src/helpers/CustomNodeEnvironment.js', };An this is the log in which I have access to the detail of each test after its execution
I will try to improve the while to get the describe and test names.
Does this work if the test cases (the "test(..)") are running in parallel? Don't the test events get sent out of order?
just wanted to add that this would be super useful when using an XHR vcr like nock back. Right now I have to do this in each test
const { nockDone } = await nockBack('fixtureName.json')
this is literally exactly what i came here looking for. this is how i do it in playwright.
Just wanted to add a use-case to this kind of reflective-data available at runtime:
- Enabling any kind of global rule (in our case, a detector ensuring a mock is set for xhr's) with an iterative rollout. It would fail in too many places to fix if we attempted to enable and fix everything in a single change. So we want an allow-list of locations in the meantime. If we could identify each test we'd then have a way to roll it out slowly while having a todo-list of things to fix.
Specifically we'd love if the filepath itself would be available of the executing spec, but even the full test name (such as that returned by expect.getState().currentTestName) would be useful in this case.
This issue is stale because it has been open for 1 year with no activity. Remove stale label or comment or this will be closed in 30 days.
commenting to keep this request alive