@qavajs/po-playwright
v0.16.1
Published
library for plain-english access to page object
Downloads
1,034
Keywords
Readme
@qavajs/po-playwright
This library provides the ability to create hierarchical page objects and access elements using plain-english selectors. Works on top of Playwright.
npm install @qavajs/po-playwright
Usage
Lib provides getElement method that resolves plain-english selector and return playwright locator.
const { po } = require('@qavajs/po-playwright');
When(/^click '(.+)'$/, async function (alias) {
const element = await po.getElement(alias);
await element.click();
});
When click '#1 of Multiple Component > Child Item'
Lib provides capability to get single element from collection by index (#index of Collection) or inner text (#text in Collection).
Create page object
Lib provides two methods $ and $$ that allow registering elements and collections. An element can be defined in form of webdriverIO selector or as an instance of the component class.
Each not top-level component should have selector element in form of webdriverIO selector.
const { $, $$ } = require('@qavajs/po-playwright');
class MultipleComponent {
selector = '.list-components li';
ChildItem = $('div');
}
class SingleComponent {
selector = '.container';
ChildItem = $('.child-item');
}
class App {
SingleElement = $('.single-element');
List = $$('.list li');
SingleComponent = $(new SingleComponent());
MultipleComponents = $$(new MultipleComponent());
}
module.exports = new App();
Register PO
Before using po object need to be initiated and hierarchy of elements needs to be registered The best place to do it is cucumber-js Before hook
const { po } = require('@qavajs/po-playwright');
const pos = require('./app.js');
Before(async function() {
po.init(page, { timeout: 10000 }); // page is an instance of playwright page
po.register(pos); // pos is page object hierarchy
});
Ignore hierarchy
In case if child element and parent component doesn't have hierarchy dependency it's possible to pass extra parameter ignoreHierarchy parameter to start traverse from root
class ComponentThatDescribesNotWellDesignedDOMTree {
selector = '.container';
//ignoreHierarchy will ignore component selector .container and start traverse from root
ChildItem = $('.child-item', { ignoreHierarchy: true });
}
Optional selector property
If selector property is not provided for Component then parent element will be returned
class ParentComponent {
selector = '.container';
ChildComponent = $(new ChildComponent());
}
class ChildComponent {
//Element will be searched in parent .container element
Element = $('.someElement');
}
Dynamic selectors
In case you need to generate selector based on some data you can use dynamic selectors
const { Selector } = require('@qavajs/po-playwright');
class Component {
selector = '.container';
Element = $(Selector((index => `div:nth-child(${index})`))); // function should return valid selector
}
Then you can pass parameter to this function from Gherkin file
When I click 'Component > Element (2)'
Native framework selectors
It is also possible to use driver-built capabilities to return element. You can pass handler that has access to
current page
and current locator.
const { NativeSelector } = require('@qavajs/po-playwright');
class Component {
selector = '.container';
Element = $(NativeSelector(page => page.getByText(`some text`)));
IFrame = $(NativeSelector((_, parent) => parent.frameLocator('#iframe').getByText(`some text`)));
}