vitest-dev/vitest · error · Error
Cannot take a screenshot outside of a test.
Error message
Cannot take a screenshot outside of a test.
What it means
page.screenshot() reads getWorkerState().current and throws if there is no active test. Screenshots must be bound to a test task so Vitest can attribute the image, track repeat counts, and write it to the right path; calling it from module top-level, setup hooks that run outside a test context (rare), or after the test has finished yields no current task.
Source
Thrown at packages/browser/src/client/tester/context.ts:315
iframeId: id,
} satisfies IframeViewportEvent)
return new Promise((resolve, reject) => {
channel.addEventListener('message', function handler(e) {
if (e.data.event === 'viewport:done' && e.data.iframeId === id) {
channel.removeEventListener('message', handler)
resolve()
}
if (e.data.event === 'viewport:fail' && e.data.iframeId === id) {
channel.removeEventListener('message', handler)
reject(new Error(e.data.error))
}
})
})
},
async screenshot(options = {}) {
const currentTest = getWorkerState().current
if (!currentTest) {
throw new Error('Cannot take a screenshot outside of a test.')
}
if (currentTest.concurrent) {
throw new Error(
'Cannot take a screenshot in a concurrent test because '
+ 'concurrent tests run at the same time in the same iframe and affect each other\'s environment. '
+ 'Use a non-concurrent test to take a screenshot.',
)
}
const repeatCount = currentTest.result?.repeatCount ?? 0
const taskName = getTaskFullName(currentTest)
const number = screenshotIds[repeatCount]?.[taskName] ?? 1
screenshotIds[repeatCount] ??= {}
screenshotIds[repeatCount][taskName] = number + 1
const nameView on GitHub (pinned to d568f8ce37)
Solutions
- Move the page.screenshot() call inside an it() / test() body.
- If it's in a detached async callback, await the callback within the test so it resolves before the test ends.
- For setup-time captures, take the screenshot inside the first test or use beforeEach.
Example fix
// before — top-level call, no active test
await page.screenshot()
it('loads home', () => { ... })
// after
it('loads home', async () => {
await page.screenshot()
}) Defensive patterns
Strategy: validation
Validate before calling
import { getWorkerState } from 'vitest'
const current = getWorkerState().current
if (current) {
await page.screenshot()
} else {
// not inside a test; skip or move the call
} Prevention
- Always call page.screenshot inside it()/test().
- Await any async work that calls page.screenshot so it resolves within the test.
When it happens
Trigger: Calling page.screenshot() at the top level of a test file, inside a beforeAll/beforeEach in certain non-test scopes, or in an async callback that resolves after the test has completed (detached promise). Defined at packages/browser/src/client/tester/context.ts:312-316.
Common situations: Taking a baseline screenshot at module load, calling page.screenshot() inside a setTimeout/setInterval callback that outlives the test, or invoking it from a utility invoked outside it()/test().
Related errors
- Cannot take a screenshot without a test path
- 'toMatchScreenshot' cannot be used without test context
- stopChunkTrace cannot be called outside of the test file.
- This command can only be called inside a test file.
- Cannot upload files outside of a test
AI-assisted analysis of vitest-dev/vitest@d568f8ce37 (2026-08-03).
Data as JSON: /data/errors/c141002116b3d322.json.
Report an issue: GitHub.