Sets up the core infrastructure for Playwright-based automated testing, including: - Docker support for consistent environments - Azure Pipelines configuration for CI/CD - Page Object Model structure for maintainable tests - Test data, validation, and rule engine implementation - Test configuration for alerts and other scenarios
142 lines
No EOL
5.3 KiB
TypeScript
142 lines
No EOL
5.3 KiB
TypeScript
import { expect, type Locator, type Page } from '@playwright/test';
|
|
import { BasePage } from './BasePage';
|
|
|
|
export class InsuranceBasePage extends BasePage {
|
|
readonly cookieContinueButton: Locator;
|
|
readonly continueWithSafeliteButton: Locator;
|
|
|
|
constructor(page: Page) {
|
|
super(page);
|
|
|
|
// Targeting continue buttons with multiple selectors
|
|
this.cookieContinueButton = page.locator([
|
|
'button:has-text("Continue")',
|
|
'button#navNext.btn-success',
|
|
'button[name="navNext"][type="submit"]',
|
|
'.btn-success:has-text("Continue")'
|
|
].join(', '));
|
|
|
|
// Targeting "Continue with Safelite" buttons
|
|
this.continueWithSafeliteButton = page.locator([
|
|
'button:has-text("Continue with Safelite")',
|
|
'button#navNext:has-text("Safelite")',
|
|
'.btn-success:has-text("Continue with Safelite")'
|
|
].join(', '));
|
|
}
|
|
|
|
/**
|
|
* Navigates to the next page in the insurance flow
|
|
* Overrides the BasePage nextPage() method to handle insurance modal buttons
|
|
*/
|
|
async nextPage() {
|
|
const startingUrl = this.page.url();
|
|
let attemptCount = 0;
|
|
const maxAttempts = 3;
|
|
|
|
while (attemptCount < maxAttempts) {
|
|
try {
|
|
// Try navNext ID button first
|
|
const navNextButton = this.page.locator('#navNext:visible');
|
|
if (await navNextButton.count() > 0) {
|
|
await navNextButton.click();
|
|
await this.page.waitForTimeout(500);
|
|
}
|
|
// Try button with Continue text
|
|
else if (await this.cookieContinueButton.isVisible({ timeout: 2000 })) {
|
|
await this.cookieContinueButton.click();
|
|
await this.page.waitForTimeout(500);
|
|
}
|
|
// Try button with Continue with Safelite text
|
|
else if (await this.continueWithSafeliteButton.isVisible({ timeout: 2000 })) {
|
|
await this.continueWithSafeliteButton.click();
|
|
await this.page.waitForTimeout(500);
|
|
}
|
|
// Try any button that might work
|
|
else {
|
|
const possibleButtons = [
|
|
'button.btn-success',
|
|
'button[type="submit"]',
|
|
'button[name="navNext"]',
|
|
'.button-content',
|
|
'button:has-text("Continue")',
|
|
'button:has-text("Next")'
|
|
];
|
|
|
|
let buttonFound = false;
|
|
for (const selector of possibleButtons) {
|
|
const button = this.page.locator(selector);
|
|
if (await button.count() > 0 && await button.first().isVisible()) {
|
|
await button.first().click();
|
|
buttonFound = true;
|
|
await this.page.waitForTimeout(500);
|
|
break;
|
|
}
|
|
}
|
|
|
|
if (!buttonFound) {
|
|
await super.nextPage();
|
|
return;
|
|
}
|
|
}
|
|
|
|
// Check if URL changed
|
|
const currentUrl = this.page.url();
|
|
if (currentUrl !== startingUrl) {
|
|
break;
|
|
}
|
|
|
|
// Try Enter key on second attempt
|
|
if (attemptCount === 1) {
|
|
await this.page.keyboard.press('Enter');
|
|
await this.page.waitForTimeout(1000);
|
|
|
|
if (this.page.url() !== startingUrl) {
|
|
break;
|
|
}
|
|
}
|
|
|
|
attemptCount++;
|
|
} catch (error) {
|
|
attemptCount++;
|
|
|
|
if (attemptCount >= maxAttempts) {
|
|
await super.nextPage();
|
|
return;
|
|
}
|
|
|
|
await this.page.waitForTimeout(1000);
|
|
}
|
|
}
|
|
|
|
// Wait for spinner to disappear
|
|
try {
|
|
await expect(this.pageSpinner).toHaveCount(0, { timeout: 60000 });
|
|
} catch (error) {
|
|
// Continue if spinner check fails
|
|
}
|
|
|
|
// Final navigation stability check
|
|
await this.page.waitForLoadState('networkidle', { timeout: 10000 }).catch(() => {
|
|
// Continue if networkidle times out
|
|
});
|
|
}
|
|
|
|
/**
|
|
* Direct method to click Continue with Safelite button
|
|
*/
|
|
async clickContinueWithSafelite() {
|
|
try {
|
|
// Try direct ID selector first
|
|
if (await this.page.$('#navNext:has-text("Safelite")') !== null) {
|
|
await this.page.click('#navNext');
|
|
} else if (await this.continueWithSafeliteButton.isVisible({ timeout: 2000 })) {
|
|
await this.continueWithSafeliteButton.click();
|
|
} else {
|
|
await this.page.click('button:has-text("Continue with Safelite")');
|
|
}
|
|
return true;
|
|
} catch (error) {
|
|
return false;
|
|
}
|
|
}
|
|
} |