Socket
Socket
Sign inDemoInstall

expect-playwright

Package Overview
Dependencies
Maintainers
2
Versions
23
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

expect-playwright - npm Package Compare versions

Comparing version 0.5.1 to 0.6.0

_config.yml

85

global.d.ts

@@ -1,2 +0,2 @@

// copied into our codebase for autocompletion purposes
// copied into our codebase for autocompletion purposes from 'playwright/types/types.d.ts' so we don't depend on it.
interface PageWaitForSelectorOptions {

@@ -17,5 +17,4 @@ /**

* using the
* [browserContext.setDefaultTimeout(…)](https://github.com/microsoft/playwright/blob/master/docs/api.md#browsercontextsetdefaulttimeout)
* or [page.setDefaultTimeout(…)](https://github.com/microsoft/playwright/blob/master/docs/api.md#pagesetdefaulttimeout)
* methods.
* [browserContext.setDefaultTimeout(timeout)](https://playwright.dev/docs/api/class-browsercontext#browser-context-set-default-timeout)
* or [page.setDefaultTimeout(timeout)](https://playwright.dev/docs/api/class-page#page-set-default-timeout) methods.
*/

@@ -27,2 +26,35 @@ timeout?: number

/**
* Will check if the element on the page determined by the selector is checked.
*/
toBeChecked(
selector: string,
options?: PageWaitForSelectorOptions
): Promise<R>
/**
* Will check if the element is checked.
*/
toBeChecked(options?: PageWaitForSelectorOptions): Promise<R>
/**
* Will check if the element on the page determined by the selector is disabled.
*/
toBeDisabled(
selector: string,
options?: PageWaitForSelectorOptions
): Promise<R>
/**
* Will check if the element is disabled.
*/
toBeDisabled(options?: PageWaitForSelectorOptions): Promise<R>
/**
* Will check if the element on the page determined by the selector is enabled.
*/
toBeEnabled(
selector: string,
options?: PageWaitForSelectorOptions
): Promise<R>
/**
* Will check if the element is enabled.
*/
toBeEnabled(options?: PageWaitForSelectorOptions): Promise<R>
/**
* Will check if the element's textContent on the page determined by the selector includes the given text.

@@ -42,2 +74,19 @@ * @deprecated Use toMatchText instead

/**
* Will check if an element's attribute on the page determined by the selector matches the given pattern.
*/
toMatchAttribute(
selector: string,
attribute: string,
value: RegExp | string,
options?: PageWaitForSelectorOptions
): Promise<R>
/**
* Will check if an element's attribute matches the given pattern.
*/
toMatchAttribute(
attribute: string,
value: RegExp | string,
options?: PageWaitForSelectorOptions
): Promise<R>
/**
* Will check if the element's textContent on the page determined by the selector matches the given pattern.

@@ -58,3 +107,27 @@ */

/**
* Will check if the page title matches a given string or regex.
*/
toMatchTitle(pattern: RegExp | string): Promise<R>
/**
* Will check if the page URL matches the given pattern.
*/
toMatchURL(value: RegExp | string): Promise<R>
/**
* Will check an element's value on the page determined by the selector matches the given pattern.
*/
toMatchValue(
selector: string,
value: RegExp | string,
options?: PageWaitForSelectorOptions
): Promise<R>
/**
* Will check an element's value matches the given pattern.
*/
toMatchValue(
value: RegExp | string,
options?: PageWaitForSelectorOptions
): Promise<R>
/**
* Will compare the element's textContent on the page determined by the selector with the given text.
* @deprecated - Use `toMatchText`
*/

@@ -68,2 +141,3 @@ toEqualText(

* Will compare the element's textContent by the given text.
* @deprecated - Use `toMatchText`
*/

@@ -96,2 +170,3 @@ toEqualText(value: string, options?: PageWaitForSelectorOptions): Promise<R>

* Will compare the element's value on the page determined by the selector with the given value.
* @deprecated - use `toMatchValue` instead
*/

@@ -105,2 +180,3 @@ toEqualValue(

* Will compare element's value with the given value.
* @deprecated - use `toMatchValue` instead
*/

@@ -110,2 +186,3 @@ toEqualValue(value: string, options?: PageWaitForSelectorOptions): Promise<R>

* Will assert the given URL with the page's URL
* @deprecated - use `toMatchURL` instead
*/

@@ -112,0 +189,0 @@ toEqualUrl(value: string): Promise<R>

30

lib/matchers/index.js

@@ -6,19 +6,33 @@ "use strict";

Object.defineProperty(exports, "__esModule", { value: true });
const toHaveText_1 = __importDefault(require("./toHaveText"));
const toBeChecked_1 = __importDefault(require("./toBeChecked"));
const toBeDisabled_1 = __importDefault(require("./toBeDisabled"));
const toBeEnabled_1 = __importDefault(require("./toBeEnabled"));
const toEqualText_1 = __importDefault(require("./toEqualText"));
const toEqualUrl_1 = __importDefault(require("./toEqualUrl"));
const toEqualValue_1 = __importDefault(require("./toEqualValue"));
const toHaveFocus_1 = __importDefault(require("./toHaveFocus"));
const toHaveSelector_1 = __importDefault(require("./toHaveSelector"));
const toEqualValue_1 = __importDefault(require("./toEqualValue"));
const toHaveSelectorCount_1 = __importDefault(require("./toHaveSelectorCount"));
const toEqualUrl_1 = __importDefault(require("./toEqualUrl"));
const toHaveFocus_1 = __importDefault(require("./toHaveFocus"));
const toHaveText_1 = __importDefault(require("./toHaveText"));
const toMatchAttribute_1 = __importDefault(require("./toMatchAttribute"));
const toMatchText_1 = __importDefault(require("./toMatchText"));
const toMatchTitle_1 = __importDefault(require("./toMatchTitle"));
const toMatchURL_1 = __importDefault(require("./toMatchURL"));
const toMatchValue_1 = __importDefault(require("./toMatchValue"));
exports.default = {
toHaveText: toHaveText_1.default,
toBeChecked: toBeChecked_1.default,
toBeDisabled: toBeDisabled_1.default,
toBeEnabled: toBeEnabled_1.default,
toEqualText: toEqualText_1.default,
toEqualUrl: toEqualUrl_1.default,
toEqualValue: toEqualValue_1.default,
toHaveFocus: toHaveFocus_1.default,
toHaveSelector: toHaveSelector_1.default,
toEqualValue: toEqualValue_1.default,
toHaveSelectorCount: toHaveSelectorCount_1.default,
toEqualUrl: toEqualUrl_1.default,
toHaveFocus: toHaveFocus_1.default,
toHaveText: toHaveText_1.default,
toMatchAttribute: toMatchAttribute_1.default,
toMatchText: toMatchText_1.default,
toMatchTitle: toMatchTitle_1.default,
toMatchURL: toMatchURL_1.default,
toMatchValue: toMatchValue_1.default,
};

@@ -6,3 +6,3 @@ "use strict";

try {
const { elementHandle, expectedValue } = await utils_1.getElementText(...args);
const [elementHandle, [expectedValue]] = await utils_1.getElementHandle(args);
/* istanbul ignore next */

@@ -9,0 +9,0 @@ const actualTextContent = await elementHandle.evaluate((el) => el.textContent);

@@ -6,3 +6,3 @@ "use strict";

try {
const { elementHandle, expectedValue } = await utils_1.getElementText(...args);
const [elementHandle, [expectedValue]] = await utils_1.getElementHandle(args);
/* istanbul ignore next */

@@ -9,0 +9,0 @@ const actualTextContent = await elementHandle.evaluate((el) => el.value);

@@ -5,5 +5,8 @@ "use strict";

const pass = await page
.waitForSelector(selector, options)
.then(() => true)
.catch(() => false);
.waitForSelector(selector, {
state: this.isNot ? "hidden" : "visible",
...options,
})
.then(() => !this.isNot)
.catch(() => this.isNot);
return {

@@ -10,0 +13,0 @@ pass: pass,

@@ -10,3 +10,3 @@ "use strict";

try {
const { elementHandle, expectedValue } = await utils_1.getElementText(...args);
const [elementHandle, [expectedValue]] = await utils_1.getElementHandle(args);
/* istanbul ignore next */

@@ -13,0 +13,0 @@ const actualTextContent = await elementHandle.evaluate((el) => el.textContent);

@@ -6,9 +6,9 @@ "use strict";

try {
const { elementHandle, expectedValue } = await utils_1.getElementText(...args);
const [elementHandle, [expectedValue]] = await utils_1.getElementHandle(args);
/* istanbul ignore next */
const actualTextContent = await elementHandle.evaluate((el) => el.textContent);
const res = actualTextContent === null || actualTextContent === void 0 ? void 0 : actualTextContent.match(expectedValue);
const actualValue = await elementHandle.evaluate((el) => el.textContent);
const pass = utils_1.compareText(expectedValue, actualValue);
return {
pass: !!res,
message: () => utils_1.getMessage(this, "toMatchText", expectedValue, actualTextContent),
pass,
message: () => utils_1.getMessage(this, "toMatchText", expectedValue, actualValue),
};

@@ -15,0 +15,0 @@ }

"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.getMessage = exports.quote = exports.getElementText = exports.getFrame = exports.detectExpectType = void 0;
const detectExpectType = (value) => {
const className = value.constructor.name;
const type = {
Page: 1 /* Page */,
Frame: 0 /* Frame */,
ElementHandle: 2 /* ElementHandle */,
}[className];
if (type === undefined) {
throw new Error(`could not recognize type: ${className}`);
}
return type;
exports.compareText = exports.getMessage = exports.quote = exports.getElementHandle = exports.getFrame = void 0;
const isElementHandle = (value) => {
return value.constructor.name === "ElementHandle";
};
exports.detectExpectType = detectExpectType;
const isElementHandle = (value) => exports.detectExpectType(value) === 2 /* ElementHandle */;
const getFrame = (value) => isElementHandle(value) ? value.contentFrame() : value;
const getFrame = async (value) => {
const resolved = await value;
return isElementHandle(resolved) ? resolved.contentFrame() : resolved;
};
exports.getFrame = getFrame;
const lastElementHasType = (args, type) => typeof args[args.length - 1] === type;
const getSelectorOptions = (args) => {
let selectorOptions = undefined;
if (args.length === 3 && lastElementHasType(args, "object")) {
selectorOptions = args[2];
}
if (args.length === 4 && lastElementHasType(args, "object")) {
selectorOptions = args[3];
}
return selectorOptions;
};
const getElementText = async (...args) => {
if (args.length > 1) {
const type = exports.detectExpectType(args[0]);
/**
* Handle the following cases:
* - expect(page).foo("bar")
* - expect(element).foo("bar")
*/
if (args.length === 2) {
if (type === 2 /* ElementHandle */) {
const iframe = await args[0].contentFrame();
const elem = iframe ? await iframe.$("body") : args[0];
return {
elementHandle: elem,
expectedValue: args[1],
};
}
const frame = args[0];
return {
elementHandle: (await frame.$("body")),
expectedValue: args[1],
};
const isObject = (value) => typeof value === "object" && !(value instanceof RegExp);
const getElementHandle = async (args, valueArgCount = 1) => {
var _a, _b;
// Pluck the options off the end first
const options = args.length > 1 && isObject(args[args.length - 1])
? args.pop()
: {};
// Next, pluck the number of args required by the matcher (defaults to 1)
const expectedValue = args.splice(-valueArgCount, valueArgCount);
// Finally, we can find the element handle
const handle = await args[0];
let elementHandle = (_a = (await exports.getFrame(handle))) !== null && _a !== void 0 ? _a : handle;
// If the user provided a page or iframe, we need to locate the provided
// selector or the `body` element if none was provided.
if (!isElementHandle(elementHandle)) {
const selector = (_b = args[1]) !== null && _b !== void 0 ? _b : "body";
try {
elementHandle = (await elementHandle.waitForSelector(selector, options));
}
/**
* Handle the following case:
* - expect(page).foo("#foo", "bar")
*/
const selector = args[1];
if (type === 1 /* Page */ || type === 0 /* Frame */) {
const frame = args[0];
const selectorOptions = getSelectorOptions(args);
try {
await frame.waitForSelector(selector, selectorOptions);
}
catch (err) {
throw new Error(`Timeout exceed for element ${exports.quote(selector)}`);
}
return {
elementHandle: (await frame.$(selector)),
expectedValue: args[2],
};
catch (err) {
throw new Error(`Timeout exceed for element ${exports.quote(selector)}`);
}
if (type === 2 /* ElementHandle */) {
const iframe = await args[0].contentFrame();
const elem = iframe ? await iframe.$("body") : args[0];
const selectorOptions = getSelectorOptions(args);
try {
await elem.waitForSelector(selector, selectorOptions);
}
catch (err) {
throw new Error(`Timeout exceed for element ${exports.quote(selector)}`);
}
return {
elementHandle: (await elem.$(selector)),
expectedValue: args[2],
};
}
}
throw new Error(`Invalid input length: ${args.length}`);
return [elementHandle, expectedValue];
};
exports.getElementText = getElementText;
exports.getElementHandle = getElementHandle;
const quote = (val) => (val === null ? "" : `'${val}'`);
exports.quote = quote;
const getMessage = ({ isNot, promise, utils }, matcher, expected, received) => {
const getMessage = ({ isNot, promise, utils, expand }, matcher, expected, received, expectedHint = undefined) => {
const message = isNot
? `Expected: not ${utils.printExpected(expected)}`
: `Expected: ${utils.printExpected(expected)}\n` +
`Received: ${utils.printReceived(received)}`;
return (utils.matcherHint(matcher, undefined, undefined, { isNot, promise }) +
: utils.printDiffOrStringify(expected, received, "Expected", "Received", expand);
return (utils.matcherHint(matcher, undefined, expectedHint, { isNot, promise }) +
"\n\n" +

@@ -104,1 +49,7 @@ message);

exports.getMessage = getMessage;
const compareText = (expectedValue, actualValue) => {
return typeof expectedValue === "string"
? expectedValue === actualValue
: expectedValue.test(actualValue !== null && actualValue !== void 0 ? actualValue : "");
};
exports.compareText = compareText;
{
"name": "expect-playwright",
"version": "0.5.1",
"version": "0.6.0",
"main": "lib/index.js",

@@ -12,7 +12,4 @@ "types": "./global.d.ts",

"start": "tsc --watch",
"test": "jest"
"test": "jest --maxWorkers=4"
},
"peerDependencies": {
"playwright-core": "^1.12.0"
},
"devDependencies": {

@@ -19,0 +16,0 @@ "@types/jest": "^26.0.23",

@@ -10,3 +10,3 @@ # expect-playwright

```txt
npm install -D expect-playwright playwright-core
npm install -D expect-playwright
```

@@ -16,12 +16,2 @@

### With Jest
To activate it in your Jest environment you have to include it in your configuration.
```json
{
"setupFilesAfterEnv": ["expect-playwright"]
}
```
### With [Playwright test runner](https://playwright.dev/docs/test-intro)

@@ -41,2 +31,12 @@

### With Jest
To activate it in your Jest environment you have to include it in your configuration.
```json
{
"setupFilesAfterEnv": ["expect-playwright"]
}
```
## Why do I need it

@@ -55,5 +55,17 @@

// after by using expect-playwright
await expect(page).toHaveText("#foo", "my text")
await expect(page).toMatchText("#foo", "my text")
```
But that's not all! Our matchers also work inside of iframes and accept an [ElementHandle] which targets an `iframe` element or a [Frame] obtained by calling `element.contentFrame()`. Not only that, but if you pass a promise, we will automatically resolve it for you!
```javascript
// before
const element = await page.$("iframe")
const frame = await element.contentFrame()
await expect(frame).toBeChecked("#foo")
// after
await expect(page.$("iframe")).toBeChecked("#foo")
```
## API documentation

@@ -63,28 +75,66 @@

- [toBeChecked](#toBeChecked)
- [toBeDisabled](#toBeDisabled)
- [toBeEnabled](#toBeEnabled)
- [toHaveFocus](#toHaveFocus)
- [toHaveSelector](#toHaveSelector)
- [toHaveSelectorCount](#toHaveSelectorCount)
- [toMatchText](#toMatchText)
- [toEqualText](#toEqualText)
- [toEqualValue](#toEqualValue)
- [toEqualUrl](#toEqualUrl)
- [toHaveFocus](#toHaveFocus)
- [toMatchTitle](#toMatchTitle)
- [toMatchURL](#toMatchURL)
- [toMatchValue](#toMatchValue)
### toHaveSelector
### toBeChecked
**expect(page: [Page]).toHaveSelector(selector: string, options?: [PageWaitForSelectorOptions](https://playwright.dev/docs/api/class-page/#pagewaitforselectorselector-options))**
This function checks if a given element is checked.
This function waits as a maximum as the timeout exceeds for a given selector once it appears on the page.
You can do this via a selector on the whole page:
```js
await expect(page).toHaveSelector("#foobar")
// or via not, useful to only wait 1 second instead of for the default timeout by Playwright which is 30 seconds.
await expect(page).not.toHaveSelector("#foobar", {
timeout: 1 * 1000,
})
```javascript
await expect(page).toBeChecked("#my-element")
```
Or by passing a Playwright [ElementHandle]:
```javascript
const element = await page.$("#my-element")
await expect(element).toBeChecked()
```
### toBeDisabled
This function checks if a given element is disabled.
You can do this via a selector on the whole page:
```javascript
await expect(page).toBeDisabled("#my-element")
```
Or by passing a Playwright [ElementHandle]:
```javascript
const element = await page.$("#my-element")
await expect(element).toBeDisabled()
```
### toBeEnabled
This function checks if a given element is enabled.
You can do this via a selector on the whole page:
```javascript
await expect(page).toBeEnabled("#my-element")
```
Or by passing a Playwright [ElementHandle]:
```javascript
const element = await page.$("#my-element")
await expect(element).toBeEnabled()
```
### toHaveFocus
**expect(page: [Page]).toHaveFocus(selector: string, options?: [PageWaitForSelectorOptions](https://playwright.dev/docs/api/class-page/#pagewaitforselectorselector-options))**
This function checks if the given selector has focus.

@@ -100,10 +150,14 @@

### toEqualUrl
### toHaveSelector
**expect(page: [Page]).toHaveSelector(value: string)**
This function waits as a maximum as the timeout exceeds for a given selector once it appears on the page.
This function checks if the given URL matches the current page's URL
```js
await expect(page).toHaveSelector("#foobar")
```
```javascript
await expect(page).toEqualUrl("https://github.com")
When used with `not`, `toHaveSelector` will wait until the element is not visible or not attached. See the Playwright [waitForSelector](https://playwright.dev/docs/api/class-page#page-wait-for-selector) docs for more details.
```js
await expect(page).not.toHaveSelector("#foobar")
```

@@ -113,4 +167,2 @@

**expect(page: [Page]).toHaveSelector(selector: string, value: number, options?: [PageWaitForSelectorOptions](https://playwright.dev/docs/api/class-page/#pagewaitforselectorselector-options))**
This function checks if the count of a given selector is the same as the provided value.

@@ -124,11 +176,9 @@

This function checks if the `textContent` of a given element matches the provided pattern.
This function checks if the `textContent` of a given element matches the provided string or regex pattern.
You can do this via a selector on the whole page:
**expect(page: [Page]).toMatchText(selector: string, pattern: RegExp | string, options?: [PageWaitForSelectorOptions](https://playwright.dev/docs/api/class-page/#pagewaitforselectorselector-options))**
```javascript
await expect(page).toMatchText("#my-element", "MyPattern")
await expect(page).toMatchText("#my-element", /MyPattern/)
await expect(page).toMatchText("#my-element", "Playwright")
await expect(page).toMatchText("#my-element", /Play.+/)
```

@@ -138,7 +188,5 @@

**expect(page: [Page]).toMatchText(pattern: RegExp | string)**
```javascript
await expect(page).toMatchText(/Playwright/)
await expect(page).toMatchText("Playwright")
await expect(page).toMatchText(/Play.+/)
```

@@ -148,48 +196,35 @@

**expect(element: [ElementHandle]).toHaveText(value: string)**
```javascript
const element = await page.$("#my-element")
await expect(element).toHaveText("Playwright")
await expect(element).toMatchText("Playwright")
await expect(element).toMatchText(/Play.+/)
```
### toEqualText
### toMatchTitle
This function checks if the `textContent` of a given element is the same as the provided value.
This function checks if the page or frame title matches the provided string or regex pattern.
You can do this via a selector on the whole page:
**expect(page: [Page]).toEqualText(selector: string, value: string, options?: [PageWaitForSelectorOptions](https://playwright.dev/docs/api/class-page/#pagewaitforselectorselector-options))**
```javascript
await expect(page).toEqualText("#my-element", "Playwright")
await expect(page).toMatchTitle("My app - page 1")
await expect(page).toMatchTitle(/My app - page \d/)
```
Or without a selector which will use the `body` element:
### toMatchURL
**expect(page: [Page]).toEqualText(value: string, options?: [PageWaitForSelectorOptions](https://playwright.dev/docs/api/class-page/#pagewaitforselectorselector-options))**
This function checks if the current page's URL matches the provided string or regex pattern.
```javascript
await expect(page).toEqualText("Playwright")
await expect(page).toMatchURL("https://github.com")
await expect(page).toMatchURL(/github\.com/)
```
Or by passing a Playwright [ElementHandle]:
### toMatchValue
**expect(element: [ElementHandle]).toEqualText(value: string, options?: [PageWaitForSelectorOptions](https://playwright.dev/docs/api/class-page/#pagewaitforselectorselector-options))**
This function checks if the `value` of a given element is the same as the provided string or regex pattern.
```javascript
const element = await page.$("#my-element")
await expect(element).toEqualText("Playwright")
```
### toEqualValue
This function checks if the `value` of a given element is the same as the provided value.
You can do this via a selector or the element directly:
**expect(page: [Page]).toEqualValue(selector: string, value: string, options?: [PageWaitForSelectorOptions](https://playwright.dev/docs/api/class-page/#pagewaitforselectorselector-options))**
```javascript
await expect(page).toEqualValue("#my-element", "Playwright")
await expect(page).toMatchValue("#my-element", "Playwright")
await expect(page).toMatchValue("#my-element", /Play.+/)
```

@@ -199,7 +234,6 @@

**expect(element: [ElementHandle]).toEqualValue(value: string, options?: [PageWaitForSelectorOptions](https://playwright.dev/docs/api/class-page/#pagewaitforselectorselector-options))**
```javascript
const element = await page.$("#my-element")
await expect(element).toEqualValue("Playwright")
await expect(element).toMatchValue("Playwright")
await expect(element).toMatchValue(/Play.+/)
```

@@ -217,5 +251,5 @@

await page.goto("https://github.com/microsoft/playwright")
await expect(page).toHaveText("#readme h1", "Playwright")
await expect(page).toMatchText("#readme h1", "Playwright")
// or also all of them via the not property
await expect(page).not.toHaveText("this-is-no-anywhere", {
await expect(page).not.toMatchText("this-is-no-anywhere", {
timeout: 1 * 1000,

@@ -242,4 +276,4 @@ })

[elementhandle]: https://github.com/microsoft/playwright/blob/master/docs/api.md#class-elementhandle
[page]: https://github.com/microsoft/playwright/blob/master/docs/api.md#class-page
[playwright]: https://github.com/microsoft/Playwright
[elementhandle]: https://playwright.dev/docs/api/class-elementhandle/
[frame]: https://playwright.dev/docs/api/class-frame/
[playwright]: https://playwright.dev
SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc