Skip to content

Commit e05c925

Browse files
committed
Clean Up Playwright Page Objects
1 parent 54740fe commit e05c925

14 files changed

Lines changed: 133 additions & 124 deletions

.eslintrc.js

Lines changed: 0 additions & 13 deletions
This file was deleted.

eslint.config.js

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
const tsPlugin = require(`@typescript-eslint/eslint-plugin`);
2+
const tsParser = require(`@typescript-eslint/parser`);
3+
4+
const nodeGlobals = {
5+
Buffer: `readonly`,
6+
__dirname: `readonly`,
7+
__filename: `readonly`,
8+
clearInterval: `readonly`,
9+
clearTimeout: `readonly`,
10+
console: `readonly`,
11+
exports: `readonly`,
12+
module: `readonly`,
13+
process: `readonly`,
14+
require: `readonly`,
15+
setInterval: `readonly`,
16+
setTimeout: `readonly`,
17+
};
18+
19+
module.exports = [
20+
{
21+
ignores: [
22+
`allure-results/**`,
23+
`html-report/**`,
24+
`logs/**`,
25+
`node_modules/**`,
26+
`playwright-report/**`,
27+
`test-results/**`,
28+
],
29+
},
30+
{
31+
files: [`**/*.{js,ts}`],
32+
languageOptions: {
33+
ecmaVersion: 2022,
34+
globals: nodeGlobals,
35+
sourceType: `module`,
36+
},
37+
},
38+
{
39+
files: [`**/*.ts`],
40+
languageOptions: {
41+
parser: tsParser,
42+
parserOptions: {
43+
ecmaVersion: 2022,
44+
sourceType: `module`,
45+
},
46+
},
47+
plugins: {
48+
'@typescript-eslint': tsPlugin,
49+
},
50+
rules: {
51+
...tsPlugin.configs.recommended.rules,
52+
'@typescript-eslint/no-explicit-any': `off`,
53+
'@typescript-eslint/no-require-imports': `off`,
54+
'@typescript-eslint/no-unused-vars': `off`,
55+
'@typescript-eslint/no-wrapper-object-types': `off`,
56+
},
57+
},
58+
];

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
},
99
"scripts": {
1010
"test": "cross-env ENV=%ENV% npx playwright test",
11-
"test:single": "cross-env ENV=%ENV% npx playwright test AlertsFrameWindows.test.ts --project=Chrome",
11+
"test:single": "cross-env ENV=%ENV% npx playwright test Interactions.test.ts --project=Chrome",
1212
"test:parallel": "cross-env ENV=%ENV% npx playwright test --grep @Smoke --project=Chrome",
1313
"test:serial": "cross-env ENV=%ENV% npx playwright test --grep @Smoke --workers=1 --project=Chrome",
1414
"test:serial:ci": "npx playwright test --grep @Smoke --workers=1 --project=Chrome",
Lines changed: 6 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { expect, Locator, Page, BrowserContext } from '@playwright/test';
1+
import { Locator, Page, BrowserContext } from '@playwright/test';
22

33
export class AlertsFrameWindowsPage {
44
readonly page: Page;
@@ -22,46 +22,26 @@ export class AlertsFrameWindowsPage {
2222
this.NESTED_CHILDFRAME_LOCATOR = page.frameLocator('#frame1').frameLocator('iframe').getByText('Child Iframe');
2323
}
2424

25-
async verifyNewTab(newTabUrlExpect): Promise<void> {
25+
async openNewTab(): Promise<Page> {
2626
// Start waiting for new page before clicking.
2727
const pagePromise = this.context.waitForEvent('page');
2828
await this.NEW_TAB_BUTTON.click();
2929
const newTab = await pagePromise;
3030
await newTab.waitForLoadState();
31-
const newTabUrlActual = newTab.url();
32-
//Verify New Tab URL
33-
expect(newTabUrlActual == newTabUrlExpect).toBeTruthy();
34-
//Verify Text displayed in New tab
35-
await expect(newTab.locator('#sampleHeading')).toContainText('This is a sample page');
36-
//Close New tab
37-
await newTab.close();
31+
return newTab;
3832
}
3933

40-
async verifyNewWindow(newWindowUrlExpect): Promise<void> {
34+
async openNewWindow(): Promise<Page> {
4135
const pagePromise = this.context.waitForEvent('page');
4236
await this.NEW_WINDOW_BUTTON.click();
4337
const newWindow = await pagePromise;
4438
await newWindow.waitForLoadState();
45-
const newWindowUrlActual = newWindow.url();
46-
//Verify New Tab URL
47-
expect(newWindowUrlActual == newWindowUrlExpect).toBeTruthy();
48-
//Close New Window
49-
await newWindow.close();
39+
return newWindow;
5040
}
5141

5242
async enterTextAndAccept(text: string): Promise<void> {
5343
//We have to accept the dialog before we perform action
5444
this.page.on('dialog', dialog => dialog.accept(text));
5545
await this.PROMPT_ALERT_BUTTON.click();
56-
expect(this.PROMPT_RESULT).toContainText(`You entered ${text}`); // Verify User has clicked on Cancel button
5746
}
58-
59-
async verifyFrameText(expectedFrameText: string): Promise<void> {
60-
const actualFrameText = await this.FRAME_LOCATOR.textContent();
61-
expect(expectedFrameText == actualFrameText).toBeTruthy();
62-
}
63-
64-
async verifyNestedFrameChildText() {
65-
expect(this.NESTED_CHILDFRAME_LOCATOR).toBeVisible();
66-
}
67-
}
47+
}

pageFactory/pageRepository/ElementsPage.ts

Lines changed: 9 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { expect, Locator, Page, BrowserContext } from '@playwright/test';
1+
import { Locator, Page, BrowserContext } from '@playwright/test';
22
import path from 'path';
33

44
export class ElementsPage {
@@ -31,7 +31,7 @@ export class ElementsPage {
3131
this.FULL_NAME_EDITBOX = page.getByPlaceholder(`Full Name`);
3232
this.SUBMIT_BUTTON = page.getByText(`Submit`);
3333
this.SUBMITTED_TEXT = page.getByText(`Name:AutoTest`, { exact: true }); // Matches exact text
34-
this.HOME_CHECK_BOX = page.getByText('Home');
34+
this.HOME_CHECK_BOX = page.getByRole('checkbox', { name: 'Select Home' });
3535
this.HOME_SELECTED_TEXT = page.locator(`#result`);
3636
this.NO_RADIO_BUTTON = page.locator(`#noRadio`); // Using CSS Selector
3737
this.WEB_TABLES_HEADER = page.getByRole('columnheader');
@@ -56,35 +56,19 @@ export class ElementsPage {
5656
await this.SUBMIT_BUTTON.click();
5757
}
5858

59-
async verifySubmittedText(): Promise<void> {
60-
await expect(this.SUBMITTED_TEXT).toBeVisible(); // Verifies if the text is visble on webpage
61-
}
62-
6359
async clickHomeCheckBox(): Promise<void> {
6460
await this.HOME_CHECK_BOX.check();
6561
}
6662

67-
async verifyHomeCheckboxSelectedText(): Promise<void> {
68-
await expect(this.HOME_SELECTED_TEXT).toContainText('home'); // Verifies if the locator contains text
69-
}
70-
71-
async verifyNoRadioButtonDisabled(): Promise<void> {
72-
expect(this.NO_RADIO_BUTTON).toBeDisabled()
73-
}
74-
75-
async verifyFirstColumnTableHeader(header: String): Promise<void> {
63+
async getFirstColumnTableHeader(): Promise<string> {
7664
const headerText = await this.WEB_TABLES_HEADER.allTextContents(); // Get all Text from WebTable Header
77-
expect(headerText[0] == header).toBeTruthy(); // Verify the First Column Header here we are comparing string values
65+
return headerText[0];
7866
}
7967

8068
async editCierraEntry(): Promise<void> {
8169
await this.WEB_TABLES_EDIT_ICON.click();
8270
}
8371

84-
async verifyRegistrationForm(): Promise<void> {
85-
await expect(this.REGISTRATION_FORM_HEADER).toBeVisible();
86-
}
87-
8872
async registrationFormClose(): Promise<void> {
8973
await this.REGISTRATION_FORM_CLOSE_BUTTON.click();
9074
}
@@ -93,29 +77,20 @@ export class ElementsPage {
9377
await this.DOUBLE_CLICK_BUTTON.dblclick();
9478
}
9579

96-
async verifyDoubleClickText(): Promise<void> {
97-
await expect(this.DOUBLE_CLICK_TEXT).toBeVisible();
98-
}
99-
10080
async rightClickButton(): Promise<void> {
10181
await this.RIGHT_CLICK_BUTTON.click({ button: 'right' }); // Right Click on button
10282
}
10383

104-
async verifyRightClickText(): Promise<void> {
105-
await expect(this.RIGHT_CLICK_TEXT).toBeVisible();
106-
}
107-
108-
async verifyNewBrowserTab(newPageURLExpected): Promise<void> {
84+
async openHomeLinkInNewTab(): Promise<Page> {
10985
// Start waiting for new page before clicking.
11086
const pagePromise = this.context.waitForEvent('page');
11187
await this.HOME_LINK.click();
11288
const newPage = await pagePromise;
11389
await newPage.waitForLoadState();
114-
const newPageURLActual = newPage.url();
115-
expect(newPageURLActual == newPageURLExpected).toBeTruthy();
90+
return newPage;
11691
}
11792

118-
async verifyFileDownload(): Promise<void> {
93+
async downloadFile(): Promise<void> {
11994
// Start waiting for download before clicking. Note no await.
12095
const downloadPromise = this.page.waitForEvent('download');
12196
await this.DOWNLOAD_BUTTON.click();
@@ -125,10 +100,9 @@ export class ElementsPage {
125100
await download.saveAs(path.join(__dirname, `../../Downloads`, download.suggestedFilename()));
126101
}
127102

128-
async verifyFileUpload(): Promise<void> {
103+
async uploadFile(): Promise<void> {
129104
// Select one file
130105
const uploadFilePath = path.join(__dirname, `../../utils/functional/sampleFile.jpeg`);
131106
await this.UPLOAD_BUTTON.setInputFiles(uploadFilePath);
132-
await expect(this.UPLOADED_FILE_TEXT).toBeVisible();
133107
}
134-
}
108+
}
Lines changed: 11 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,23 +1,23 @@
1-
import { expect, Locator, Page, BrowserContext } from '@playwright/test';
1+
import { Locator, Page, BrowserContext } from '@playwright/test';
22

33
export class InteractionsPage {
44
readonly page: Page;
55
readonly context: BrowserContext;
66
readonly DRAGGABLE: Locator;
7-
readonly DROPPABLE: Locator
7+
readonly DROPPABLE: Locator;
8+
readonly DROPPABLE_READY: Locator;
89

910
constructor(page: Page, context: BrowserContext) {
1011
this.page = page;
1112
this.context = context;
12-
this.DRAGGABLE = page.getByRole('tabpanel', { name: 'Simple' }).locator('#draggable');
13-
this.DROPPABLE = page.getByRole('tabpanel', { name: 'Simple' }).locator('#droppable');
13+
const simpleTab = page.getByRole('tabpanel', { name: 'Simple' });
14+
this.DRAGGABLE = simpleTab.locator('#draggable');
15+
this.DROPPABLE = simpleTab.locator('#droppable');
16+
this.DROPPABLE_READY = simpleTab.locator('#droppable.ui-droppable');
1417
}
1518

16-
async verifyDragandDrop(): Promise<void> {
17-
await this.DRAGGABLE.hover();
18-
await this.page.mouse.down();
19-
await this.DROPPABLE.hover();
20-
await this.page.mouse.up();
21-
await expect(this.DROPPABLE).toContainText('Dropped'); //Verify Dropped text
19+
async dragAndDrop(): Promise<void> {
20+
await this.DROPPABLE_READY.waitFor();
21+
await this.DRAGGABLE.dragTo(this.DROPPABLE);
2222
}
23-
}
23+
}

pageFactory/pageRepository/LoginPage.ts

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { Page, BrowserContext, Locator, expect } from '@playwright/test';
1+
import { Page, BrowserContext, Locator } from '@playwright/test';
22
import { WebActions } from "@lib/WebActions";
33
import { testConfig } from '../../testConfig';
44

@@ -37,7 +37,4 @@ export class LoginPage {
3737
await this.LOGIN_BUTTON.click();
3838
}
3939

40-
async verifyProfilePage(): Promise<void> {
41-
await expect(this.BOOKS_SEARCH_BOX).toBeVisible();
42-
}
43-
}
40+
}

pageFactory/pageRepository/WidgetsPage.ts

Lines changed: 3 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { expect, Locator, Page, BrowserContext } from '@playwright/test';
1+
import { Locator, Page, BrowserContext } from '@playwright/test';
22

33
export class WidgetsPage {
44
readonly page: Page;
@@ -26,16 +26,11 @@ export class WidgetsPage {
2626
await this.BLUE_COLOUR_TEXT.click();
2727
}
2828

29-
async verifyBlueColourSelected(): Promise<void> {
30-
await expect(this.BLUE_COLOUR_TEXT).toBeVisible();
31-
}
32-
33-
async verifyButtonTooltip(hoverText: string): Promise<void> {
29+
async hoverButtonForTooltip(): Promise<void> {
3430
await this.HOVER_BUTTON.hover(); //Hover over element
35-
await expect(this.TOOL_TIP_TEXT).toContainText(hoverText); // Verify Tooltip
3631
}
3732

3833
async oldStyleSelectColour(colourName: string): Promise<void> {
3934
await this.OLD_SELECT_MENU.selectOption(colourName);
4035
}
41-
}
36+
}
Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,23 @@
11
import test from '@lib/BaseTest';
2+
import { expect } from '@playwright/test';
23

34
test(`Verify Alerts, Frame & Windows Page`, { tag: '@Smoke'}, async ({ loginPage, alertsFrameWindowsPage, webActions }) => {
45
await loginPage.navigateToURL();
56
await webActions.clickByText('Alerts, Frame & Windows'); // Click on Alerts, Frame & Windows icon
67
await webActions.clickByText('Browser Windows'); // Click on Browser Windows navigation side bar
7-
await alertsFrameWindowsPage.verifyNewTab(`https://demoqa.com/sample`);
8-
await alertsFrameWindowsPage.verifyNewWindow(`https://demoqa.com/sample`);
8+
const newTab = await alertsFrameWindowsPage.openNewTab();
9+
expect(newTab.url()).toBe(`https://demoqa.com/sample`);
10+
await expect(newTab.locator(`#sampleHeading`)).toContainText(`This is a sample page`);
11+
await newTab.close();
12+
13+
const newWindow = await alertsFrameWindowsPage.openNewWindow();
14+
expect(newWindow.url()).toBe(`https://demoqa.com/sample`);
15+
await newWindow.close();
916
await webActions.clickByText('Alerts');
1017
await alertsFrameWindowsPage.enterTextAndAccept(`Hello`); // Enter Text Hello in alert prompt and click ok
18+
await expect(alertsFrameWindowsPage.PROMPT_RESULT).toContainText(`You entered Hello`);
1119
await webActions.clickByText('Frames');
12-
await alertsFrameWindowsPage.verifyFrameText('This is a sample page');
20+
await expect(alertsFrameWindowsPage.FRAME_LOCATOR).toHaveText(`This is a sample page`);
1321
await webActions.clickByText('Nested Frames');
14-
await alertsFrameWindowsPage.verifyNestedFrameChildText();
15-
});
22+
await expect(alertsFrameWindowsPage.NESTED_CHILDFRAME_LOCATOR).toBeVisible();
23+
});

tests/functional/Elements.test.ts

Lines changed: 15 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,30 +1,34 @@
11
import test from '@lib/BaseTest';
2+
import { expect } from '@playwright/test';
23

34
test(`Verify Elements Page`, { tag: '@Smoke'}, async ({ loginPage, elementsPage, webActions }) => {
45
await loginPage.navigateToURL();
56
await webActions.clickByText('Elements'); // Click on Elements Icon identified via text selector
67
await webActions.clickByText('Text Box'); //Click on TextBox Navigation Sidebar identified via text selector
78
await elementsPage.enterFullName(`AutoTest`);
89
await elementsPage.clickSubmit();
9-
await elementsPage.verifySubmittedText();
10+
await expect(elementsPage.SUBMITTED_TEXT).toBeVisible();
1011
await webActions.clickByText('Check Box');
1112
await elementsPage.clickHomeCheckBox();
12-
await elementsPage.verifyHomeCheckboxSelectedText();
13+
await expect(elementsPage.HOME_SELECTED_TEXT).toContainText(`home`);
1314
await webActions.clickByText('Radio Button');
14-
await elementsPage.verifyNoRadioButtonDisabled();
15+
await expect(elementsPage.NO_RADIO_BUTTON).toBeDisabled();
1516
await webActions.clickByText('Web Tables');
16-
await elementsPage.verifyFirstColumnTableHeader('First Name');
17+
expect(await elementsPage.getFirstColumnTableHeader()).toBe(`First Name`);
1718
await elementsPage.editCierraEntry();
18-
await elementsPage.verifyRegistrationForm();
19+
await expect(elementsPage.REGISTRATION_FORM_HEADER).toBeVisible();
1920
await elementsPage.registrationFormClose();
2021
await webActions.clickByText('Buttons');
2122
await elementsPage.doubleClickButton();
22-
await elementsPage.verifyDoubleClickText();
23+
await expect(elementsPage.DOUBLE_CLICK_TEXT).toBeVisible();
2324
await elementsPage.rightClickButton();
24-
await elementsPage.verifyRightClickText();
25+
await expect(elementsPage.RIGHT_CLICK_TEXT).toBeVisible();
2526
await webActions.clickByText('Upload and Download');
26-
await elementsPage.verifyFileDownload();
27-
await elementsPage.verifyFileUpload();
27+
await elementsPage.downloadFile();
28+
await elementsPage.uploadFile();
29+
await expect(elementsPage.UPLOADED_FILE_TEXT).toBeVisible();
2830
await webActions.clickByText('Links');
29-
await elementsPage.verifyNewBrowserTab("https://demoqa.com/");
30-
});
31+
const homePage = await elementsPage.openHomeLinkInNewTab();
32+
expect(homePage.url()).toBe(`https://demoqa.com/`);
33+
await homePage.close();
34+
});

0 commit comments

Comments
 (0)