Debug steps are diagnostic prints for ad hoc investigation: dump the current URL or the full HTML of the page to the console so you can diagnose a failing scenario without attaching a debugger. Drop one in right before the failing step, re-run, and read the output in your terminal (and in the per-step output of the HTML report).
Both steps are deliberately forgiving - they never fail a scenario. If the page is unavailable (for example nothing has been opened yet), they print an "unavailable" line with the underlying reason instead of throwing. And although they are registered as Then steps, Cucumber lets you write them with Then, When, or And, so they slot in anywhere mid-scenario.
They are strictly local-debug tooling: use them sparingly and strip them from feature files before merging. For evidence that stays in the branch, prefer the automatic failure screenshots, @javascript error capture, and the HTML report described under Tips below.
Quick reference
| Step | What it does |
|---|---|
Then print current URL | Print the current page URL to the console. |
Then print last response | Print the full page HTML (last response) to the console. |
Steps in detail
Then print current URL
Prints page.url() under a --- Current URL --- banner. Handy after redirects, form submissions, or logins when a later path assertion fails and you want to see where the browser actually ended up. Pairs well with the path steps you are debugging.
Given I am on "/about-us.html"
Then print current URL
Then print last response
Prints the full serialized HTML of the current page (page.content()) under a --- Last Response (HTML) --- banner. This is the live DOM - after JavaScript has run - so it is the ground truth for "why doesn't my selector match?". Expect a lot of output on real pages; pipe it to a file or search the terminal scrollback.
Given I am on homepage
Then print current URL
And print last response
Complete example
From tests/features/test--then--print-current-url-and-response.feature:
Feature: Debug helpers - print current URL and last response HTML
As a tester,
I want to dump the current URL and page HTML to the console
so that I can diagnose failures without attaching a debugger.
Scenario: Print both in the same scenario
Given I am on homepage
Then print current URL
And print last response
Scenario: Print current URL after navigating
Given I am on "/about-us.html"
Then print current URL
Tips
These two steps are one layer of a larger debugging toolkit. When a scenario fails you also have:
- Auto-screenshot on failure - every failed step writes a screenshot under
screenshots/. Control per run with env vars:WEBSHIP_SCREENSHOT_DIR(output directory),WEBSHIP_SCREENSHOT_PURGE=1(wipe the directory at run start),WEBSHIP_SCREENSHOT_ON_FAILED=0(disable),WEBSHIP_SCREENSHOT_ON_EVERY_STEP=1(screenshot every step),WEBSHIP_SCREENSHOT_FULLSCREEN=1(always full page). - Headed mode -
HEADLESS=false SLOW_MO=800 npm test(ornpm run test:headed) opens the browser and delays every action bySLOW_MOms so you can watch the scenario play out. - JS error capture - every scenario tracks
pageerrorandconsole.error; tag a scenario@javascriptto auto-fail on errors, or assert explicitly withThen there should be no JavaScript errors. - HTML report -
tests/reports/cucumber_report.htmlis regenerated after every run with per-step output (including these prints), durations, and screenshots. Disable withWEBSHIP_REPORT_DISABLE=1. Export a shareable PDF withnpx generate-reports --format pdf(page format, orientation, margins, and branded header/footer are all configurable via flags). - Scenario timing -
time npx cucumber-jsfor the whole run; the per-scenario breakdown can be extracted fromtests/reports/cucumber_report.json.
Common diagnoses
Frequent symptoms these prints (plus the toolkit above) help pin down:
| Symptom | Likely cause | Fix |
|---|---|---|
| Passes locally, fails in CI | Timing | Use a web-first assertion or edge wait |
| Flickering - sometimes passes | Race condition | wait for "selector" to appear instead of a fixed wait |
| Modal dialog is visible, but it should not be | Stale modal selector | Register a modal selector in your CMS preset |
page.goto: net::ERR_CONNECTION_REFUSED | Dev server not started | npm start in another terminal |
function has 0 arguments, should have 3 | Step regex captures missing in callback | Add the captured group params to the callback signature |
When a selector will not match, print last response is usually the fastest answer: it shows the DOM as it exists after JavaScript ran, which often differs from the served HTML source. When a path assertion fails, print current URL reveals unexpected redirects immediately.