UNPKG

playwright-cucumber-ts-steps

Version:

A collection of reusable Playwright step definitions for Cucumber in TypeScript, designed to streamline end-to-end testing across web, API, and mobile applications.

646 lines (645 loc) 23.7 kB
import type { DataTable } from "@cucumber/cucumber"; import { CustomWorld } from "../helpers/world"; /** * Enables fake timers for the current page, fixing the time at the moment this step is executed. * This is useful for testing time-dependent UI components without actual time passing. * * ```gherkin * When I use fake timers * ``` * * @example * When I use fake timers * And I go to "/countdown-page" * When I advance timers by 1000 milliseconds * Then I should see text "9 seconds remaining" * * @remarks * This step uses Playwright's `page.clock.setFixedTime()` to control the browser's internal * clock. All subsequent time-related operations (like `setTimeout`, `setInterval`, `Date.now()`) * will operate based on this fixed time. Use {@link When_I_advance_timers_by_milliseconds | "When I advance timers by X milliseconds"} * or {@link When_I_advance_timers_by_seconds | "When I advance timers by X seconds"} to progress time. * To revert, use {@link When_I_use_real_timers | "When I use real timers"}. * @category Timer Steps */ export declare function When_I_use_fake_timers(this: CustomWorld): Promise<void>; /** * Restores real timers for the current page, releasing control over the browser's internal clock. * * ```gherkin * When I use real timers * ``` * * @example * When I use fake timers * When I advance timers by 10 seconds * When I use real timers * * @remarks * This step uses Playwright's `page.clock.useRealTimers()`. After this step, `setTimeout`, `setInterval`, * and other time-related functions will behave normally, using the system's real time. * @category Timer Steps */ export declare function When_I_use_real_timers(this: CustomWorld): Promise<void>; export declare function When_I_advance_timers_by_milliseconds(this: CustomWorld, ms: number): Promise<void>; /** * Advances fake timers by the given number of seconds. Requires fake timers to be enabled. * * ```gherkin * When I advance timers by {int} seconds * ``` * * @param seconds - The number of seconds to advance the fake clock by. * * @example * When I use fake timers * When I advance timers by 2 seconds * * @remarks * This step converts seconds to milliseconds and uses Playwright's `page.clock.tick()`. * It will only have an effect if {@link When_I_use_fake_timers | "When I use fake timers"} * has been called previously. If real timers are active, a warning will be logged. * @category Timer Steps */ export declare function When_I_advance_timers_by_seconds(this: CustomWorld, seconds: number): Promise<void>; /** * Waits for the given number of seconds using `setTimeout`. This is a real-time wait. * * ```gherkin * When I wait {int} second[s] * ``` * * @param seconds - The number of seconds to wait. * * @example * When I wait 3 seconds * * @remarks * This step pauses test execution for the specified duration using Node.js `setTimeout`. * It's generally preferred to use explicit waits for element conditions (e.g., `toBeVisible`) * over arbitrary waits, but this can be useful for debugging or waiting for external factors. * @category General Action Steps */ export declare function When_I_wait_seconds(seconds: number): Promise<void>; /** * Waits for the given number of milliseconds using `setTimeout`. This is a real-time wait. * * ```gherkin * When I wait {int} millisecond[s] * ``` * * @param ms - The number of milliseconds to wait. * * @example * When I wait 500 milliseconds * * @remarks * This step pauses test execution for the specified duration using Node.js `setTimeout`. * It's generally preferred to use explicit waits for element conditions (e.g., `toBeVisible`) * over arbitrary waits, but this can be useful for debugging or waiting for external factors. * @category General Action Steps */ export declare function When_I_wait_milliseconds(this: CustomWorld, ms: number): Promise<void>; /** * Sets the default step timeout for all subsequent Cucumber steps. * This can override the global timeout set in `cucumber.js` configuration. * * ```gherkin * When I set step timeout to {int} ms * ``` * * @param timeoutMs - The new default timeout in milliseconds. * * @example * When I set step timeout to 10000 ms * And I find element by selector "#slow-loading-element" * * @remarks * This step uses Cucumber's `setDefaultTimeout()` function. It applies to all following * steps within the same test run. Use with caution as setting very high timeouts can * hide performance issues. * @category Configuration Steps */ export declare function When_I_set_step_timeout_to(this: CustomWorld, timeoutMs: number): void; /** * Triggers a generic DOM event of the given type on the element matching the provided selector. * * ```gherkin * When I trigger {string} event on {string} * ``` * * @param eventType - The type of DOM event to trigger (e.g., "change", "input", "focus"). * @param selector - The CSS selector of the element to trigger the event on. * * @example * When I trigger "change" event on ".my-input" * * @remarks * This step uses Playwright's `locator.evaluate()` to dispatch a new `Event` directly * on the DOM element. It can be useful for simulating browser-level events that * might not be covered by Playwright's high-level actions (like `fill` for `input` events). * @category Event Steps */ export declare function When_I_trigger_event_on_selector(this: CustomWorld, eventType: string, selector: string): Promise<void>; /** * Triggers a generic DOM event of the given type on the previously selected element. * * ```gherkin * When I trigger event {string} * ``` * * @param eventName - The name of the event to dispatch (e.g., "change", "input", "blur"). * * @example * When I find element by selector ".my-input" * And I trigger event "change" * * @remarks * This step requires a preceding step that sets the {@link CustomWorld.element | current element}. * It uses Playwright's `locator.dispatchEvent()` to dispatch the specified event. * @category Event Steps */ export declare function When_I_trigger_event(this: CustomWorld, eventName: string): Promise<void>; /** * Removes focus from the previously selected element. * * ```gherkin * When I blur * ``` * * @example * When I find element by selector "input[name='username']" * And I blur * * @remarks * This step requires a preceding step that sets the {@link CustomWorld.element | current element}. * It uses `locator.evaluate()` to call the DOM `blur()` method on the element, * simulating a loss of focus. * @category Event Steps */ export declare function When_I_blur(this: CustomWorld): Promise<void>; /** * Focuses the previously selected element. * * ```gherkin * When I focus * ``` * * @example * When I find element by selector "input[name='search']" * And I focus * * @remarks * This step requires a preceding step that sets the {@link CustomWorld.element | current element}. * It uses Playwright's `locator.focus()` to bring the element into focus, simulating * a user tabbing to or clicking on the element. * @category Event Steps */ export declare function When_I_focus(this: CustomWorld): Promise<void>; /** * Logs a message to the test output (stdout/console). * * ```gherkin * When I log {string} * ``` * * @param message - The string message to log. * * @example * When I log "Test scenario started" * * @remarks * This step is useful for injecting debugging or informative messages directly * into the Cucumber test report or console output during test execution. * @category Debugging Steps */ export declare function When_I_log(this: CustomWorld, message: string): Promise<void>; /** * Triggers a debugger statement, pausing test execution if a debugger is attached. * * ```gherkin * When I debug * ``` * * @example * When I find element by selector "#problematic-button" * And I debug * When I click current element * * @remarks * This step is extremely useful for interactive debugging. When executed with a debugger * (e.g., VS Code debugger attached to your Node.js process), it will pause execution * at this point, allowing you to inspect the browser state, variables, etc. * @category Debugging Steps */ export declare function When_I_debug(): Promise<void>; /** * Takes a full-page screenshot of the current page and saves it with the given name. * The screenshot will be saved in the `e2e/screenshots/` directory (relative to your project root). * * ```gherkin * When I screenshot {string} * ``` * * @param name - The desired filename for the screenshot (without extension). * * @example * When I screenshot "dashboard-view" * * @remarks * This step creates a PNG image. The `fullPage: true` option ensures that the * entire scrollable height of the page is captured. * @category Screenshot Steps */ export declare function When_I_screenshot_named(this: CustomWorld, name: string): Promise<void>; /** * Takes a full-page screenshot of the current page and saves it with a timestamped filename. * The screenshot will be saved in the `screenshots/` directory (relative to your project root). * * ```gherkin * When I screenshot * ``` * * @example * When I screenshot * * @remarks * This step is useful for quick visual debugging or capturing the state of the UI at * various points in the test without needing to manually name each file. * The filename will be in the format `screenshots/screenshot-TIMESTAMP.png`. * @category Screenshot Steps */ export declare function When_I_screenshot(this: CustomWorld): Promise<void>; /** * Navigates the browser to the given URL or an aliased URL. * If a relative path is provided (starts with `/`), it will be prepended with `process.env.BASE_URL`. * * ```gherkin * When I visit {string} * ``` * * @param urlOrAlias - The URL to visit, or an alias (prefixed with `@`) pointing to a URL. * * @example * When I visit "/dashboard" * When I visit "https://www.example.com" * Given I store "https://my.app.com/profile" as "profilePageUrl" * When I visit "@profilePageUrl" * * @remarks * This step uses Playwright's `page.goto()`. Ensure `BASE_URL` environment variable is set * if you are using relative paths. * @category Page Navigation Steps */ export declare function When_I_visit(this: CustomWorld, urlOrAlias: string): Promise<void>; /** * Reloads the current page. * * ```gherkin * When I reload the page * ``` * * @example * When I reload the page * * @remarks * This step is equivalent to hitting the browser's reload button. * It uses Playwright's `page.reload()`. * @category Page Navigation Steps */ export declare function When_I_reload_the_page(this: CustomWorld): Promise<void>; /** * Navigates back in the browser's history. * * ```gherkin * When I go back * ``` * * @example * Given I visit "/page1" * And I visit "/page2" * When I go back * Then I should be on "/page1" * * @remarks * This step is equivalent to hitting the browser's back button. * It uses Playwright's `page.goBack()`. * @category Page Navigation Steps */ export declare function When_I_go_back(this: CustomWorld): Promise<void>; /** * Navigates forward in the browser's history. * * ```gherkin * When I go forward * ``` * * @example * Given I visit "/page1" * And I visit "/page2" * When I go back * When I go forward * Then I should be on "/page2" * * @remarks * This step is equivalent to hitting the browser's forward button. * It uses Playwright's `page.goForward()`. * @category Page Navigation Steps */ export declare function When_I_go_forward(this: CustomWorld): Promise<void>; /** * Pauses the test execution in debug mode. * This is useful for inspecting the browser state interactively during test runs. * * ```gherkin * When I pause * ``` * * @example * When I perform an action * And I pause * Then I assert something visually * * @remarks * When running tests in debug mode (e.g., with `npx playwright test --debug`), * this step will open Playwright's inspector, allowing you to step through * actions, inspect elements, and troubleshoot. The test will resume when you * continue from the inspector. * @category Debugging Steps */ export declare function When_I_pause(this: CustomWorld): Promise<void>; /** * Stores a new date calculated by offsetting an existing aliased date by a given amount and unit. * * ```gherkin * When I store {string} {int} {word} {word} as "{word}" * ``` * * @param baseAlias - The alias of an existing date string in `this.data` (e.g., "today"). * @param amount - The numerical amount to offset by (e.g., 2, 5). * @param unit - The unit of time (e.g., "days", "months", "hours"). * @param direction - Whether to offset "before" or "after" the base date. * @param newAlias - The alias under which to store the newly calculated date. * * @example * Given I store "2024-01-15" as "invoiceDate" * When I store "invoiceDate" 30 days after as "dueDate" * Then the value of alias "dueDate" should be "2024-02-14" * * @remarks * This step uses the `dayjs` library for date manipulation. The `baseAlias` must * point to a valid date string that `dayjs` can parse. The `unit` must be one of: * "second", "minute", "hour", "day", "week", "month", "year" (plural forms also supported). * The new date is stored in `this.data` in "YYYY-MM-DD" format. * @category Data Manipulation Steps */ export declare function When_I_store_date_offset(this: CustomWorld, baseAlias: string, amount: number, unit: string, direction: string, // "before" or "after" newAlias: string): Promise<void>; /** * Switches the current Playwright context to an iframe located by a CSS selector. * The step waits for the iframe's `body` element to be visible before proceeding. * * ```gherkin * When I switch to iframe with selector {string} * ``` * * @param selector - The CSS selector for the iframe element (e.g., "#my-iframe", "iframe[name='chatFrame']"). * * @example * When I switch to iframe with selector "#payment-form-iframe" * And I find element by placeholder text "Card Number" * And I type "1234..." * * @remarks * Once inside an iframe, all subsequent element finding and interaction steps will * target elements within that iframe. To exit the iframe context, use * {@link When_I_exit_iframe | "When I exit iframe"}. * @category IFrame Steps */ export declare function When_I_switch_to_iframe_with_selector(this: CustomWorld, selector: string): Promise<void>; /** * Switches the current Playwright context to an iframe located by its title attribute. * * ```gherkin * When I switch to iframe with title {string} * ``` * * @param title - The title of the iframe to switch to. * * @example * When I switch to iframe with title "My Iframe" * And I find element by label text "Card Holder" * * @remarks * This step iterates through all frames on the page to find one whose title matches * (case-insensitively, partially matched with `includes`). Once found, subsequent * element operations will target elements within this iframe. To exit, use * {@link When_I_exit_iframe | "When I exit iframe"}. * @category IFrame Steps */ export declare function When_I_switch_to_iframe_with_title(this: CustomWorld, title: string): Promise<void>; /** * Switches the current Playwright context to an iframe located by a CSS selector, * and then waits for specific text to become visible inside that iframe. * * ```gherkin * When I switch to iframe with selector {string} and wait for text {string} * ``` * * @param selector - The CSS selector for the iframe element. * @param expectedText - The text string to wait for inside the iframe. * * @example * When I switch to iframe with selector "#dynamic-content-iframe" and wait for text "Content Loaded" * * @remarks * This step combines switching into an iframe with a wait condition, which is * useful for dynamic iframe content. The `expectedText` must be present * and visible inside the iframe. To exit the iframe context, use * {@link When_I_exit_iframe | "When I exit iframe"}. * @category IFrame Steps */ export declare function When_I_switch_to_iframe_with_selector_and_wait_for_text(this: CustomWorld, selector: string, expectedText: string): Promise<void>; /** * Exits the current iframe context, returning the Playwright context to the main page. * All subsequent element finding and interaction steps will operate on the main page. * * ```gherkin * When I exit iframe * ``` * * @example * When I switch to iframe with selector "#my-iframe" * And I fill "my data" * When I exit iframe * And I click "Main Page Button" * * @remarks * This step is crucial for navigating back to the main document after interacting * with elements inside an iframe. It sets `this.frame` back to `undefined` (or the main page locator). * @category IFrame Steps */ export declare function When_I_exit_iframe(this: CustomWorld): void; /** * Performs a specified action (e.g., click, hover, check, uncheck, focus, blur) * on a subset of the previously stored elements (first N, last N, or random N). * * ```gherkin * When I {word} the {word} {int} * ``` * * @param action - The action to perform (e.g., "click", "hover", "check", "uncheck", "focus", "blur", "fill"). * @param mode - The selection mode: "first", "last", or "random". * @param count - The number of elements to apply the action to. * @param table - (Optional) A Cucumber DataTable for action-specific options (e.g., `ClickOptions`). * * @example * Given I find elements by selector ".item-checkbox" * When I check the first 2 * When I hover the last 3 * * @remarks * This step requires that `this.elements` (a Playwright `Locator` that points to multiple * elements) has been populated by a preceding step (e.g., `When I find elements by selector`). * The `action` must be one of the supported actions. The `count` specifies how many of * the matched elements to target. * @category Multi-Element Action Steps */ export declare function When_I_perform_action_on_subset_of_elements(this: CustomWorld, action: string, mode: string, count: number, table?: DataTable): Promise<void>; /** * Performs a specified action (e.g., click, hover, check, uncheck, focus, blur) * on the Nth element of the previously stored elements collection. * * ```gherkin * When I {word} the {int}(?:st|nd|rd|th) element * ``` * * @param action - The action to perform (e.g., "click", "hover", "check", "uncheck", "focus", "blur", "fill"). * @param nth - The 1-based index of the element to target (e.g., 1 for 1st, 2 for 2nd). * @param table - (Optional) A Cucumber DataTable for action-specific options. * * @example * Given I find elements by selector ".product-card" * When I click the 2nd element * When I fill the 1st element * * @remarks * This step requires that `this.elements` has been populated by a preceding step. * It targets a single element at a specific 1-based ordinal position within that collection. * The `action` must be one of the supported actions. * @category Multi-Element Action Steps */ export declare function When_I_perform_action_on_nth_element(this: CustomWorld, action: string, nth: number, table?: DataTable): Promise<void>; /** * Presses a specific key on the previously selected element. * * ```gherkin * When I press key {string} * ``` * * @param key - The key to press (e.g., "Enter", "Escape", "ArrowDown", "Tab"). * * @example * When I find element by selector "input[name='email']" * And I type "my query" * When I press key "Enter" * * @remarks * This step requires a preceding step that sets the {@link CustomWorld.element | current element}. * It first focuses the element and then simulates a key press. * This is useful for triggering keyboard shortcuts or submitting forms via "Enter". * @category Keyboard Interaction Steps */ export declare function When_I_press_key(this: CustomWorld, key: string): Promise<void>; /** * Sets the browser viewport to emulate a specific Playwright device profile and orientation. * This will close the current browser context and open a new one with the specified device settings. * * ```gherkin * When I set viewport to {string} * When I set viewport to {string} and {string} * ``` * * @param deviceInput - The name of the Playwright device (e.g., "iPhone 12", "iPad", "Desktop Chrome"). * @param orientation - (Optional) The orientation, either "landscape" or "portrait" (default if not specified). * * @example * When I set viewport to "iPhone 12" * When I set viewport to "iPad" and "landscape" * * @remarks * This step creates a *new* browser context and page, so any previous page state or * setup (like routes, localStorage) will be reset. * The `deviceInput` is normalized to match Playwright's `devices` object keys. * @category Browser Context Steps */ export declare function When_I_set_viewport_to_device(this: CustomWorld, deviceInput: string, orientation?: string): Promise<void>; /** * Sets the viewport to the given width and height in pixels. * This will close the current browser context and open a new one with the specified dimensions. * * ```gherkin * When I set viewport to {int}px by {int}px * ``` * * @param width - The desired viewport width in pixels. * @param height - The desired viewport height in pixels. * * @example * When I set viewport to 1280px by 720px * * @remarks * This step creates a *new* browser context and page, so any previous page state or * setup (like routes, localStorage) will be reset. * @category Browser Context Steps */ export declare function When_I_set_viewport_to_dimensions(this: CustomWorld, width: number, height: number): Promise<void>; /** * Sets a specific Playwright page configuration property to the given value. * This can be used to dynamically change page-level settings during a test. * * ```gherkin * When I set Playwright config {word} to {string} * ``` * * @param key - The name of the Playwright `Page` property to set (e.g., "userAgent", "defaultTimeout"). * @param value - The string value to set the property to. Note: All values are treated as strings. * * @example * When I set Playwright config "userAgent" to "MyCustomAgent" * * @remarks * This step directly assigns a value to a property on the `this.page` object. * It's important to know which properties are settable and what their expected * types are. Using incorrect keys or values may lead to unexpected behavior or errors. * Not all Playwright page properties are designed to be set this way after page creation. * @category Configuration Steps */ export declare function When_I_set_playwright_page_config_key(this: CustomWorld, key: string, value: string): Promise<void>; /** * Sets multiple Playwright page configuration properties using a data table. * * ```gherkin * When I set Playwright config * | key | value | * | userAgent | MyAgent | * | defaultTimeout | 5000 | * ``` * * @param table - A Cucumber DataTable with two columns: `key` (the property name) * and `value` (the string value to set). * * @example * When I set Playwright config * | key | value | * | userAgent | TestBot | * | defaultTimeout | 10000 | * * @remarks * Similar to the single-key version, this step dynamically assigns values to * properties on the `this.page` object. All values from the data table are * treated as strings. Use with caution, understanding which properties can * be dynamically set. * @category Configuration Steps */ export declare function When_I_set_playwright_page_config_from_table(this: CustomWorld, table: DataTable): Promise<void>;