The Tool Desk
Outbyte Driver Updater FREEFix the driver behind crashes, sound loss and screen glitchesFind Drivers →Outbyte PC Repair FREEClear out junk files and repair common Windows errorsFree Scan →Some links on this page are affiliate links: if you buy through them we may earn a commission, at no extra cost to you.
To verify that your app called window.alert() and supplied the expected message, register a stub as a listener for Cypress’s window:alert event before the action that triggers it. Cypress automatically accepts native alerts; the listener lets you inspect the alert text, not control whether the dialog is accepted.
The reliable pattern: listen for the alert event
For a typical end-to-end test, create a Sinon stub, attach it to Cypress’s window:alert event, perform the action, then assert that the stub received the expected text. Cypress documents this event-listener pattern and the alert message supplied to the handler in its Catalog of Events.
it('shows the expected alert', () => {
const alertStub = cy.stub().as('alert')
cy.on('window:alert', alertStub)
cy.get('button').click()
cy.get('@alert').should('have.been.calledOnceWith', 'Saved successfully')
})
Replace the button selector and expected string with the ones from your application. The important order is listener first, triggering action second, assertion afterward. Registering the listener before the action means the event is already being observed when the application calls alert().
Quick wins for a faster PC:
Repair Windows errors before they cause bigger problemsFix Now →Fix the driver behind crashes, sound loss and screen glitchesFind Drivers →The assertion checks both that the alert happened exactly once and that its argument matched. Checking only a message elsewhere on the page would not establish that the application invoked the native alert API.
#1 Best Overall
What Cypress means by “stub alert”
There are two related APIs, but they do different jobs:
cy.stub(object, method)replaces a method with a Sinon stub. A stub can record calls and, when appropriate, supply controlled behavior. See Cypress’s cy.stub() API.cy.on('window:alert', handler)listens for Cypress’s application event when the app callswindow.alert(). The event handler receives the alert text. It is an observation point for the native alert, not a way to replace or customize its behavior.
For ordinary end-to-end assertions about an alert, the second API is the direct solution. You can pass a standalone stub as the event handler, as in the example above, and then use Sinon call assertions on it. You do not need to replace the browser’s alert method just to capture the message.
Cypress automatically accepts native alerts. Its event documentation says, “You cannot change this behavior.” That limitation refers to the automatic acceptance of the alert; it does not prevent you from observing the event and asserting its text.
Choose setup based on when the alert can fire
End-to-end: alert caused by a later user action
When a click or other interaction triggers the alert, register cy.on('window:alert', ...) before issuing that interaction. Keep the listener and assertion in the test that exercises the behavior so the test’s intent remains clear.
it('alerts after saving', () => {
const alertStub = cy.stub()
cy.on('window:alert', alertStub)
cy.get('[data-cy="save"]').click()
cy.wrap(alertStub).should('have.been.calledOnceWith', 'Saved successfully')
})
This version keeps a direct reference to the stub and wraps it for a Cypress retryable assertion. Alternatively, alias the stub with .as('alert') and assert through cy.get('@alert'), as in the first example.
End-to-end: alert during application startup
If application code can call alert() as soon as the page loads, installing the event listener after the app has started may miss the event. Arrange setup before loading the app. Cypress documents window:before:load as firing before application JavaScript executes and at the same time as the cy.visit() onBeforeLoad callback. The event catalog describes these lifecycle points at Catalog of Events.
Rank #3
it('observes an alert on startup', () => {
const alertStub = cy.stub()
cy.on('window:before:load', () => {
cy.on('window:alert', alertStub)
})
cy.visit('/')
cy.wrap(alertStub).should('have.been.calledOnceWith', 'Welcome')
})
Use the startup hook only when the alert may occur during page initialization. For an alert triggered by a later click, registering directly before the click is simpler.
Component tests
Cypress component tests do not reload the page in the same way as an end-to-end visit. Cypress’s stub documentation shows that built-in methods can be stubbed before mounting the component. Apply your event listener or any required setup before mounting or performing the component action that could cause an alert. The cy.stub() API includes the component setup context.
Assert on one alert or a sequence
For one expected alert, make the call count explicit. A check for the right argument alone can pass even if the application unexpectedly fires the alert more than once.
Rank #4
cy.get('@alert').should('have.been.calledOnceWith', 'Saved successfully')
If multiple alerts are intentional, inspect their calls in order. Cypress’s event example demonstrates checking indexed calls; the stub records each alert invocation and its message argument.
it('shows the expected sequence', () => {
const alertStub = cy.stub()
cy.on('window:alert', alertStub)
cy.get('[data-cy="run-sequence"]').click().then(() => {
expect(alertStub.getCall(0)).to.be.calledWith('First message')
expect(alertStub.getCall(1)).to.be.calledWith('Second message')
expect(alertStub.getCall(2)).to.be.calledWith('Third message')
})
})
Use only as many indexed assertions as the behavior is meant to produce. If an exact total matters too, assert the expected call count as well as each message, so an extra alert does not go unnoticed.
Do these 3 things before closing this tab:
1Scan for outdated or missing drivers - takes under a minute2Repair Windows errors before they cause bigger problems3Fix the driver behind crashes, sound loss and screen glitchesDo not copy the confirm or prompt recipe
Browser dialogs may look similar in a test, but Cypress handles their control behavior differently. The distinctions documented in Cypress’s event catalog and Playwright migration guide are:
Best Value
| Browser API | Cypress behavior | Approach |
|---|---|---|
alert() |
Automatically accepted; the window:alert event does not change that behavior. |
Listen for window:alert and assert the captured message. |
confirm() |
Automatically accepted by default; returning false from window:confirm cancels it. |
Use the confirm event when you need to control acceptance or assert its message. |
prompt() |
Its method can be stubbed when the test needs to control the entered value. | Stub win.prompt before application code runs, such as in cy.visit()’s onBeforeLoad. |
For example, Cypress documents replacing prompt before app code loads like this:
cy.visit('/', {
onBeforeLoad(win) {
cy.stub(win, 'prompt').returns('Ada Lovelace')
},
})
That is a prompt-control example, not an alert assertion recipe. Cypress’s stubs, spies, and clocks guide also distinguishes a spy, which records calls while leaving the original function in place, from a stub, which replaces or controls a function. For observing native alert text, use the event listener instead of substituting a spy for the alert method.
Independent reader supportYour contribution helps us test, update, and keep practical guides available for everyone.Common failures and how to fix them
- The stub has no calls. Check that the listener was registered before the action. If the alert can happen during app startup, arrange setup before loading the app rather than after the visit.
- The test expects Cypress to leave the alert open. Cypress automatically accepts native alerts; the event lets you inspect the alert message but does not change that behavior.
- The test replaces
alertbut still misses startup behavior. When you genuinely need to replace a built-in window method, Cypress documents setting it up before application code loads withonBeforeLoad. For a normal alert assertion, prefer observingwindow:alert. - A prompt or confirm example behaves differently. Do not transfer their control patterns to alerts: prompt values can be stubbed, while confirm acceptance can be controlled through its event. Alert acceptance is automatic.
- The test manually restores a stub after each case. Cypress documents that
cy.stub()stubs are sandboxed and reset and restored between tests. See the stub API. - A call assertion passes but an extra alert is possible. Include the expected call count, or assert the exact sequence and total when the application is supposed to display several alerts.
Or skip the browser setup
For Cypress assertions, keep the event-listener pattern above: a screenshot cannot tell you whether alert() was called or what argument it received. If your separate task is to capture a website image or PDF rather than test dialog behavior, ScreenshotNeo offers a one-request screenshot API and an MCP server for AI agents.
For example, this cURL request saves a WebP screenshot of Stripe:
curl -G "https://api.screenshotneo.com/v1/shot" -d access_key=YOUR_API_KEY --data-urlencode url=https://stripe.com -o shot.webp
See the ScreenshotNeo API documentation for request options. Its clean-shot flow accepts cookie or consent banners like a visitor and removes more than 60 known consent platforms, newsletter popups, and chat widgets before capture; each step can be turned off. Bot checks, blank pages, timeouts, failed loads, and cache hits are not billed, and responses identify the page verdict and billing status in headers. AI agents can use its MCP server tools, including take_screenshot, get_page_info, and capture_pdf. The Free plan includes 1,000 shots per month with no card; paid plans start at $5 for 3,000 shots.
Sign up for ScreenshotNeo’s free plan to try 1,000 screenshots a month with no card.
Quick Recap
Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.
Recommended Free Tools

