Merge pull request #1150 from Safelite/feature/jnou/fix-iss-regression
Fix ISS Playwright tests
This commit is contained in:
commit
5c22d0ba31
70 changed files with 1025 additions and 659 deletions
|
|
@ -14,7 +14,7 @@ resources:
|
||||||
type: github
|
type: github
|
||||||
name: Safelite/AzureDevOps
|
name: Safelite/AzureDevOps
|
||||||
endpoint: Safelite
|
endpoint: Safelite
|
||||||
ref: refs/tags/t5.7.40
|
ref: refs/tags/t5.7.53
|
||||||
|
|
||||||
variables:
|
variables:
|
||||||
# - group: Digital-Infrastructure
|
# - group: Digital-Infrastructure
|
||||||
|
|
|
||||||
|
|
@ -235,6 +235,7 @@ const defaultAfterpayDetails: IPaymentDetails = {
|
||||||
|
|
||||||
const defaultPaypalDetails: IPaymentDetails = {
|
const defaultPaypalDetails: IPaymentDetails = {
|
||||||
paymentType: PaymentType.Paypal,
|
paymentType: PaymentType.Paypal,
|
||||||
|
username:'Itqatest@safelite.com',
|
||||||
password: 'Safelite1'
|
password: 'Safelite1'
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -44,6 +44,8 @@ export interface IAppointmentDetails {
|
||||||
serviceAddress?: IAddress, // Used for mobile
|
serviceAddress?: IAddress, // Used for mobile
|
||||||
isVehicleProtected?: boolean // Used for mobile
|
isVehicleProtected?: boolean // Used for mobile
|
||||||
alternateServiceZip?: string // Used for in-shop and drop-off if doing service in a different ZIP
|
alternateServiceZip?: string // Used for in-shop and drop-off if doing service in a different ZIP
|
||||||
|
alternateMobileCity?: string // Used for mobile if doing service in a different city then customers address
|
||||||
|
alternateMobileStreetAddress?: string // Used for mobile if doing service in a different street address then customers address
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface IPartQuestion {
|
export interface IPartQuestion {
|
||||||
|
|
|
||||||
|
|
@ -8,7 +8,7 @@ export enum DamageType {
|
||||||
Theft = 'Attempted theft or theft',
|
Theft = 'Attempted theft or theft',
|
||||||
Hail = 'Hailstorm',
|
Hail = 'Hailstorm',
|
||||||
HurricaneStorm = 'Hurricane/storm',
|
HurricaneStorm = 'Hurricane/storm',
|
||||||
Collision = 'Collision',
|
OtherWeather = 'Other weather',
|
||||||
Object = 'Object hit glass',
|
Object = 'Object hit glass',
|
||||||
Other = 'Other/unknown'
|
Other = 'Other/unknown'
|
||||||
}
|
}
|
||||||
|
|
@ -90,7 +90,11 @@ export enum PartQuestionType {
|
||||||
RearWindowColor = 'Rear-Stationary',
|
RearWindowColor = 'Rear-Stationary',
|
||||||
LeatherSeats = 'question-0-1',
|
LeatherSeats = 'question-0-1',
|
||||||
DriverSideColor = 'Driver-SideDoor',
|
DriverSideColor = 'Driver-SideDoor',
|
||||||
LaneKeepAssist = 'question-0-1'
|
LaneKeepAssist = 'question-0-1',
|
||||||
|
GeneralQuestion1 = "question-0-1",
|
||||||
|
GeneralQuestion2 = "question-0-2",
|
||||||
|
GeneralQuestion3 = "question-0-3",
|
||||||
|
GeneralQuestion4 = "question-0-4"
|
||||||
}
|
}
|
||||||
|
|
||||||
export enum PaymentType{
|
export enum PaymentType{
|
||||||
|
|
@ -133,19 +137,23 @@ export enum SideDoorDamage{
|
||||||
|
|
||||||
export enum BailoutCode {
|
export enum BailoutCode {
|
||||||
Unknown = 0,
|
Unknown = 0,
|
||||||
SaveSessionError,
|
SaveSessionError = 1,
|
||||||
VehicleNotFound,
|
VehicleNotFound = 2,
|
||||||
VehicleLookupError,
|
VehicleVinLookupError = 3,
|
||||||
CoverageStatementInvalidState,
|
CoverageStatementInvalidState = 4,
|
||||||
DoNotSeeMyShop,
|
DoNotSeeMyShop = 5,
|
||||||
PricingResponseError,
|
PricingResponseError = 6,
|
||||||
TPANotEnabled,
|
TPANotEnabled = 7,
|
||||||
RequestCallback,
|
RequestCallback = 8,
|
||||||
HeavyTruckVehicle,
|
HeavyTruckVehicle = 9,
|
||||||
NoPartsAvailable,
|
NoPartsAvailable = 10,
|
||||||
PartsServiceError,
|
PartsServiceError = 11,
|
||||||
SafeliteNotTheProvider,
|
SafeliteNotTheProvider = 12,
|
||||||
VehicleYMMSLookupError
|
VehicleYMMSLookupError = 13,
|
||||||
|
ApplicationError = 14,
|
||||||
|
ApiError = 15,
|
||||||
|
RouterError = 16,
|
||||||
|
CoverageCancelledByUser = 17
|
||||||
}
|
}
|
||||||
|
|
||||||
export enum SignatureAlgorithm {
|
export enum SignatureAlgorithm {
|
||||||
|
|
@ -171,3 +179,32 @@ export enum Authentication {
|
||||||
RSATokenEncParamsOneTimeUse = 'RSATokenEncParamsOneTimeUse',
|
RSATokenEncParamsOneTimeUse = 'RSATokenEncParamsOneTimeUse',
|
||||||
Unknown = 'Unknown',
|
Unknown = 'Unknown',
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: Add validations for the percentages on each page like url validations
|
||||||
|
export enum ProgressBarPercentage {
|
||||||
|
DuplicateCheckPage = '15%',
|
||||||
|
PolicyVehiclesPage = '20%',
|
||||||
|
PolicyEndorsementsPage = '20%',
|
||||||
|
VehicleSelectionPage = '25%',
|
||||||
|
PolicyHolderDetailsPage = '30%',
|
||||||
|
VehicleDamagePage = '35%',
|
||||||
|
PartQuestionsPage = '40%',
|
||||||
|
MoldingQuestionsPage = '45%',
|
||||||
|
VehiclePartsPage = '45%',
|
||||||
|
CapabilityQuestionsPage = '45%',
|
||||||
|
VehicleLookupPage = '45%',
|
||||||
|
VinLookupPage = '50%',
|
||||||
|
LicensePlateLookupPage = '50%',
|
||||||
|
AddressLookupPage = '50%',
|
||||||
|
AddressVehiclesPage = '50%',
|
||||||
|
CoverageStatementPage = '55%',
|
||||||
|
ProviderPreferencePage = '60%',
|
||||||
|
SchedulePage = '70%',
|
||||||
|
ServicePackagesPage = '75%',
|
||||||
|
ContactDetailsPage = '85%',
|
||||||
|
PaymentMethodPage = '95%',
|
||||||
|
PaymentPage = '0%',
|
||||||
|
OrderConfirmationPage = '100%',
|
||||||
|
TpaSearchPage = '80%',
|
||||||
|
TpaSubmitPage = '95%',
|
||||||
|
}
|
||||||
|
|
@ -1,11 +1,12 @@
|
||||||
export default interface IBailoutFlags {
|
export default interface IBailoutFlags {
|
||||||
isVehicleSelectBailout: boolean,
|
isVehicleSelectBailout: boolean,
|
||||||
isDoNotSeeMyShopBailout: boolean,
|
|
||||||
isTpaNotEnabledBailout: boolean,
|
isTpaNotEnabledBailout: boolean,
|
||||||
isRequestCallbackBailout: boolean,
|
isRequestCallbackBailout: boolean,
|
||||||
isHeavyTruckVehicleBailout: boolean,
|
isHeavyTruckVehicleBailout: boolean,
|
||||||
isPartsServiceErrorBailout: boolean,
|
isPartsServiceErrorBailout: boolean,
|
||||||
isSafeliteNotTheProviderBailout: boolean,
|
isSafeliteNotTheProviderBailout: boolean,
|
||||||
isVehicleLookupBailout: boolean,
|
isVehicleLookupBailout: boolean,
|
||||||
isPriceServiceErrorBailout: boolean
|
isPriceServiceErrorBailout: boolean,
|
||||||
|
isCoverageCancelledByUser: boolean,
|
||||||
|
isAPIErrorBailout: boolean
|
||||||
}
|
}
|
||||||
|
|
@ -7,6 +7,7 @@ export interface ITestData {
|
||||||
clientTag: string,
|
clientTag: string,
|
||||||
isDuplicateClaim: boolean,
|
isDuplicateClaim: boolean,
|
||||||
isPolicyFound: boolean, // Effective difference between advanced and essential
|
isPolicyFound: boolean, // Effective difference between advanced and essential
|
||||||
|
isUnverifiedPolicyAfterVehicleLookup: boolean, // Changing license plate can cause flow to change to unverified from verified
|
||||||
isUseVehicleOnPolicy: boolean, // Should we use the vehicle on the policy?
|
isUseVehicleOnPolicy: boolean, // Should we use the vehicle on the policy?
|
||||||
isVehicleLookupValidations: boolean, // Should we validate vehicle lookup?
|
isVehicleLookupValidations: boolean, // Should we validate vehicle lookup?
|
||||||
isAddressLookupValidations: boolean, // Should we validate address lookup errors?
|
isAddressLookupValidations: boolean, // Should we validate address lookup errors?
|
||||||
|
|
|
||||||
|
|
@ -12,7 +12,8 @@ export default class CcisApiUtil {
|
||||||
createFakeResponse(requestBody: IPostSaveFakeResponseRequestBody) {
|
createFakeResponse(requestBody: IPostSaveFakeResponseRequestBody) {
|
||||||
return axios.post(this.postCreateMockPolicyUrl, requestBody, {
|
return axios.post(this.postCreateMockPolicyUrl, requestBody, {
|
||||||
headers: {
|
headers: {
|
||||||
'X-Mule-Origin-Verify': authToken
|
'X-Mule-Origin-Verify': authToken,
|
||||||
|
'x-Application-Name': 'ISS Playwright'
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
@ -21,7 +22,8 @@ export default class CcisApiUtil {
|
||||||
const deleteUrl = `${this.deleteFakeResponseUrl}/${params.accountNumber}/${params.key}/${params.responseType}`;
|
const deleteUrl = `${this.deleteFakeResponseUrl}/${params.accountNumber}/${params.key}/${params.responseType}`;
|
||||||
return axios.delete(deleteUrl, {
|
return axios.delete(deleteUrl, {
|
||||||
headers: {
|
headers: {
|
||||||
'X-Mule-Origin-Verify': authToken
|
'X-Mule-Origin-Verify': authToken,
|
||||||
|
'x-Application-Name': 'ISS Playwright'
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -15,7 +15,7 @@ export class AddressLookupPage extends BasePage {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.addressForm = new AddressForm(page);
|
this.addressForm = new AddressForm(page);
|
||||||
this.addressNoMatchTextBox = page.getByText('Your address didn’t return a VIN matchPlease re-enter the information below or');
|
this.addressNoMatchTextBox = page.getByText('Your address didn’t return a VIN match');
|
||||||
this.stateRestrictionsTextBox = page.getByText('State restrictionsLooks like');
|
this.stateRestrictionsTextBox = page.getByText('State restrictionsLooks like');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,34 +1,31 @@
|
||||||
import { Locator, Page } from "@playwright/test";
|
import { Locator, Page } from "@playwright/test";
|
||||||
import { BasePage } from "./BasePage";
|
import { BasePage } from "./BasePage";
|
||||||
import { IPaymentDetails } from "@business-logic/types/CustomerDetails";
|
import { IClaimDetails, IPaymentDetails } from "@business-logic/types/CustomerDetails";
|
||||||
|
import { ServicePackage } from "@business-logic/types/Enums";
|
||||||
|
|
||||||
export class AfterpayPage extends BasePage {
|
export class AfterpayPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
readonly submitButton: Locator;
|
|
||||||
|
|
||||||
// Login
|
|
||||||
readonly passwordTextBox: Locator;
|
readonly passwordTextBox: Locator;
|
||||||
|
readonly submitButton: Locator;
|
||||||
// Card details
|
|
||||||
readonly cardholderNameTextBox: Locator;
|
|
||||||
readonly cardNumberTextBox: Locator;
|
|
||||||
readonly expirationDateTextBox: Locator;
|
|
||||||
readonly cvvTextBox: Locator;
|
|
||||||
|
|
||||||
readonly confirmButton: Locator;
|
readonly confirmButton: Locator;
|
||||||
|
|
||||||
|
readonly selectAfterpayWithInterestButton: Locator;
|
||||||
|
readonly selectAfterpayWithoutInterestButton: Locator;
|
||||||
|
readonly continueAfterpayButton: Locator;
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.passwordTextBox = page.getByRole('textbox', { name: 'Please enter your password' });
|
this.passwordTextBox = page.getByTestId('login-password-input');
|
||||||
this.submitButton = page.getByRole('button', { name: 'Continue' });
|
this.submitButton = page.getByRole('button', { name: 'Continue' });
|
||||||
|
|
||||||
this.cardholderNameTextBox = page.getByTestId('payment-method-cardHolderName-input');
|
|
||||||
this.cardNumberTextBox = page.getByTestId('payment-method-cardNumber-input');
|
|
||||||
this.expirationDateTextBox = page.getByTestId('payment-method-cardExpiry-input');
|
|
||||||
this.cvvTextBox = page.getByTestId('payment-method-cardCvv-input');
|
|
||||||
|
|
||||||
this.confirmButton = page.getByRole('button', { name: 'Confirm' });
|
this.confirmButton = page.getByRole('button', { name: 'Confirm' });
|
||||||
|
|
||||||
|
// Monthly with interest option
|
||||||
|
this.selectAfterpayWithInterestButton = page.getByRole('radio', { name: /month/ });
|
||||||
|
// Biweekly without interest option
|
||||||
|
this.selectAfterpayWithoutInterestButton = page.getByTestId('payment-types-label').filter({ hasText: /every 2 weeks/ });
|
||||||
|
this.continueAfterpayButton = page.getByRole('button', { name: 'Continue' });
|
||||||
}
|
}
|
||||||
|
|
||||||
async login(password: string) {
|
async login(password: string) {
|
||||||
|
|
@ -36,21 +33,28 @@ export class AfterpayPage extends BasePage {
|
||||||
await this.submitButton.click();
|
await this.submitButton.click();
|
||||||
}
|
}
|
||||||
|
|
||||||
async populateCardDetails(paymentDetails: IPaymentDetails) {
|
async executeAfterpayPayment(paymentDetails: IPaymentDetails, claimDetails: IClaimDetails, servicePackage: ServicePackage) {
|
||||||
await this.cardholderNameTextBox.fill('Roberts'); // TODO: Add cardholder name field
|
|
||||||
await this.cardNumberTextBox.fill(paymentDetails.cardNumber!);
|
const confirmButtonOrPaymentOptions = this.confirmButton.or(this.selectAfterpayWithoutInterestButton);
|
||||||
await this.expirationDateTextBox.fill(`${paymentDetails.expirationMonth}/${paymentDetails.expirationYear}`);
|
|
||||||
await this.cvvTextBox.fill(paymentDetails.cvv!);
|
|
||||||
await this.submitButton.click();
|
|
||||||
}
|
|
||||||
|
|
||||||
async executeAfterpayPayment(paymentDetails: IPaymentDetails) {
|
|
||||||
await this.login(paymentDetails.password!);
|
await this.login(paymentDetails.password!);
|
||||||
|
|
||||||
await this.populateCardDetails(paymentDetails);
|
await this.page.locator('div[data-testid=\'loading-icon-svg\']').filter({ visible: true}).first().waitFor({ state: 'hidden' });
|
||||||
|
await confirmButtonOrPaymentOptions.waitFor({ state: 'visible' });
|
||||||
|
|
||||||
|
if (await this.confirmButton.isVisible()) {
|
||||||
|
await this.confirmButton.waitFor({ state: 'attached' });
|
||||||
|
await this.confirmButton.click();
|
||||||
|
} else {
|
||||||
|
// For some orders, user will have 2 options to choose from: monthly with interest or biweekly without interest
|
||||||
|
if (await this.selectAfterpayWithoutInterestButton.isVisible()) {
|
||||||
|
await this.selectAfterpayWithoutInterestButton.click();
|
||||||
|
await this.continueAfterpayButton.click();
|
||||||
|
} else if (await this.selectAfterpayWithInterestButton.isVisible()) {
|
||||||
|
await this.selectAfterpayWithInterestButton.click();
|
||||||
|
await this.continueAfterpayButton.click();
|
||||||
|
}
|
||||||
await this.confirmButton.click();
|
await this.confirmButton.click();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
@ -28,8 +28,7 @@ export class BailoutPage extends BasePage {
|
||||||
await expect.soft(this.firstNameTextBox).toHaveValue(customerDetails.firstName);
|
await expect.soft(this.firstNameTextBox).toHaveValue(customerDetails.firstName);
|
||||||
await expect.soft(this.lastNameTextBox).toHaveValue(customerDetails.lastName);
|
await expect.soft(this.lastNameTextBox).toHaveValue(customerDetails.lastName);
|
||||||
await expect.soft(this.phoneNumberTextBox).toHaveValue(customerDetails.phoneNumber);
|
await expect.soft(this.phoneNumberTextBox).toHaveValue(customerDetails.phoneNumber);
|
||||||
await expect.soft(this.emailAddressTextBox).toHaveValue(customerDetails.email);
|
expect.soft(await this.getBailoutCode()).toEqual(bailoutCode);
|
||||||
await expect.soft(await this.getBailoutCode()).toEqual(bailoutCode);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async validateBailoutDetailsNotNull(){
|
async validateBailoutDetailsNotNull(){
|
||||||
|
|
@ -41,7 +40,7 @@ export class BailoutPage extends BasePage {
|
||||||
}
|
}
|
||||||
|
|
||||||
async getBailoutCode() {
|
async getBailoutCode() {
|
||||||
const mainLocalStorage = JSON.parse(await this.page.evaluate('localStorage.getItem(\'main\')'));
|
const mainLocalStorage = JSON.parse(await this.page.evaluate('sessionStorage.getItem(\'main\')'));
|
||||||
const bailoutCode = mainLocalStorage.applicationUser.pageData['bailout-page'].bailoutCode as number;
|
const bailoutCode = mainLocalStorage.applicationUser.pageData['bailout-page'].bailoutCode as number;
|
||||||
return bailoutCode;
|
return bailoutCode;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -17,7 +17,8 @@ export class BasePage {
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.continueButton = page.locator('[id="infoBox"]').getByRole('button');
|
this.continueButton = page.locator('button[data-test-id="site-footer-main-button"]')
|
||||||
|
.and(page.locator('button', { hasText: /get\s*started|continue|submit/i }));
|
||||||
this.pageSpinner = page.getByRole('status');
|
this.pageSpinner = page.getByRole('status');
|
||||||
this.buttonLoadSpin = page.getByRole('alert');
|
this.buttonLoadSpin = page.getByRole('alert');
|
||||||
}
|
}
|
||||||
|
|
@ -95,16 +96,16 @@ export class BasePage {
|
||||||
}
|
}
|
||||||
|
|
||||||
async logReferralNumber() {
|
async logReferralNumber() {
|
||||||
let mainLocalStorage = JSON.parse(await this.page.evaluate('localStorage.getItem(\'main\')'));
|
let mainSessionStorage = JSON.parse(await this.page.evaluate('sessionStorage.getItem(\'main\')'));
|
||||||
let referralNumber = mainLocalStorage.order.referralNumber as number;
|
let referralNumber = mainSessionStorage.order.referralNumber as number;
|
||||||
let referralSequenceNumber = mainLocalStorage.order.referralSequenceNumber as number;
|
let referralSequenceNumber = mainSessionStorage.order.referralSequenceNumber as number;
|
||||||
if (referralNumber == null) {
|
if (referralNumber == null) {
|
||||||
for (let i = 1; i <= 20; i++) {
|
for (let i = 1; i <= 20; i++) {
|
||||||
if (!referralNumber == null) break;
|
if (!referralNumber == null) break;
|
||||||
await this.page.waitForTimeout(500);
|
await this.page.waitForTimeout(500);
|
||||||
mainLocalStorage = JSON.parse(await this.page.evaluate('localStorage.getItem(\'main\')'));
|
mainSessionStorage = JSON.parse(await this.page.evaluate('localStorage.getItem(\'main\')'));
|
||||||
referralNumber = mainLocalStorage.order.referralNumber as number;
|
referralNumber = mainSessionStorage.order.referralNumber as number;
|
||||||
referralSequenceNumber = mainLocalStorage.order.referralSequenceNumber as number;
|
referralSequenceNumber = mainSessionStorage.order.referralSequenceNumber as number;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -6,35 +6,57 @@ export class ContactDetailsPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
issPageValue = 'contact-details';
|
issPageValue = 'contact-details';
|
||||||
|
|
||||||
// Contact details form
|
readonly appointmentInformationAlert: Locator;
|
||||||
// TODO: Check if we can consolidate
|
readonly changeZipCodeAlert: Locator;
|
||||||
readonly firstNameTextBox: Locator;
|
|
||||||
readonly lastNameTextBox: Locator;
|
readonly streetAddressTextBox: Locator;
|
||||||
readonly emailAddressTextBox: Locator;
|
readonly apartmentNumberTextBox: Locator;
|
||||||
readonly phoneNumberTextBox: Locator;
|
readonly cityTextBox: Locator;
|
||||||
|
readonly stateTextBox: Locator;
|
||||||
|
readonly zipCodeTextBox: Locator;
|
||||||
|
readonly coveredLocationYesButton: Locator;
|
||||||
|
readonly coveredLocationNoButton: Locator
|
||||||
readonly notesTextBox: Locator;
|
readonly notesTextBox: Locator;
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
|
|
||||||
|
// Alerts
|
||||||
|
this.appointmentInformationAlert = this.page.locator('[class*="widget-name-AppointmentInformationAlertWidget"]');
|
||||||
|
this.changeZipCodeAlert = this.page.locator('[class*="widget-name-ChangeZipCodeAlertWidget"]');
|
||||||
|
|
||||||
// Contact details form
|
// Contact details form
|
||||||
this.firstNameTextBox = this.page.getByRole('textbox', { name: 'First name' });
|
this.streetAddressTextBox = this.page.getByRole('textbox', { name: 'Street address' });
|
||||||
this.lastNameTextBox = this.page.getByRole('textbox', { name: 'Last name' });
|
this.apartmentNumberTextBox = this.page.getByRole('textbox', { name: 'Apartment number or letter (Optional)' });
|
||||||
this.emailAddressTextBox = this.page.getByRole('textbox', { name: 'Email address' });
|
this.cityTextBox = this.page.getByRole('textbox', { name: 'City' });
|
||||||
this.phoneNumberTextBox = this.page.getByRole('textbox', { name: 'Phone number' });
|
this.stateTextBox = this.page.getByRole('textbox', { name: 'state' });
|
||||||
this.notesTextBox = this.page.getByRole('textbox', { name: 'Notes' });
|
this.zipCodeTextBox = this.page.getByRole('textbox', { name: 'ZIP' });
|
||||||
|
this.coveredLocationYesButton = this.page.locator('#vehicleProtectedQuestion-true');
|
||||||
|
this.coveredLocationNoButton = this.page.locator('#vehicleProtectedQuestion-false');
|
||||||
|
this.notesTextBox = this.page.getByRole('textbox', { name: 'technicianNotes' });
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async validateAlertsAreVisible() {
|
||||||
|
await expect(this.appointmentInformationAlert).toBeVisible();
|
||||||
|
await this.appointmentInformationAlert.click(); //
|
||||||
|
await expect(this.appointmentInformationAlert).toContainText('Please have your vehicle keys or key card available, as your technician needs access inside the vehicle and may need to move your vehicle to complete service.');
|
||||||
|
|
||||||
async getContactDetails() {
|
await expect(this.changeZipCodeAlert).toBeVisible();
|
||||||
const customerDetails: Partial<ICustomerDetails> = {};
|
await this.changeZipCodeAlert.click();
|
||||||
customerDetails.firstName = await this.firstNameTextBox.inputValue();
|
await expect(this.changeZipCodeAlert).toContainText('If your service ZIP code has changed, please go back and update it to ensure we have the correct information for your appointment.');
|
||||||
customerDetails.lastName = await this.lastNameTextBox.inputValue();
|
}
|
||||||
customerDetails.email = await this.emailAddressTextBox.inputValue();
|
|
||||||
customerDetails.phoneNumber = await this.phoneNumberTextBox.inputValue();
|
|
||||||
|
|
||||||
return customerDetails;
|
// TO-DO add method for when checkbox for same as policy address displays
|
||||||
|
|
||||||
|
async fillContactDetails(customerDetails: ICustomerDetails) {
|
||||||
|
await this.streetAddressTextBox.fill(customerDetails.address.street!);
|
||||||
|
await this.cityTextBox.fill(customerDetails.address.city!);
|
||||||
|
}
|
||||||
|
|
||||||
|
async fillAlternateMobileStreetAndCity(alternateMobileStreetAddress: string, alternateMobileCity: string) {
|
||||||
|
await this.streetAddressTextBox.fill(alternateMobileStreetAddress);
|
||||||
|
await this.cityTextBox.fill(alternateMobileCity);
|
||||||
}
|
}
|
||||||
|
|
||||||
async fillNotes(notes?: string) {
|
async fillNotes(notes?: string) {
|
||||||
|
|
|
||||||
|
|
@ -1,30 +1,46 @@
|
||||||
import { expect, type Locator, type Page } from '@playwright/test';
|
import { expect, type Locator, type Page } from '@playwright/test';
|
||||||
import { BasePage } from './BasePage';
|
import { BasePage } from './BasePage';
|
||||||
|
import { IClaimDetails, ICustomerDetails } from '@business-logic/types/CustomerDetails';
|
||||||
|
import { defaultTestData, ITestData, VehicleDamage } from 'safelite-playwright-core';
|
||||||
|
|
||||||
export class CoverageStatementPage extends BasePage {
|
export class CoverageStatementPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
readonly scheduleOnlineButton: Locator;
|
|
||||||
readonly cancelMyClaimButton: Locator;
|
readonly cancelMyClaimButton: Locator;
|
||||||
readonly cancelMyClaimConfirm: Locator;
|
readonly cancelMyClaimConfirm: Locator;
|
||||||
readonly deductibleAmount: Locator;
|
readonly deductibleAmount: Locator;
|
||||||
readonly verfiyingCoverageText: Locator;
|
readonly noDeductibleRepairText: Locator; // For essential flow when there is no deductible and repair is covered
|
||||||
readonly continueToScheduleButton: Locator; // For ITAC/NoComp
|
readonly youPayYourDeductibleText: Locator;
|
||||||
|
readonly verifiedCoverageHeader: Locator; // For essential flow when coverage is verified
|
||||||
|
readonly headerForITAC: Locator; // For ITAC when coverage is found
|
||||||
|
readonly headerForNoComp: Locator; // For NoComp when coverage is found
|
||||||
|
readonly unverifiedCoverageHeader: Locator; // For essential flows when verifying deductible
|
||||||
|
readonly oemBullet: Locator; // For OEM bullet when OEM endorsement is present
|
||||||
|
readonly continueSchedulingButton: Locator; // For ITAC/NoComp
|
||||||
|
readonly continueButton: Locator; // For essential flows
|
||||||
issPageValue = 'coverage-statement';
|
issPageValue = 'coverage-statement';
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.scheduleOnlineButton = this.page.getByText('Continue to schedule online');
|
|
||||||
this.cancelMyClaimButton = this.page.getByText('Cancel my claim');
|
|
||||||
this.cancelMyClaimConfirm = this.page.getByText('No, I want to cancel');
|
|
||||||
|
|
||||||
this.deductibleAmount = this.page.getByText('$');
|
this.cancelMyClaimButton = this.page.getByRole('link', { name: "No, I want to cancel" }); // seen for ITAC/NoComp flows
|
||||||
this.verfiyingCoverageText = this.page.getByRole('heading', { name: 'We’re verifying your coverage' });
|
this.cancelMyClaimConfirm = this.page.locator('div.text-center', { hasText: "No, I want to cancel" }); // on modal for cancel claim
|
||||||
this.continueToScheduleButton = page.locator('div[class*="button-content"]', {hasText:'Continue to schedule online'});
|
|
||||||
|
this.deductibleAmount = this.page.locator('.cost-underline');
|
||||||
|
this.noDeductibleRepairText = this.page.getByText('According to your policy, there is no deductible for a repair.'); // no deductible for repair text
|
||||||
|
this.youPayYourDeductibleText = this.page.getByText('You pay your deductible:'); // no deductible for replacement text
|
||||||
|
this.verifiedCoverageHeader = this.page.getByRole('heading', { name: 'We have verified your coverage' });
|
||||||
|
this.unverifiedCoverageHeader = this.page.getByRole('heading', { level: 5, name: "We’re verifying your coverage" });
|
||||||
|
this.headerForITAC = this.page.getByRole('heading', { name: 'Good news! Safelite\'s price is lower than your deductible' });
|
||||||
|
this.headerForNoComp = this.page.getByRole('heading', { name: 'Looks like your policy doesn\'t include comprehensive coverage.\nSafelite can still get you fixed up and safely back on the road.' });
|
||||||
|
this.oemBullet = this.page.getByText('OEM (Original Equipment Manufacturer) glass replacement is included under your policy and will be installed in your vehicle.');
|
||||||
|
|
||||||
|
this.continueSchedulingButton = page.getByRole('button', { name: 'Continue scheduling' }); // continue button for ITAC/NoComp flow
|
||||||
|
this.continueButton = page.getByRole('button', { name: 'Continue' }); // continue button for essential flow
|
||||||
}
|
}
|
||||||
|
|
||||||
async scheduleOnline(){
|
async scheduleOnline(){
|
||||||
await this.scheduleOnlineButton.click();
|
await this.continueSchedulingButton.click();
|
||||||
}
|
}
|
||||||
|
|
||||||
async cancelMyClaim(){
|
async cancelMyClaim(){
|
||||||
|
|
@ -32,11 +48,70 @@ export class CoverageStatementPage extends BasePage {
|
||||||
await this.cancelMyClaimConfirm.click();
|
await this.cancelMyClaimConfirm.click();
|
||||||
}
|
}
|
||||||
|
|
||||||
async validateDeductibleAmount(customer){
|
async handleRepairWithNoDeductibleFlow() {
|
||||||
await expect(this.deductibleAmount). toContainText(`$${customer.deductibleAmount}`, {timeout: 60000});
|
|
||||||
|
if (VehicleDamage.WindshieldOneChip || VehicleDamage.WindshieldTwoChips || VehicleDamage.WindshieldThreeChips) {
|
||||||
|
await expect(this.verifiedCoverageHeader).toBeVisible();
|
||||||
|
await expect(this.noDeductibleRepairText).toBeVisible();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
async handleReplacementOrRepairWithNoDeductibleFlow(claimDetails: IClaimDetails, VehicleDamage){
|
||||||
|
const noDeductibleFlow = claimDetails.policyDeductible === 0;
|
||||||
|
|
||||||
|
if (noDeductibleFlow && VehicleDamage === VehicleDamage.WindshieldOneChip || VehicleDamage.WindshieldTwoChips || VehicleDamage.WindshieldThreeChips) {
|
||||||
|
|
||||||
|
// await expect(this.noDeductibleRepairText).toBeVisible();
|
||||||
|
await this.continueButton.click();
|
||||||
|
|
||||||
|
} else {
|
||||||
|
await expect(this.youPayYourDeductibleText).toBeVisible();
|
||||||
|
await expect(this.deductibleAmount).toContainText(`$0`, {timeout: 60000});
|
||||||
|
await this.continueButton.click();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
async handleReplacementWithDeductibleFlow(claimDetails: IClaimDetails){
|
||||||
|
const replaceWithDeductibleFlow = claimDetails.policyDeductible! > 0 && claimDetails.policyDeductible !== 9999;
|
||||||
|
|
||||||
|
if (replaceWithDeductibleFlow) {
|
||||||
|
await expect(this.youPayYourDeductibleText).toBeVisible();
|
||||||
|
await expect(this.deductibleAmount).toContainText(`$${claimDetails.policyDeductible?.toLocaleString()}`, {timeout: 60000});
|
||||||
|
|
||||||
|
await this.continueButton.click();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
async handleUnverifiedFlow(claimDetails: IClaimDetails){
|
||||||
|
const unVerifiedCustomer = claimDetails.policyDeductible === -1; // if deductible is -1, we treat it as unverified flow
|
||||||
|
|
||||||
|
if (unVerifiedCustomer) {
|
||||||
|
await expect(this.unverifiedCoverageHeader).toBeVisible();
|
||||||
|
|
||||||
|
await this.continueButton.click();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
async handleUnverifiedPolicyAfterVehicleLookupFlow(){
|
||||||
|
await expect(this.unverifiedCoverageHeader).toBeVisible();
|
||||||
|
await this.continueButton.click();
|
||||||
|
}
|
||||||
|
|
||||||
|
async handleITACFlow(){
|
||||||
|
await expect(this.headerForITAC).toBeVisible(); // verify ITAC header is visible
|
||||||
|
|
||||||
|
await this.continueSchedulingButton.click(); // happy path to scheduling for ITAC
|
||||||
|
}
|
||||||
|
|
||||||
|
async handleNoCompFlow(){
|
||||||
|
await expect(this.headerForNoComp).toBeVisible(); // verify NoComp header is visible
|
||||||
|
|
||||||
|
await this.continueSchedulingButton.click(); // happy path to scheduling for NoComp
|
||||||
|
}
|
||||||
|
|
||||||
|
async validateOEMBullet(){
|
||||||
|
await expect(this.oemBullet).toBeVisible();
|
||||||
}
|
}
|
||||||
|
|
||||||
async validateUnverifiedText(){
|
|
||||||
await expect(this.verfiyingCoverageText).toBeEnabled();
|
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
@ -12,11 +12,11 @@ export class EndorsementsPage extends BasePage {
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.educatorYesButton = this.page.locator('label[for="schoolProperty-Yes"]');
|
this.educatorYesButton = this.page.locator('label:has(div.button-content:has(span:has-text("Yes")))');
|
||||||
this.educatorNoButton = this.page.locator('label[for="schoolProperty-No"]');
|
this.educatorNoButton = this.page.locator('label:has(div.button-content:has(span:has-text("No")))');
|
||||||
}
|
}
|
||||||
|
|
||||||
async verifyEndorsements(endorsements: IEndorsementDetails[]) {
|
async verifyEndorsements(endorsements: IEndorsementDetails[]) {
|
||||||
for (const endorsement of endorsements) {
|
for (const endorsement of endorsements) {
|
||||||
switch(endorsement.endorsementType) {
|
switch(endorsement.endorsementType) {
|
||||||
case EndorsementType.Educator:
|
case EndorsementType.Educator:
|
||||||
|
|
|
||||||
|
|
@ -6,110 +6,175 @@ import { ITestData } from '@business-logic/types/ITestData';
|
||||||
|
|
||||||
export class OrderConfirmationPage extends BasePage {
|
export class OrderConfirmationPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
|
|
||||||
|
readonly successCheckmark: Locator;
|
||||||
|
readonly successHeader: Locator;
|
||||||
|
|
||||||
readonly serviceText: Locator;
|
readonly serviceText: Locator;
|
||||||
readonly emailText: Locator;
|
readonly workOrderNumberText: Locator;
|
||||||
readonly apptDateText: Locator;
|
readonly confirmationText: Locator;
|
||||||
readonly amountDueText: Locator;
|
readonly appointmentTypeText: Locator;
|
||||||
readonly viewCartButton: Locator;
|
readonly apptDetailsText: Locator;
|
||||||
readonly deductibleText: Locator;
|
readonly deductibleText: Locator;
|
||||||
readonly subtotalText: Locator;
|
readonly subtotalText: Locator;
|
||||||
|
readonly totalAmountDueText: Locator;
|
||||||
|
readonly amountPaidText: Locator;
|
||||||
readonly finalAmountDue: Locator;
|
readonly finalAmountDue: Locator;
|
||||||
readonly cartServicePackageText: Locator;
|
readonly cartLineItemsText: Locator;
|
||||||
|
readonly unverifiedCoverageDeductibleText: Locator;
|
||||||
|
|
||||||
issPageValue = 'order-confirmation';
|
issPageValue = 'order-confirmation';
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.serviceText = this.page.locator('[class="appointment-text text-center lh-base"]');
|
|
||||||
this.emailText = this.page.locator('[class="email-confirmation-text"]');
|
this.successCheckmark = this.page.locator('img[src*="-checkmark.svg"]');
|
||||||
this.apptDateText = this.page.locator('[class="appointment-date-time text-center mt-4"]');
|
this.successHeader = this.page.locator('[class="header-text"]');
|
||||||
this.amountDueText = this.page.getByLabel('expand cart details');
|
|
||||||
this.viewCartButton = this.page.locator('#cart-dropdown-head');
|
this.confirmationText = this.page.locator('[class="subheader-text"]', { hasText: 'Your appointment is on Safelite\'s schedule and your confirmation email is on the way.' });
|
||||||
this.deductibleText = this.page.locator('#deductible-value');
|
this.serviceText = this.page.locator('[class="service-description confirmation-section"]');
|
||||||
this.subtotalText = this.page.locator("#subtotal-value");
|
this.workOrderNumberText = this.page.locator('[class="work-order-description"]');
|
||||||
|
this.appointmentTypeText = this.page.locator('[class="appointment-title"]');
|
||||||
|
this.apptDetailsText = this.page.locator('[class="appointment-details confirmation-section"]');
|
||||||
|
|
||||||
|
// Order details section
|
||||||
|
this.deductibleText = this.page.locator('span#deductible-value, span.deductible-value');
|
||||||
|
this.subtotalText = this.page.locator('#subtotal-value');
|
||||||
|
this.totalAmountDueText = this.page.locator('#total-value');
|
||||||
|
this.amountPaidText = this.page.locator('#amount-paid-value');
|
||||||
this.finalAmountDue = this.page.locator('#bottom-amount-due-value');
|
this.finalAmountDue = this.page.locator('#bottom-amount-due-value');
|
||||||
this.cartServicePackageText = this.page.locator('#cart-service-package');
|
this.cartLineItemsText = this.page.locator('.cart-item-list');
|
||||||
|
this.unverifiedCoverageDeductibleText = this.page.locator('span#deductible-value', { hasText: 'Verifying coverage' });
|
||||||
}
|
}
|
||||||
|
|
||||||
async validateOrderConfirmationPage(testData: Partial<ITestData>) {
|
async validateOrderConfirmationPage(testData: Partial<ITestData>) {
|
||||||
// Destructure data we use
|
// Destructure data we use
|
||||||
const { vehicleDetails, customerDetails, servicePackage, isItac,
|
const { vehicleDetails, customerDetails, servicePackage, isItac,
|
||||||
isNoComp, isPolicyFound, claimDetails, paymentDetails, isUseVehicleOnPolicy } = testData;
|
isNoComp, isPolicyFound, claimDetails, paymentDetails, isUseVehicleOnPolicy } = testData;
|
||||||
await this.serviceText.waitFor({ state: "visible" });
|
|
||||||
await this.logOrderNumber();
|
|
||||||
|
|
||||||
// Grab text
|
// Grab text
|
||||||
const serviceTextValue = await this.serviceText.textContent();
|
const serviceTextValue = await this.serviceText.textContent();
|
||||||
const apptDateValue = await this.apptDateText.textContent();
|
const apptDetailsValue = await this.apptDetailsText.textContent();
|
||||||
const emailTextValue = await this.emailText.textContent();
|
const appointmentTypeValue = await this.appointmentTypeText.textContent();
|
||||||
const servicePackageValue = await this.cartServicePackageText.textContent();
|
|
||||||
const amountDueValue = await this.amountDueText.textContent();
|
|
||||||
const deductibleTextValue = (isItac || isNoComp) ? null : await this.deductibleText.textContent();
|
// Derived conditions
|
||||||
const subtotalTextValue = await this.subtotalText.textContent();
|
const isItacOrNoComp = !!(isItac || isNoComp);
|
||||||
const finalAmountDueValue = await this.finalAmountDue.textContent();
|
const isUnverified = !isPolicyFound;
|
||||||
|
const isUnverifiedPolicyAfterVehicleLookup = testData.isUnverifiedPolicyAfterVehicleLookup === true;
|
||||||
|
const hasPremiumOrStandard =
|
||||||
|
(claimDetails!.policyDeductible >= 0 || !isPolicyFound) &&
|
||||||
|
(servicePackage === ServicePackage.Premium || servicePackage === ServicePackage.Standard);
|
||||||
|
|
||||||
|
const payAtService =
|
||||||
|
(claimDetails!.policyDeductible >= 0 &&
|
||||||
|
paymentDetails?.paymentType === PaymentType.PayAtService) || !paymentDetails?.paymentType;
|
||||||
|
|
||||||
|
const paidWithPIA =
|
||||||
|
claimDetails!.policyDeductible >= 0 &&
|
||||||
|
paymentDetails?.paymentType !== PaymentType.PayAtService;
|
||||||
|
|
||||||
|
// Helper: grab textContent only when the element is expected on-screen
|
||||||
|
const textIf = async (condition: boolean, locator: Locator) =>
|
||||||
|
condition ? await locator.textContent() : null;
|
||||||
|
|
||||||
|
// Grab text content for elements that are expected on-screen
|
||||||
|
const lineItemsValue = await textIf(hasPremiumOrStandard, this.cartLineItemsText);
|
||||||
|
const deductibleTextValue = await textIf(!isItacOrNoComp, this.deductibleText);
|
||||||
|
const subtotalTextValue = await textIf((hasPremiumOrStandard || isItacOrNoComp) && !isUnverified && !isUnverifiedPolicyAfterVehicleLookup, this.subtotalText);
|
||||||
|
const totalAmountDueValue = await textIf((hasPremiumOrStandard && !payAtService) || (isItacOrNoComp && !payAtService) && !isUnverified && !isUnverifiedPolicyAfterVehicleLookup, this.totalAmountDueText);
|
||||||
|
const amountPaidTextValue = await textIf((hasPremiumOrStandard && !payAtService) || (isItacOrNoComp && !payAtService) && !isUnverified && !isUnverifiedPolicyAfterVehicleLookup, this.totalAmountDueText);
|
||||||
|
const finalAmountDueValue = await textIf(hasPremiumOrStandard || isItacOrNoComp || isUnverified || isUnverifiedPolicyAfterVehicleLookup, this.finalAmountDue);
|
||||||
|
const confirmationTextValue = await this.confirmationText.textContent();
|
||||||
|
|
||||||
|
|
||||||
// Extract service package price
|
|
||||||
const servicePackageAmt = Number.parseFloat(servicePackageValue!.split('$')[1].replaceAll(',', ''));
|
|
||||||
|
|
||||||
// General Validations
|
// General Validations
|
||||||
|
expect.soft(this.serviceText).toBeVisible();;
|
||||||
|
expect.soft(this.successHeader).toBeVisible();
|
||||||
|
expect.soft(confirmationTextValue).toContain('Your appointment is on Safelite\'s schedule and your confirmation email is on the way.');
|
||||||
expect.soft(serviceTextValue).toContain(`${vehicleDetails!.year} ${vehicleDetails!.make} ${vehicleDetails!.model}`);
|
expect.soft(serviceTextValue).toContain(`${vehicleDetails!.year} ${vehicleDetails!.make} ${vehicleDetails!.model}`);
|
||||||
expect.soft(apptDateValue).toContain(customerDetails!.apptDate);
|
|
||||||
expect.soft(emailTextValue).toContain(customerDetails!.email);
|
|
||||||
|
|
||||||
// Service package validations
|
// Validate order number and appointment type header
|
||||||
await expect.soft(this.cartServicePackageText).toContainText(`${servicePackage}`)
|
await this.validateOrderNumber();
|
||||||
if ((servicePackage === ServicePackage.Premium && testData.isReplace === true) || servicePackage === ServicePackage.Standard) {
|
await this.validateAppointmentTypeHeader();
|
||||||
expect.soft(servicePackageValue).toContain('New wiper blades');
|
|
||||||
}
|
|
||||||
if (servicePackage === ServicePackage.Premium) {
|
|
||||||
expect.soft(servicePackageValue).toContain('Rain Defense™ treatment');
|
|
||||||
}
|
|
||||||
|
|
||||||
// Price validations
|
// Validate line items
|
||||||
if (servicePackage === ServicePackage.GlassOnly) {
|
if (servicePackage === ServicePackage.Premium) {
|
||||||
expect.soft(servicePackageAmt).toEqual(0);
|
expect.soft(lineItemsValue).toContain('Front advanced beam blades');
|
||||||
|
expect.soft(lineItemsValue).toContain('Safelite Rain Repellent Treatment');
|
||||||
} else {
|
} else {
|
||||||
expect.soft(servicePackageAmt).toBeGreaterThan(0);
|
if (servicePackage === ServicePackage.Standard) {
|
||||||
|
expect.soft(lineItemsValue).toContain('Front advanced beam blades');
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isPolicyFound && (isUseVehicleOnPolicy ?? true)) {
|
|
||||||
// Extract numbers
|
if (isPolicyFound && (claimDetails!.policyDeductible === 0 && (servicePackage === ServicePackage.GlassOnly))) {
|
||||||
const amountDueAmt = Number.parseFloat(amountDueValue!.split('$')[1].replaceAll(',', ''));
|
const zeroDeductibleText = await this.deductibleText.textContent();
|
||||||
|
expect.soft(zeroDeductibleText).toEqual('$0.00');
|
||||||
|
} else if (isPolicyFound && claimDetails!.policyDeductible > 0 && !(isItac || isNoComp) && servicePackage === ServicePackage.GlassOnly){
|
||||||
|
expect.soft(deductibleTextValue).not.toBeNull();
|
||||||
const deductibleAmt = deductibleTextValue ? Number.parseFloat(deductibleTextValue.split('$')[1].replaceAll(',', '')) : 0;
|
const deductibleAmt = deductibleTextValue ? Number.parseFloat(deductibleTextValue.split('$')[1].replaceAll(',', '')) : 0;
|
||||||
const subtotalAmt = Number.parseFloat(subtotalTextValue!.split('$')[1].replaceAll(',', ''));
|
expect.soft(deductibleAmt).toEqual(claimDetails!.policyDeductible);
|
||||||
subtotalTextValue?.replaceAll(',', '')
|
|
||||||
const finalAmountDueAmt = Number.parseFloat(finalAmountDueValue!.split('$')[1].replaceAll(',', ''));
|
} else if ((isPolicyFound || isItac || (isNoComp && paymentDetails!.paymentType === PaymentType.PayAtService)) && !isUnverifiedPolicyAfterVehicleLookup && finalAmountDueValue !== null && subtotalTextValue !== null) {
|
||||||
|
// Extract numbers
|
||||||
|
const deductibleAmt = deductibleTextValue ? Number.parseFloat(deductibleTextValue.split('$')[1].replaceAll(',', '')) : null;
|
||||||
|
|
||||||
|
const subtotalAmt = subtotalTextValue ? Number.parseFloat(subtotalTextValue!.split('$')[1].replaceAll(',', '')) : null;
|
||||||
|
|
||||||
|
|
||||||
|
//const totalAmountDueAmt = Number.parseFloat(totalAmountDueValue!.split('$')[1].replaceAll(',', ''));
|
||||||
|
const finalAmountDueAmt = finalAmountDueValue ? Number.parseFloat(finalAmountDueValue!.split('$')[1].replaceAll(',', '')) : null;
|
||||||
|
|
||||||
if (!(isItac || isNoComp)) {
|
if (!(isItac || isNoComp)) {
|
||||||
expect.soft(subtotalAmt).toEqual(claimDetails!.policyDeductible + servicePackageAmt);
|
|
||||||
expect.soft(deductibleAmt).toEqual(claimDetails!.policyDeductible);
|
expect.soft(deductibleAmt).toEqual(claimDetails!.policyDeductible);
|
||||||
} else {
|
} else {
|
||||||
expect.soft(subtotalAmt).toBeGreaterThan(0);
|
expect.soft(subtotalAmt).toBeGreaterThan(0);
|
||||||
expect.soft(deductibleAmt).toEqual(0);
|
//expect.soft(deductibleAmt).toEqual(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (paymentDetails!.paymentType === PaymentType.PayAtService && (claimDetails!.policyDeductible > 0 || servicePackageAmt > 0)) {
|
if ((paymentDetails!.paymentType === PaymentType.PayAtService) && (claimDetails!.policyDeductible >= 0 && (servicePackage === ServicePackage.Standard || servicePackage === ServicePackage.Premium))) {
|
||||||
// Verify amount due > 0
|
|
||||||
expect.soft(amountDueAmt).toBeGreaterThan(0);
|
|
||||||
expect.soft(finalAmountDueAmt).toBeGreaterThan(0);
|
expect.soft(finalAmountDueAmt).toBeGreaterThan(0);
|
||||||
} else {
|
} else {
|
||||||
// Verify amount due 0
|
const totalAmountDueAmt = Number.parseFloat(totalAmountDueValue!.split('$')[1].replaceAll(',', ''));
|
||||||
expect.soft(amountDueAmt).toEqual(0);
|
const amountPaidValue = Number.parseFloat(amountPaidTextValue!.split('$')[1].replaceAll(',', ''));
|
||||||
|
// Verify amount due 0 usually when PIA is selected
|
||||||
|
expect.soft(amountPaidValue).toEqual(totalAmountDueAmt);
|
||||||
expect.soft(finalAmountDueAmt).toEqual(0);
|
expect.soft(finalAmountDueAmt).toEqual(0);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
expect.soft(amountDueValue).toContain('Verifying coverage');
|
// essential flows will have deductible and amount due as "Verifying coverage"
|
||||||
expect.soft(subtotalTextValue).toEqual('Verifying coverage');
|
const verifyingCoverageText = this.unverifiedCoverageDeductibleText;
|
||||||
|
|
||||||
|
expect.soft(verifyingCoverageText).toContainText('Verifying coverage');
|
||||||
expect.soft(finalAmountDueValue).toEqual('Verifying coverage');
|
expect.soft(finalAmountDueValue).toEqual('Verifying coverage');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async logOrderNumber() {
|
async validateOrderNumber() {
|
||||||
const sessionStorage = JSON.parse(await this.page.evaluate('sessionStorage.getItem(\'submittedOrder\')'));
|
const sessionStorage = JSON.parse(await this.page.evaluate('sessionStorage.getItem(\'submittedOrder\')'));
|
||||||
const workOrderNumber = sessionStorage.workOrderNumber;
|
const workOrderNumber = sessionStorage.workOrderNumber;
|
||||||
await test.step(`SessionStorage Work Order Number:${workOrderNumber}`, async () => {
|
const workOrderNumberValue = await this.workOrderNumberText.textContent();
|
||||||
console.log(`SessionStorage Work Order Number:${workOrderNumber}`);
|
expect.soft(workOrderNumberValue).toEqual(workOrderNumber);
|
||||||
});
|
}
|
||||||
|
|
||||||
|
async validateAppointmentTypeHeader() {
|
||||||
|
const sessionStorage = JSON.parse(await this.page.evaluate('sessionStorage.getItem(\'submittedOrder\')'));
|
||||||
|
const appointmentType = sessionStorage.serviceLocation.appointmentType;
|
||||||
|
const appointmentTypeValue = await this.appointmentTypeText.textContent();
|
||||||
|
const apptDetailsValue = await this.apptDetailsText.textContent();
|
||||||
|
|
||||||
|
if (appointmentTypeValue?.includes('going to a Safelite shop') && apptDetailsValue?.includes('Drop off before 9:30 AM')) {
|
||||||
|
expect.soft(appointmentType).toEqual('Dropoff');
|
||||||
|
} else if (appointmentTypeValue?.includes('going to a Safelite shop')) {
|
||||||
|
expect.soft(appointmentType).toEqual('Inshop');
|
||||||
|
} else {
|
||||||
|
expect.soft(appointmentType).toEqual('Mobile');
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async validateURL() {
|
async validateURL() {
|
||||||
|
|
|
||||||
|
|
@ -1,60 +1,79 @@
|
||||||
import { expect, type Locator, type Page } from '@playwright/test';
|
import { expect, type Locator, type Page } from '@playwright/test';
|
||||||
import { BasePage } from './BasePage';
|
import { BasePage } from './BasePage';
|
||||||
import { IPaymentDetails } from '@business-logic/types/CustomerDetails';
|
import { IClaimDetails, IPaymentDetails } from '@business-logic/types/CustomerDetails';
|
||||||
import { PaymentType } from '@business-logic/types/Enums';
|
import { PaymentType, ServicePackage } from '@business-logic/types/Enums';
|
||||||
import { PaymentPage } from './PaymentPage';
|
import { PaymentPage } from './PaymentPage';
|
||||||
import { AfterpayPage } from './AfterpayPage';
|
import { AfterpayPage } from './AfterpayPage';
|
||||||
import { PaypalPage } from './PaypalPage';
|
import { PaypalPage } from './PaypalPage';
|
||||||
|
|
||||||
export class PaymentMethodPage extends BasePage {
|
export class PaymentMethodPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
readonly payAtServiceButton: Locator;
|
|
||||||
readonly havePaymentReadyMsg: Locator;
|
|
||||||
readonly payNowButton: Locator;
|
|
||||||
readonly payInFourButton: Locator;
|
|
||||||
readonly paypalButton: Locator;
|
|
||||||
readonly paymentPage: PaymentPage;
|
|
||||||
readonly paypalPage: PaypalPage;
|
readonly paypalPage: PaypalPage;
|
||||||
|
readonly paymentPage: PaymentPage;
|
||||||
|
|
||||||
|
readonly payNowButton: Locator;
|
||||||
|
readonly paypalButton: Locator;
|
||||||
|
readonly payInFourButton: Locator;
|
||||||
|
readonly payAtAppointmentButton: Locator;
|
||||||
|
|
||||||
|
readonly textReminderYesButton: Locator;
|
||||||
|
readonly textReminderNoButton: Locator;
|
||||||
|
readonly continueToCheckoutButton: Locator;
|
||||||
|
readonly submitButton: Locator;
|
||||||
|
|
||||||
issPageValue = 'payment-method';
|
issPageValue = 'payment-method';
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.payAtServiceButton = this.page.locator('[buttonlabel="Pay at my appointment"]'); //this.page.getByText('Pay at time of service');
|
|
||||||
this.havePaymentReadyMsg = this.page.getByText('Please have payment ready during your appointment.'); // it will be displayed when there is no payment option
|
|
||||||
this.payNowButton = this.page.locator('[buttonlabel="Pay now"]');
|
|
||||||
this.payInFourButton = this.page.locator('[buttonlabel="Pay in 4 installments"]');
|
|
||||||
this.paypalButton = this.page.frameLocator('iframe[name="card-frame"]').locator('div[id="paypalParentDiv"]');
|
|
||||||
this.paymentPage = new PaymentPage(page);
|
|
||||||
this.paypalPage = new PaypalPage(page);
|
this.paypalPage = new PaypalPage(page);
|
||||||
|
this.paymentPage = new PaymentPage(page);
|
||||||
|
|
||||||
|
this.payNowButton = this.page.locator('[buttonlabel="Pay now"]'); // credit and paypal options behind this button
|
||||||
|
this.paypalButton = this.page.frameLocator('iframe[name="card-frame"]').locator('div[id="paypalParentDiv"]');
|
||||||
|
this.payInFourButton = this.page.locator('[buttonlabel="Pay in 4 installments"]'); // Afterpay
|
||||||
|
this.payAtAppointmentButton = this.page.locator('[buttonlabel="Pay at my appointment"]');
|
||||||
|
|
||||||
|
this.textReminderYesButton = this.page.locator('div.button-content', { hasText: /^yes$/i });
|
||||||
|
this.textReminderNoButton = this.page.locator('div.button-content', { hasText: 'No' });
|
||||||
|
this.continueToCheckoutButton = this.page.getByRole('button', { name: 'Continue to checkout' });
|
||||||
|
this.submitButton = this.page.getByRole('button', { name: 'Submit' });
|
||||||
}
|
}
|
||||||
|
|
||||||
async executePayment(paymentDetails: IPaymentDetails) {
|
async executePayment(paymentDetails: IPaymentDetails, claimDetails: IClaimDetails, servicePackage: ServicePackage) {
|
||||||
const browserContext = this.page.context();
|
const browserContext = this.page.context();
|
||||||
|
|
||||||
switch (paymentDetails.paymentType) {
|
switch (paymentDetails.paymentType) {
|
||||||
case PaymentType.Credit:
|
case PaymentType.Credit:
|
||||||
await this.selectCreditCard();
|
await this.payNowButton.click();
|
||||||
await this.paymentPage.populateCreditCardDetails(paymentDetails);
|
await this.textReminderYesButton.click();
|
||||||
|
await this.continueToCheckoutButton.click();
|
||||||
|
await this.selectCreditCard(paymentDetails);
|
||||||
break;
|
break;
|
||||||
case PaymentType.Paypal:
|
case PaymentType.Paypal:
|
||||||
|
await this.payNowButton.click();
|
||||||
|
await this.textReminderYesButton.click();
|
||||||
|
await this.continueToCheckoutButton.click();
|
||||||
await this.selectPaypal();
|
await this.selectPaypal();
|
||||||
await this.paypalPage.completePaypalPurchase(paymentDetails);
|
await this.paypalPage.completePaypalPurchase(paymentDetails);
|
||||||
break;
|
break;
|
||||||
case PaymentType.AfterPay:
|
case PaymentType.AfterPay:
|
||||||
await this.payInFourButton.click();
|
await this.payInFourButton.click();
|
||||||
await this.nextPage();
|
await this.textReminderYesButton.click();
|
||||||
|
await this.continueToCheckoutButton.click();
|
||||||
|
|
||||||
// Capture popup
|
// Capture popup
|
||||||
const afterpayPopup = await browserContext.waitForEvent('page');
|
const afterpayPopup = await browserContext.waitForEvent('page');
|
||||||
const afterpayPage = new AfterpayPage(afterpayPopup);
|
const afterpayPage = new AfterpayPage(afterpayPopup);
|
||||||
|
|
||||||
// Execute payment
|
// Execute payment
|
||||||
await afterpayPage.executeAfterpayPayment(paymentDetails);
|
await afterpayPage.executeAfterpayPayment(paymentDetails, claimDetails, servicePackage);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case PaymentType.PayAtService:
|
case PaymentType.PayAtService:
|
||||||
await this.selectPayAtService();
|
await this.payAtAppointmentButton.click();
|
||||||
|
await this.textReminderYesButton.click();
|
||||||
|
await this.submitButton.click();
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
console.error('PaymentMethodPage >> Logic for this payment method unimplemented');
|
console.error('PaymentMethodPage >> Logic for this payment method unimplemented');
|
||||||
|
|
@ -63,22 +82,19 @@ export class PaymentMethodPage extends BasePage {
|
||||||
}
|
}
|
||||||
|
|
||||||
async selectPaypal() {
|
async selectPaypal() {
|
||||||
await this.payNowButton.click();
|
|
||||||
await this.nextPage();
|
|
||||||
await this.paypalButton.click();
|
await this.paypalButton.click();
|
||||||
}
|
}
|
||||||
|
|
||||||
async selectCreditCard() {
|
async selectCreditCard(paymentDetails: IPaymentDetails) {
|
||||||
await this.payNowButton.click();
|
await this.paymentPage.populateCreditCardDetails(paymentDetails);
|
||||||
await this.nextPage();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async selectPayAtService() {
|
async selectPayAtAppointment() {
|
||||||
await this.payAtServiceButton.click();
|
await this.payAtAppointmentButton.click();
|
||||||
}
|
}
|
||||||
|
|
||||||
// async validateAmountDue(customer){
|
async submitOrderWithoutPIA() {
|
||||||
// await this.amountDueDropDown.click();
|
await this.textReminderYesButton.click();
|
||||||
// await expect(this.deductibleAmountTextField).toContainText(`${customer.deductibleAmount}`);
|
await this.submitButton.click();
|
||||||
// }
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -1,5 +1,6 @@
|
||||||
import { type Locator, type Page } from '@playwright/test';
|
import { type Locator, type Page } from '@playwright/test';
|
||||||
import { BasePage } from './BasePage';
|
import { BasePage } from './BasePage';
|
||||||
|
import { AfterpayPage } from './AfterpayPage';
|
||||||
import { IPaymentDetails } from '@business-logic/types/CustomerDetails';
|
import { IPaymentDetails } from '@business-logic/types/CustomerDetails';
|
||||||
|
|
||||||
export class PaymentPage extends BasePage {
|
export class PaymentPage extends BasePage {
|
||||||
|
|
@ -26,8 +27,7 @@ export class PaymentPage extends BasePage {
|
||||||
this.cityTextField = page.frameLocator('iframe[name="card-frame"]').getByRole('textbox', { name: 'City' });
|
this.cityTextField = page.frameLocator('iframe[name="card-frame"]').getByRole('textbox', { name: 'City' });
|
||||||
this.stateDropDown = page.frameLocator('iframe[name="card-frame"]').getByRole('combobox', { name: 'State' });
|
this.stateDropDown = page.frameLocator('iframe[name="card-frame"]').getByRole('combobox', { name: 'State' });
|
||||||
this.billingZipTextField = page.frameLocator('iframe[name="card-frame"]').getByRole('textbox', { name: 'Billing ZIP code' });;
|
this.billingZipTextField = page.frameLocator('iframe[name="card-frame"]').getByRole('textbox', { name: 'Billing ZIP code' });;
|
||||||
this.submitPaymentButton = page.frameLocator('iframe[name="card-frame"]').locator('#buttonContainer');
|
this.submitPaymentButton = page.getByRole('button', { name: 'Submit payment' });
|
||||||
// this.validateURL(this.url);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async populateCreditCardDetails(paymentDetails: IPaymentDetails){
|
async populateCreditCardDetails(paymentDetails: IPaymentDetails){
|
||||||
|
|
|
||||||
|
|
@ -1,27 +1,33 @@
|
||||||
import { expect, type Locator, type Page } from '@playwright/test';
|
import { expect, type Locator, type Page } from "@playwright/test";
|
||||||
import { BasePage } from './BasePage';
|
import { BasePage } from "./BasePage";
|
||||||
import { IPaymentDetails } from '@business-logic/types/CustomerDetails';
|
import { IPaymentDetails } from "@business-logic/types/CustomerDetails";
|
||||||
|
|
||||||
export class PaypalPage extends BasePage {
|
export class PaypalPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
readonly loginWithPasswordButton: Locator;
|
readonly usernameTextBox: Locator;
|
||||||
readonly passwordTextBox: Locator;
|
readonly nextButton: Locator;
|
||||||
readonly paypalLoginButton: Locator;
|
readonly passwordTextBox: Locator;
|
||||||
readonly completePurchaseButton: Locator;
|
readonly paypalLoginButton: Locator;
|
||||||
|
readonly payButton: Locator;
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.loginWithPasswordButton = page.getByRole('link', { name: 'Log in with a password instead' });
|
this.usernameTextBox = page.locator("#email");
|
||||||
this.passwordTextBox = page.getByPlaceholder('Password');
|
this.nextButton = page.getByRole("button", { name: "Next" });
|
||||||
this.paypalLoginButton = page.getByRole('button', { name: 'Log In', exact: true });
|
this.passwordTextBox = page.getByRole("textbox", { name: "Password" });
|
||||||
this.completePurchaseButton = page.getByTestId('submit-button-initial');
|
this.paypalLoginButton = page.getByRole("button", {
|
||||||
}
|
name: "Log In",
|
||||||
|
exact: true,
|
||||||
|
});
|
||||||
|
this.payButton = page.getByRole("button", { name: "Pay $" });
|
||||||
|
}
|
||||||
|
|
||||||
async completePaypalPurchase(paymentDetails: IPaymentDetails){
|
async completePaypalPurchase(paymentDetails: IPaymentDetails) {
|
||||||
await this.loginWithPasswordButton.click();
|
await this.usernameTextBox.fill(paymentDetails.username!);
|
||||||
await this.passwordTextBox.fill(paymentDetails.password!);
|
await this.nextButton.click();
|
||||||
await this.paypalLoginButton.click();
|
await this.passwordTextBox.fill(paymentDetails.password!);
|
||||||
await this.completePurchaseButton.click();
|
await this.paypalLoginButton.click();
|
||||||
}
|
await this.payButton.click();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,20 +1,60 @@
|
||||||
import { type Locator, type Page } from '@playwright/test';
|
import { type Locator, type Page } from '@playwright/test';
|
||||||
import { BasePage } from './BasePage';
|
import { BasePage } from './BasePage';
|
||||||
import { ICustomerDetails } from '@business-logic/types/CustomerDetails';
|
import { ICustomerDetails } from '@business-logic/types/CustomerDetails';
|
||||||
import { AddressForm } from './forms/AddressForm';
|
|
||||||
|
|
||||||
export class PolicyHolderDetailsPage extends BasePage {
|
export class PolicyHolderDetailsPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
readonly addressForm: AddressForm;
|
readonly firstNameTextBox: Locator;
|
||||||
|
readonly lastNameTextBox: Locator;
|
||||||
|
readonly addressInputBox: Locator;
|
||||||
|
readonly emailAddressTextBox: Locator;
|
||||||
|
|
||||||
readonly issPageValue = 'policy-holder-details';
|
readonly issPageValue = 'policy-holder-details';
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.addressForm = new AddressForm(page);
|
this.firstNameTextBox = page.locator('#firstNameField');
|
||||||
|
this.lastNameTextBox = page.locator('#lastNameField');
|
||||||
|
this.emailAddressTextBox = page.locator('#emailField');
|
||||||
|
this.addressInputBox = page.locator('input[name="autocomplete"]'); // for essential flows
|
||||||
}
|
}
|
||||||
|
|
||||||
async fillCustomerDetails(customerDetails: ICustomerDetails){
|
async fillCustomerDetails(customerDetails: ICustomerDetails){
|
||||||
await this.addressForm.populateAddress(customerDetails);
|
// Check if firstName field is empty, then fill it
|
||||||
|
const firstNameValue = await this.firstNameTextBox.inputValue();
|
||||||
|
if (!firstNameValue || firstNameValue.trim() === '') {
|
||||||
|
if (customerDetails.firstName) {
|
||||||
|
await this.firstNameTextBox.fill(customerDetails.firstName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check if lastName field is empty, then fill it
|
||||||
|
const lastNameValue = await this.lastNameTextBox.inputValue();
|
||||||
|
if (!lastNameValue || lastNameValue.trim() === '') {
|
||||||
|
if (customerDetails.lastName) {
|
||||||
|
await this.lastNameTextBox.fill(customerDetails.lastName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fill email address for both essential and advanced flows
|
||||||
|
await this.emailAddressTextBox.fill(customerDetails.email);
|
||||||
|
|
||||||
|
const addressValue = await this.addressInputBox.inputValue();
|
||||||
|
|
||||||
|
// For essential flows, when address fields are not pre-filled
|
||||||
|
if (!addressValue || addressValue.trim() === '') {
|
||||||
|
await this.addressInputBox.click();
|
||||||
|
await this.addressInputBox.fill(customerDetails.address.street);
|
||||||
|
|
||||||
|
// Wait for suggestions to load (Google Places has a slight delay)
|
||||||
|
await this.page.locator('.pac-item').first().waitFor({ state: 'visible', timeout: 5000 });
|
||||||
|
|
||||||
|
// Click the first result
|
||||||
|
await this.page.locator('.pac-item').first().click();
|
||||||
|
|
||||||
|
// Optional: wait for the input to be populated by Google Places
|
||||||
|
await this.addressInputBox.waitFor({ state: 'attached' });
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -5,11 +5,14 @@ import { IVehicleDetails } from '@business-logic/types/CustomerDetails';
|
||||||
export class PolicyVehiclesPage extends BasePage {
|
export class PolicyVehiclesPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
issPageValue = 'policy-vehicles';
|
issPageValue = 'policy-vehicles';
|
||||||
|
readonly addAnotherVehicleButton: Locator;
|
||||||
|
readonly selectVehicleOnPolicyButton: Locator;
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
// this.validateURL(this.url);
|
this.addAnotherVehicleButton = this.page.getByText('Add another vehicle');
|
||||||
|
this.selectVehicleOnPolicyButton = this.page.locator(`input[type="radio"][name="policyVehiclesQuestionOption"]`).first();
|
||||||
}
|
}
|
||||||
|
|
||||||
async validateVehicleIsOnPolicy(vehicleDetails: IVehicleDetails) {
|
async validateVehicleIsOnPolicy(vehicleDetails: IVehicleDetails) {
|
||||||
|
|
@ -21,8 +24,9 @@ export class PolicyVehiclesPage extends BasePage {
|
||||||
const vehicleRegExp = new RegExp(`${vehicleDetails.year} .+ ${vehicleDetails.model}`, 'i');
|
const vehicleRegExp = new RegExp(`${vehicleDetails.year} .+ ${vehicleDetails.model}`, 'i');
|
||||||
await this.page.locator('label').filter({hasText: vehicleRegExp}).locator('div').click();
|
await this.page.locator('label').filter({hasText: vehicleRegExp}).locator('div').click();
|
||||||
}
|
}
|
||||||
async selectVehicleNotListed(){
|
|
||||||
await this.page.getByText('Vehicle not listed').click();
|
async addAnotherVehicle(){
|
||||||
|
await this.page.getByRole('button', {name: 'Add another vehicle'}).click();
|
||||||
}
|
}
|
||||||
|
|
||||||
async assertNonServiceableAlertBehavior(){
|
async assertNonServiceableAlertBehavior(){
|
||||||
|
|
|
||||||
|
|
@ -3,48 +3,78 @@ import { BasePage } from './BasePage';
|
||||||
|
|
||||||
export class ProviderPreferencePage extends BasePage {
|
export class ProviderPreferencePage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
readonly scheduleWithSafelite: Locator;
|
readonly scheduleNowButton: Locator;
|
||||||
readonly scheduleWithOther: Locator;
|
readonly findAnotherShopButton: Locator;
|
||||||
readonly acknowledgeAdasButton: Locator;
|
|
||||||
|
readonly acknowledgeAdasCheckbox: Locator;
|
||||||
readonly gotItButton: Locator;
|
readonly gotItButton: Locator;
|
||||||
|
readonly tpaRecalModal: Locator;
|
||||||
|
readonly learnMoreLink: Locator;
|
||||||
|
readonly yesButton: Locator;
|
||||||
|
readonly noButton: Locator;
|
||||||
readonly acknowledgeCheckbox: Locator;
|
readonly acknowledgeCheckbox: Locator;
|
||||||
readonly stateLawModalHeading: Locator;
|
readonly tpaRecalModalContinueButton: Locator;
|
||||||
|
readonly stateLawModalText: Locator;
|
||||||
|
readonly stateLawRepairModalText: Locator;
|
||||||
|
readonly stateLawModalOkayButton: Locator;
|
||||||
issPageValue = 'provider-preference';
|
issPageValue = 'provider-preference';
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
// this.scheduleWithSafelite = this.page.locator('div').filter({ hasText: /Schedule online with |Safelite AutoGlass/ }).first();
|
|
||||||
this.scheduleWithSafelite = this.page.getByText(/Schedule online with|Safelite AutoGlass/).first();
|
this.scheduleNowButton = this.page.getByRole('button', { name: 'Schedule now' });
|
||||||
this.scheduleWithOther = this.page.getByText(/Find another shop|Choose my own shop/).first();
|
this.findAnotherShopButton = this.page.getByRole('link', { name: 'Find another shop' });
|
||||||
this.acknowledgeAdasButton = this.page.getByLabel('I acknowledge that my vehicle');
|
|
||||||
this.gotItButton = this.page.getByRole('button', { name: 'Got it' });
|
//Recal modal
|
||||||
this.acknowledgeCheckbox = this.page.locator('#tpaAcknowledgement');
|
this.tpaRecalModal = this.page.locator('#TPARecalModal');
|
||||||
this.stateLawModalHeading = this.page.getByRole('heading').filter({ hasText: /.* State Law/});
|
this.learnMoreLink = this.page.locator('#moreDetails');
|
||||||
|
this.yesButton = this.page.getByText('Yes', { exact: true }); // schedule with Safelite
|
||||||
|
this.noButton = this.page.getByText('No', { exact: true }); // schedule with TPA
|
||||||
|
this.acknowledgeAdasCheckbox = this.page.getByRole('checkbox', { name: /I acknowledge/i })
|
||||||
|
this.tpaRecalModalContinueButton = this.page.locator('#modalbtn', { hasText: 'Continue' });
|
||||||
|
|
||||||
|
// State law modal - is there a difference between repair and replacement modals? need to check
|
||||||
|
this.stateLawModalText = this.page.getByText(/law prohibits us from requiring you.*You have the right to select the motor vehicle repair shop of your choice\./is);
|
||||||
|
this.stateLawRepairModalText = this.page.getByText(/We are prohibited by law from requiring that repairs be done at a specific automotive repair dealer. You are entitled to select the auto body repair shop to repair damage covered by us\./is);
|
||||||
|
this.stateLawModalOkayButton = this.page.getByRole('button', { name: 'Okay' })
|
||||||
}
|
}
|
||||||
|
|
||||||
async selectProvider(isSafelite = true) {
|
async selectProvider(isSafelite = true) {
|
||||||
if (isSafelite) {
|
if (isSafelite) {
|
||||||
await this.scheduleWithSafelite.click();
|
await this.scheduleNowButton.click();
|
||||||
await this.nextPage();
|
await this.nextPage();
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
await this.scheduleWithOther.waitFor({ state: 'visible' });
|
await this.findAnotherShopButton.waitFor({ state: 'visible' });
|
||||||
await this.scheduleWithOther.click();
|
await this.findAnotherShopButton.click();
|
||||||
await this.continueButton.click();
|
await this.tpaRecalModal.waitFor({ state: 'visible' });
|
||||||
//if(await this.acknowledgeAdasButton.isEnabled({timeout: 2500})){
|
await this.scheduleTPAWithAdas();
|
||||||
// await this.acknowledgeAdasButton.click();
|
|
||||||
// await this.gotItButton.click();
|
|
||||||
// await this.page.waitForTimeout(1000);
|
|
||||||
//}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
async acknowledgeRecalNotificaiton() {
|
|
||||||
await this.acknowledgeAdasButton.click();
|
async scheduleWithSafeliteADAS() {
|
||||||
await this.gotItButton.click();
|
await this.learnMoreLink.click();
|
||||||
|
await this.yesButton.click();
|
||||||
|
await this.tpaRecalModalContinueButton.click();
|
||||||
|
}
|
||||||
|
|
||||||
|
async scheduleTPAWithAdas() {
|
||||||
|
await this.learnMoreLink.click();
|
||||||
|
await this.noButton.click();
|
||||||
|
await this.acknowledgeAdasCheckbox.click();
|
||||||
|
await this.tpaRecalModalContinueButton.click();
|
||||||
|
}
|
||||||
|
|
||||||
|
async scheduleTPAWithoutAdas() {
|
||||||
|
await this.findAnotherShopButton.click();
|
||||||
}
|
}
|
||||||
|
|
||||||
async validateStateLawModalIsVisible() {
|
async validateStateLawModalIsVisible() {
|
||||||
await expect.soft(this.stateLawModalHeading).toBeVisible();
|
await expect.soft(this.stateLawModalText).toBeVisible();
|
||||||
|
}
|
||||||
|
|
||||||
|
async validateStateLawRepairModalIsVisible() {
|
||||||
|
await expect.soft(this.stateLawRepairModalText).toBeVisible();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -3,56 +3,111 @@ import { BasePage } from './BasePage';
|
||||||
import { IAppointmentDetails } from '@business-logic/types/CustomerDetails';
|
import { IAppointmentDetails } from '@business-logic/types/CustomerDetails';
|
||||||
import { formatDate, formatTime } from '@impl/utils/DateUtils';
|
import { formatDate, formatTime } from '@impl/utils/DateUtils';
|
||||||
import { ServiceLocation } from '@business-logic/types/Enums';
|
import { ServiceLocation } from '@business-logic/types/Enums';
|
||||||
|
import { getCustomerDetails, ITestData } from 'safelite-playwright-core';
|
||||||
|
|
||||||
export class SchedulePage extends BasePage {
|
export class SchedulePage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
issPageValue = 'schedule-page';
|
issPageValue = 'schedule-page';
|
||||||
readonly firstAvailableDate: Locator;
|
|
||||||
|
readonly inShopButton: Locator;
|
||||||
|
readonly mobileButton: Locator;
|
||||||
|
readonly moreLocationsButton: Locator;
|
||||||
|
readonly zipCodeTextBox: Locator;
|
||||||
|
readonly findButton: Locator;
|
||||||
|
readonly selectAShopOptions: Locator;
|
||||||
|
readonly firstAppointmentButton : Locator;
|
||||||
|
readonly firstAvailableAMDate: Locator;
|
||||||
|
readonly firstAvailablePMDate: Locator;
|
||||||
readonly firstAvailableTime: Locator;
|
readonly firstAvailableTime: Locator;
|
||||||
|
readonly firstAvailabeAMTime: Locator;
|
||||||
readonly modalContinueButton: Locator;
|
readonly modalContinueButton: Locator;
|
||||||
readonly dropOffButton: Locator;
|
readonly dropOffButton: Locator;
|
||||||
readonly dateText: Locator;
|
readonly dateText: Locator;
|
||||||
readonly viewMoreDatesLink: Locator;
|
readonly viewMoreDatesLink: Locator;
|
||||||
|
|
||||||
|
readonly continueButton: Locator;
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.firstAvailableDate = this.page.locator('.selectable-day').locator('nth=0');
|
|
||||||
this.firstAvailableTime = this.page.locator('label').filter({ hasText: /AM|PM/ }).locator('div').locator('nth=0');
|
this.inShopButton = this.page.locator('[buttonlabel="At a Safelite shop"]');
|
||||||
|
this.mobileButton = this.page.locator('[buttonlabel="Have Safelite come to me"]');
|
||||||
|
// For in shop
|
||||||
|
this.moreLocationsButton = this.page.getByRole('button', { name: 'More Locations' });
|
||||||
|
// For mobile
|
||||||
|
this.zipCodeTextBox = this.page.locator('#serviceZipCode');
|
||||||
|
this.findButton = this.page.getByRole('button', { name: 'Find' });
|
||||||
|
// For in-shop and drop off
|
||||||
|
this.selectAShopOptions = this.page.locator('[class="shop-question"]');
|
||||||
|
this.firstAppointmentButton = this.page.locator('#availabilityIndicator').first();
|
||||||
|
this.firstAvailableAMDate = this.page.locator('morning-row-cell has-appointments selected-date').first();
|
||||||
|
this.firstAvailablePMDate = this.page.locator('afternoon-row-cell has-appointments selected-date').first();
|
||||||
|
this.firstAvailableTime = this.page.locator('.time-slot-button').first();
|
||||||
|
this.firstAvailabeAMTime = this.page.locator('.time-slot-button').nth(0);
|
||||||
this.modalContinueButton = this.page.locator('#modalbtn');
|
this.modalContinueButton = this.page.locator('#modalbtn');
|
||||||
this.dropOffButton = this.page.getByText('Drop off your vehicle', { exact: true });
|
this.dropOffButton = this.page.locator('[class="dropoff-label"]');
|
||||||
this.dateText = this.page.locator('[class="modal-header mb-2 mt-2"]');
|
this.dateText = this.page.locator('[class="modal-header mb-2 mt-2"]');
|
||||||
this.viewMoreDatesLink = this.page.getByText(/View more dates/).first();
|
this.viewMoreDatesLink = this.page.getByRole('button', { name: 'More Right arrow icon' });
|
||||||
|
|
||||||
|
this.continueButton = this.page.locator('#stacked').locator('button:has-text("Continue")');
|
||||||
}
|
}
|
||||||
|
|
||||||
async scheduleAppointment(appointmentDetails: IAppointmentDetails) {
|
// Select in shop and schedule
|
||||||
const formattedDate = formatDate(appointmentDetails.appointmentDate!);
|
async scheduleInShop(appointmentDetails?: IAppointmentDetails){
|
||||||
const formattedTime = formatTime(appointmentDetails.appointmentDate!);
|
|
||||||
const dateInput = this.page.locator(`div[id="${formattedDate}"]`);
|
if (appointmentDetails?.serviceLocation === ServiceLocation.InShop) {
|
||||||
const timeButton = this.page.locator(`div[aria-label="${formattedTime}"]`);
|
try {await this.inShopButton.waitFor({ state: 'visible', timeout: 5000 });
|
||||||
if (await dateInput.isVisible()) {
|
await this.inShopButton.isVisible()
|
||||||
await dateInput.click();
|
await this.inShopButton.click();
|
||||||
} else {
|
await (await this.getFirstNonDropOffTimeSlot()).click();
|
||||||
await this.viewMoreDatesLink.click();
|
} catch {
|
||||||
await dateInput.click();
|
await this.inShopButton.isHidden()
|
||||||
|
await (await this.getFirstNonDropOffTimeSlot()).click();
|
||||||
}
|
}
|
||||||
await timeButton.click();
|
} else if (appointmentDetails?.serviceLocation === ServiceLocation.DropOff) {
|
||||||
await this.modalContinueButton.click();
|
if (await this.inShopButton.isVisible()){
|
||||||
}
|
await this.inShopButton.waitFor({ state: 'visible', timeout: 5000 });
|
||||||
|
await this.inShopButton.click();
|
||||||
|
|
||||||
async scheduleFirstAppointment(serviceLocation: ServiceLocation) {
|
if (await this.dropOffButton.isVisible()) {
|
||||||
if (await this.firstAvailableDate.isVisible()) {
|
await this.dropOffButton.waitFor({ state: 'visible', timeout: 5000 });
|
||||||
await this.firstAvailableDate.click();
|
await this.dropOffButton.click()
|
||||||
} else {
|
} else {
|
||||||
await this.viewMoreDatesLink.click();
|
await (await this.getFirstNonDropOffTimeSlot()).click();
|
||||||
while(await this.firstAvailableDate.isHidden()){
|
|
||||||
await this.viewMoreDatesLink.click();
|
|
||||||
}
|
}
|
||||||
await this.firstAvailableDate.click();
|
} else {
|
||||||
|
await (await this.getFirstNonDropOffTimeSlot()).click();
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
await this.selectFirstAvailableTime();
|
||||||
}
|
}
|
||||||
|
await this.continueButton.click();
|
||||||
|
}
|
||||||
|
|
||||||
serviceLocation === ServiceLocation.DropOff ? await this.dropOffButton.click() : await this.firstAvailableTime.click();
|
// Select mobile button, enter zip code, click find button, select first available time and continue
|
||||||
await this.modalContinueButton.click();
|
async scheduleMobile(appointmentDetails: IAppointmentDetails){
|
||||||
return (`${await this.dateText.allInnerTexts()}`);
|
await this.mobileButton.click();
|
||||||
|
await this.zipCodeTextBox.fill(appointmentDetails.serviceAddress!.postalCode!);
|
||||||
|
await this.findButton.click();
|
||||||
|
await this.selectFirstAvailableTime();
|
||||||
|
await this.continueButton.click();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Selects the first available time slot but if its not visible, click "More" first to load more dates and times
|
||||||
|
async selectFirstAvailableTime(): Promise<void> {
|
||||||
|
if (await this.firstAvailableTime.isVisible()) {
|
||||||
|
await this.firstAvailableTime.click();
|
||||||
|
} else {
|
||||||
|
await this.viewMoreDatesLink.click();
|
||||||
|
await this.firstAvailableTime.waitFor({ state: 'visible' });
|
||||||
|
await this.firstAvailableTime.click();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
async getFirstNonDropOffTimeSlot(): Promise<Locator> {
|
||||||
|
const timeSlots = this.page.locator('.time-slot-button');
|
||||||
|
const nonDropOff = timeSlots.filter({ hasNotText: /Drop & Go/i });
|
||||||
|
return nonDropOff.first();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -18,26 +18,6 @@ export class ServiceLocationPage extends BasePage {
|
||||||
readonly RecalWarningMessage2: Locator;
|
readonly RecalWarningMessage2: Locator;
|
||||||
readonly militaryWarningMessage: Locator;
|
readonly militaryWarningMessage: Locator;
|
||||||
|
|
||||||
// For in-shop and drop off
|
|
||||||
readonly selectAShopOptions: Locator;
|
|
||||||
readonly firstAppointmentButton: Locator;
|
|
||||||
readonly changeZipButton: Locator;
|
|
||||||
readonly updateZipTextBox: Locator;
|
|
||||||
readonly saveZipButton: Locator;
|
|
||||||
|
|
||||||
// For mobile
|
|
||||||
readonly enterServiceAddressButton: Locator;
|
|
||||||
readonly serviceAddressTextBox: Locator;
|
|
||||||
readonly aptNumberTextBox: Locator;
|
|
||||||
readonly cityTextBox: Locator;
|
|
||||||
readonly stateDropDown: Locator;
|
|
||||||
readonly zipCodeTextBox: Locator;
|
|
||||||
readonly vehicleProtectedYesButton: Locator;
|
|
||||||
readonly vehicleProtectedNoButton: Locator;
|
|
||||||
readonly saveAddressButton: Locator;
|
|
||||||
|
|
||||||
issPageValue = 'service-location';
|
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
|
|
@ -52,80 +32,6 @@ export class ServiceLocationPage extends BasePage {
|
||||||
this.RecalWarningMessage2 = this.page.getByText(/advanced safety system recalibration needs to be done in our shop./);
|
this.RecalWarningMessage2 = this.page.getByText(/advanced safety system recalibration needs to be done in our shop./);
|
||||||
this.militaryWarningMessage = this.page.locator('[class*="widget-name-AlertMilitaryBaseZipWidget"]');
|
this.militaryWarningMessage = this.page.locator('[class*="widget-name-AlertMilitaryBaseZipWidget"]');
|
||||||
|
|
||||||
// For in-shop and drop off
|
|
||||||
this.selectAShopOptions = this.page.locator('[class="shop-question"]');
|
|
||||||
// this.firstAppointmentButton = this.page.locator('div').filter({ hasText: /Appts/}).first();
|
|
||||||
this.firstAppointmentButton = this.page.locator('#availabilityIndicator').first();
|
|
||||||
this.changeZipButton = this.page.locator('[id="serviceZipLinkPromptId"]');
|
|
||||||
this.updateZipTextBox = this.page.getByRole('textbox', { name: 'Update your service ZIP code'});
|
|
||||||
this.saveZipButton = this.page.getByRole('button', { name: 'Save ZIP code' });
|
|
||||||
|
|
||||||
|
|
||||||
// For mobile
|
|
||||||
this.enterServiceAddressButton = this.page.getByRole('link', { name: 'Enter your service address' });
|
|
||||||
this.serviceAddressTextBox = this.page.getByRole('textbox', { name: 'Street Address' });
|
|
||||||
this.aptNumberTextBox = this.page.getByRole('textbox', { name: 'Apt. number'});
|
|
||||||
this.cityTextBox = this.page.getByRole('textbox', { name: 'City' });
|
|
||||||
this.stateDropDown = this.page.getByRole('combobox', { name: 'State' });
|
|
||||||
this.zipCodeTextBox = this.page.getByRole('textbox', { name: 'Zip code' });
|
|
||||||
this.vehicleProtectedYesButton = this.page.locator('label').filter({ hasText: 'Yes' }).locator('div');
|
|
||||||
this.vehicleProtectedNoButton = this.page.locator('label').filter({ hasText: 'No' }).locator('div');
|
|
||||||
this.saveAddressButton = this.page.getByRole('button', { name: 'Save Address' });
|
|
||||||
}
|
|
||||||
|
|
||||||
async selectLocation(appointmentDetails: IAppointmentDetails){
|
|
||||||
if (appointmentDetails.alternateServiceZip) {
|
|
||||||
await this.changeZipButton.click();
|
|
||||||
await this.fillAndValidate(this.updateZipTextBox, appointmentDetails.alternateServiceZip);
|
|
||||||
await this.saveZipButton.click();
|
|
||||||
}
|
|
||||||
|
|
||||||
switch(appointmentDetails.serviceLocation) {
|
|
||||||
case ServiceLocation.Mobile:
|
|
||||||
await this.scheduleMobile(appointmentDetails);
|
|
||||||
break;
|
|
||||||
case ServiceLocation.InShop:
|
|
||||||
await this.scheduleInShop(appointmentDetails);
|
|
||||||
break;
|
|
||||||
case ServiceLocation.DropOff:
|
|
||||||
await this.scheduleDropOff(appointmentDetails);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
async scheduleInShop(appointmentDetails?: IAppointmentDetails) {
|
|
||||||
await this.inShopButton.click();
|
|
||||||
if (appointmentDetails && appointmentDetails.shopAddress) {
|
|
||||||
await this.selectAShopOptions.locator(`[buttonbodycopy="${appointmentDetails.shopAddress}"]`).check();
|
|
||||||
} else {
|
|
||||||
await this.firstAppointmentButton.click();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
async scheduleMobile(appointmentDetails: IAppointmentDetails){
|
|
||||||
if (appointmentDetails.serviceAddress) {
|
|
||||||
await this.mobileButton.click();
|
|
||||||
await this.enterServiceAddressButton.click();
|
|
||||||
await this.addressForm.populateAddress({ address: appointmentDetails.serviceAddress! });
|
|
||||||
if (faker.datatype.boolean()) {
|
|
||||||
await this.vehicleProtectedYesButton.check();
|
|
||||||
} else {
|
|
||||||
await this.vehicleProtectedNoButton.check();
|
|
||||||
}
|
|
||||||
await this.saveAddressButton.click();
|
|
||||||
} else {
|
|
||||||
console.error('ServiceLocationPage >> Please supply an address')
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
async scheduleDropOff(appointmentDetails?: IAppointmentDetails){
|
|
||||||
await this.dropOffButton.click();
|
|
||||||
if (appointmentDetails && appointmentDetails.shopAddress) {
|
|
||||||
await this.selectAShopOptions.locator(`[buttonbodycopy="${appointmentDetails.shopAddress}"]`).check();
|
|
||||||
} else {
|
|
||||||
await this.firstAppointmentButton.click();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async validateRecalWarning(){
|
async validateRecalWarning(){
|
||||||
|
|
|
||||||
|
|
@ -6,21 +6,37 @@ export class ServicePackagesPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
readonly standardPackageButton: Locator;
|
readonly standardPackageButton: Locator;
|
||||||
readonly premiumPackageButton: Locator;
|
readonly premiumPackageButton: Locator;
|
||||||
readonly glassOnlyButton: Locator;
|
readonly glassOnlyPackageButton: Locator;
|
||||||
|
readonly wiperModal: Locator;
|
||||||
|
readonly wiperModalCloseButton: Locator;
|
||||||
|
readonly continueButton: Locator;
|
||||||
issPageValue = 'service-packages';
|
issPageValue = 'service-packages';
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.standardPackageButton = this.page.locator('li').filter({ hasText: 'Standard' });
|
this.standardPackageButton = this.page.locator('label[for="ServicePackageQuestion-TierTwo"]'); // standard package
|
||||||
this.premiumPackageButton = this.page.locator('li').filter({ hasText: 'Premium' });
|
this.premiumPackageButton = this.page.locator('label[for="ServicePackageQuestion-TierThree"]'); // premium package
|
||||||
this.glassOnlyButton = this.page.locator('li').filter({ hasText: 'Glass service' });
|
this.glassOnlyPackageButton = this.page.locator('label[for="ServicePackageQuestion-TierOne"]'); // glass only package
|
||||||
|
this.wiperModal = this.page.locator('#FrontWiperModal #modalbtn');
|
||||||
|
this.wiperModalCloseButton = this.page.locator('#FrontWiperModal').getByLabel('Close')
|
||||||
|
this.continueButton = this.page.getByRole('button', { name: 'Continue' });
|
||||||
// this.validateURL(this.url);
|
// this.validateURL(this.url);
|
||||||
}
|
}
|
||||||
|
|
||||||
async selectServicePackage(servicePackage: ServicePackage){
|
async selectServicePackage(servicePackage: ServicePackage){
|
||||||
await this.page.getByText(servicePackage).click();
|
if (servicePackage === ServicePackage.Standard) {
|
||||||
return (`${await this.page.locator('li').filter({ hasText: 'Premium' }).locator('[class="pricing-info"]').allInnerTexts()}`);
|
await this.standardPackageButton.check();
|
||||||
//return (`${await this.page.getByText(servicePackage).locator('[class="pricing-info"]').allInnerTexts()}`);
|
} else if (servicePackage === ServicePackage.Premium) {
|
||||||
|
await this.premiumPackageButton.check();
|
||||||
|
try {await this.wiperModal.waitFor({ state: 'visible', timeout: 5000 });
|
||||||
|
await this.wiperModalCloseButton.click();
|
||||||
|
} catch {
|
||||||
|
await this.continueButton.click();
|
||||||
|
}
|
||||||
|
} else if (servicePackage === ServicePackage.GlassOnly) {
|
||||||
|
await this.glassOnlyPackageButton.check();
|
||||||
|
}
|
||||||
|
await this.continueButton.click();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -4,16 +4,30 @@ import { BasePage } from './BasePage';
|
||||||
export class TpaConfirmationPage extends BasePage {
|
export class TpaConfirmationPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
readonly successMessage: Locator;
|
readonly successMessage: Locator;
|
||||||
|
readonly shopConfirmationMessage: Locator;
|
||||||
readonly issPageValue = 'tpa-confirmation';
|
readonly issPageValue = 'tpa-confirmation';
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.successMessage = page.getByText('Success');
|
this.successMessage = page.getByText('Thank you for submitting your claim; there is one final step.');
|
||||||
|
this.shopConfirmationMessage = page.locator('div.subheader').first()
|
||||||
|
}
|
||||||
|
|
||||||
|
async getTpaShopSelectedName() {
|
||||||
|
const sessionStorage = JSON.parse(await this.page.evaluate('sessionStorage.getItem(\'submittedOrder\')'));
|
||||||
|
const tpaShopSelectedName = sessionStorage.serviceLocation.provider.companyName;
|
||||||
|
return tpaShopSelectedName;
|
||||||
}
|
}
|
||||||
|
|
||||||
async validateSuccessMessage() {
|
async validateSuccessMessage() {
|
||||||
await expect(this.successMessage).toBeVisible();
|
const shopConfirmationMessageText = await this.shopConfirmationMessage.textContent();
|
||||||
}
|
const tpaShopSelectedNameText = await this.getTpaShopSelectedName();
|
||||||
|
|
||||||
|
await this.successMessage.waitFor({ state: 'visible' });
|
||||||
|
await expect(this.successMessage).toBeVisible();
|
||||||
|
expect.soft(shopConfirmationMessageText?.toLowerCase()).toContain(
|
||||||
|
('Your information has been sent to' + ' ' + tpaShopSelectedNameText).toLowerCase()
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -4,20 +4,12 @@ import { BasePage } from './BasePage';
|
||||||
export class TpaSearchPage extends BasePage {
|
export class TpaSearchPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
readonly firstLocationButton: Locator;
|
readonly firstLocationButton: Locator;
|
||||||
readonly doNotSeeMyShopButton: Locator;
|
|
||||||
issPageValue = 'tpa-search';
|
issPageValue = 'tpa-search';
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
// this.firstLocationButton = page.locator("fieldset[aria-labelledby='chooseShop']/span").first();
|
this.firstLocationButton = page.locator('div.button-content').first();
|
||||||
this.firstLocationButton = page.locator("#buttonLabelSpan").first();
|
|
||||||
|
|
||||||
this.doNotSeeMyShopButton = page.getByRole('link', { name: 'I don\'t see my shop' });
|
|
||||||
}
|
|
||||||
|
|
||||||
async selectDoNotSeeMyShop() {
|
|
||||||
await this.doNotSeeMyShopButton.click()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async selectFirstLocation() {
|
async selectFirstLocation() {
|
||||||
|
|
|
||||||
|
|
@ -1,18 +1,29 @@
|
||||||
import { expect, type Locator, type Page } from '@playwright/test';
|
import { expect, type Locator, type Page } from '@playwright/test';
|
||||||
import { BasePage } from './BasePage';
|
import { BasePage } from './BasePage';
|
||||||
|
import { IClaimDetails } from '@business-logic/types/CustomerDetails';
|
||||||
|
|
||||||
export class TpaSubmitPage extends BasePage {
|
export class TpaSubmitPage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
readonly deductible: Locator;
|
readonly deductible: Locator;
|
||||||
|
readonly recalAlert: Locator;
|
||||||
|
readonly learnMoreLink: Locator;
|
||||||
|
readonly recalModal: Locator;
|
||||||
|
readonly closeRecalModalButton: Locator;
|
||||||
issPageValue = 'tpa-submit';
|
issPageValue = 'tpa-submit';
|
||||||
|
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.deductible = page.getByText('Deductible $');
|
this.recalAlert = page.getByRole('alert').filter({ hasText: 'Some vehicle safety features may not work properly.'});
|
||||||
|
this.learnMoreLink = page.getByRole('link', { name: 'Learn more' });
|
||||||
|
this.recalModal = page.getByRole('dialog').filter({ hasText: 'IMPORTANT SERVICE REQUIRED' }).first();
|
||||||
|
this.closeRecalModalButton = page.locator('.modalbtn', { hasText: 'Close' });
|
||||||
|
this.deductible = page.locator('span#deductible-value, span.deductible-value');
|
||||||
}
|
}
|
||||||
|
|
||||||
async validateDeductible(expDeductible) {
|
async validateDeductible(claimDetails: IClaimDetails) {
|
||||||
await expect(this.deductible).toContainText(expDeductible);
|
await expect(this.deductible).toContainText(claimDetails.policyDeductible.toLocaleString());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: Validate change preferred shop and contact details flows
|
||||||
}
|
}
|
||||||
|
|
@ -4,13 +4,13 @@ import { VehicleDamage } from '@business-logic/types/Enums';
|
||||||
|
|
||||||
export class VehicleDamagePage extends BasePage {
|
export class VehicleDamagePage extends BasePage {
|
||||||
readonly page: Page;
|
readonly page: Page;
|
||||||
readonly windshieldChkBox: Locator;
|
readonly windshieldButton: Locator;
|
||||||
readonly crackButton: Locator;
|
readonly sideDoorButton: Locator;
|
||||||
readonly chipButton: Locator;
|
readonly replaceButton: Locator;
|
||||||
|
readonly repairButton: Locator;
|
||||||
readonly singleWindshieldButton: Locator;
|
readonly singleWindshieldButton: Locator;
|
||||||
readonly splitWindshieldDriverSideButton: Locator;
|
readonly splitWindshieldDriverSideButton: Locator;
|
||||||
readonly splitWindshieldPassengerSideButton: Locator;
|
readonly splitWindshieldPassengerSideButton: Locator;
|
||||||
readonly sideDoorButton: Locator;
|
|
||||||
readonly driverSideButton: Locator;
|
readonly driverSideButton: Locator;
|
||||||
readonly passengerSideButton: Locator;
|
readonly passengerSideButton: Locator;
|
||||||
readonly driverQuarterPanelChkBox: Locator;
|
readonly driverQuarterPanelChkBox: Locator;
|
||||||
|
|
@ -30,9 +30,11 @@ export class VehicleDamagePage extends BasePage {
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.windshieldChkBox = this.page.locator('[buttonlabel="Windshield"]');
|
this.windshieldButton = this.page.locator('[buttonlabel="Windshield"]');
|
||||||
this.crackButton = this.page.locator('[buttonlabel="Crack"]');
|
this.sideDoorButton = this.page.locator('[buttonlabel="Side door"]');
|
||||||
this.chipButton = this.page.locator('[buttonlabel="Chip(s)"]');
|
this.rearWindowChkBox = this.page.locator('[buttonlabel="Rear window"]');
|
||||||
|
this.replaceButton = this.page.locator('div.list-card-content:has-text("Replace")');
|
||||||
|
this.repairButton = this.page.locator('div.list-card-content:has-text("Repair")');
|
||||||
this.singleWindshieldButton = this.page.locator('[buttonlabel="Single windshield"]');
|
this.singleWindshieldButton = this.page.locator('[buttonlabel="Single windshield"]');
|
||||||
this.splitWindshieldDriverSideButton = this.page.locator('[buttonlabel="Split windshield, driver side"]');
|
this.splitWindshieldDriverSideButton = this.page.locator('[buttonlabel="Split windshield, driver side"]');
|
||||||
this.splitWindshieldPassengerSideButton = this.page.locator('[buttonlabel="Split windshield, passenger side"]');
|
this.splitWindshieldPassengerSideButton = this.page.locator('[buttonlabel="Split windshield, passenger side"]');
|
||||||
|
|
@ -55,17 +57,17 @@ export class VehicleDamagePage extends BasePage {
|
||||||
|
|
||||||
async checkSeparateApptsWarning() {
|
async checkSeparateApptsWarning() {
|
||||||
// Select conflict
|
// Select conflict
|
||||||
await this.windshieldChkBox.check();
|
await this.windshieldButton.check();
|
||||||
await this.chipButton.check();
|
await this.repairButton.check();
|
||||||
await this.rearWindowChkBox.check();
|
await this.rearWindowChkBox.check();
|
||||||
|
|
||||||
// Expect warning
|
// Expect warning
|
||||||
await expect.soft(this.separateApptsWarning).toBeAttached();
|
await expect.soft(this.separateApptsWarning).toBeAttached();
|
||||||
|
|
||||||
// Undo changes
|
// Undo changes
|
||||||
await this.crackButton.check();
|
await this.replaceButton.check();
|
||||||
await this.windshieldChkBox.uncheck();
|
await this.windshieldButton.uncheck();
|
||||||
await expect.soft(this.crackButton).not.toBeVisible();
|
await expect.soft(this.replaceButton).not.toBeVisible();
|
||||||
await this.rearWindowChkBox.uncheck();
|
await this.rearWindowChkBox.uncheck();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -73,33 +75,33 @@ export class VehicleDamagePage extends BasePage {
|
||||||
for (const damage of vehicleDamage) {
|
for (const damage of vehicleDamage) {
|
||||||
switch(damage) {
|
switch(damage) {
|
||||||
case VehicleDamage.WindshieldOneChip:
|
case VehicleDamage.WindshieldOneChip:
|
||||||
await this.windshieldChkBox.check();
|
await this.windshieldButton.check();
|
||||||
await this.selectChips('1');
|
await this.selectChips('1');
|
||||||
break;
|
break;
|
||||||
case VehicleDamage.WindshieldTwoChips:
|
case VehicleDamage.WindshieldTwoChips:
|
||||||
await this.windshieldChkBox.check();
|
await this.windshieldButton.check();
|
||||||
await this.selectChips('2');
|
await this.selectChips('2');
|
||||||
break;
|
break;
|
||||||
case VehicleDamage.WindshieldThreeChips:
|
case VehicleDamage.WindshieldThreeChips:
|
||||||
await this.windshieldChkBox.check();
|
await this.windshieldButton.check();
|
||||||
await this.selectChips('3');
|
await this.selectChips('3');
|
||||||
break;
|
break;
|
||||||
case VehicleDamage.WindshieldCrack:
|
case VehicleDamage.WindshieldCrack:
|
||||||
await this.windshieldChkBox.check();
|
await this.windshieldButton.check();
|
||||||
await this.selectCrack();
|
await this.selectCrack();
|
||||||
break;
|
break;
|
||||||
case VehicleDamage.WindshieldCrackSingleWindshield:
|
case VehicleDamage.WindshieldCrackSingleWindshield:
|
||||||
await this.windshieldChkBox.check();
|
await this.windshieldButton.check();
|
||||||
await this.selectCrack();
|
await this.selectCrack();
|
||||||
await this.singleWindshieldButton.check();
|
await this.singleWindshieldButton.check();
|
||||||
break;
|
break;
|
||||||
case VehicleDamage.WindshieldCrackDriverSide:
|
case VehicleDamage.WindshieldCrackDriverSide:
|
||||||
await this.windshieldChkBox.check();
|
await this.windshieldButton.check();
|
||||||
await this.selectCrack();
|
await this.selectCrack();
|
||||||
await this.splitWindshieldDriverSideButton.check();
|
await this.splitWindshieldDriverSideButton.check();
|
||||||
break;
|
break;
|
||||||
case VehicleDamage.WindshieldCrackPassengerSide:
|
case VehicleDamage.WindshieldCrackPassengerSide:
|
||||||
await this.windshieldChkBox.check();
|
await this.windshieldButton.check();
|
||||||
await this.selectCrack();
|
await this.selectCrack();
|
||||||
await this.splitWindshieldPassengerSideButton.check();
|
await this.splitWindshieldPassengerSideButton.check();
|
||||||
break;
|
break;
|
||||||
|
|
@ -156,12 +158,12 @@ export class VehicleDamagePage extends BasePage {
|
||||||
}
|
}
|
||||||
|
|
||||||
async selectCrack(){
|
async selectCrack(){
|
||||||
await this.crackButton.check();
|
await this.replaceButton.click();
|
||||||
}
|
}
|
||||||
|
|
||||||
async selectChips(numChips: string){
|
async selectChips(numChips: string){
|
||||||
const numChipsButton = this.page.getByText(numChips, {exact: true});
|
const numChipsButton = this.page.getByText(numChips, {exact: true});
|
||||||
await this.chipButton.check();
|
await this.repairButton.check();
|
||||||
await numChipsButton.check();
|
await numChipsButton.check();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -16,7 +16,7 @@ export class VehicleLookupLicensePage extends BasePage {
|
||||||
this.licensePlateNumTextBox = page.getByRole('textbox', { name: 'License plate number' });
|
this.licensePlateNumTextBox = page.getByRole('textbox', { name: 'License plate number' });
|
||||||
this.licensePlateStateDrpDwn = page.getByRole('combobox', { name: 'License plate state' });
|
this.licensePlateStateDrpDwn = page.getByRole('combobox', { name: 'License plate state' });
|
||||||
this.plateNoMatchError = page.getByText('Your license plate didn’t return a VIN match.Please re-enter the information');
|
this.plateNoMatchError = page.getByText('Your license plate didn’t return a VIN match.Please re-enter the information');
|
||||||
this.plateMismatchAlert = page.getByRole('alert').locator('div');
|
this.plateMismatchAlert = page.getByText('We found a windshield, but the VIN associated with the license plate you provided is for a');
|
||||||
}
|
}
|
||||||
|
|
||||||
async enterPlateDetails(vehicleDetails: IVehicleDetails, isVehicleLookupValidations = false) {
|
async enterPlateDetails(vehicleDetails: IVehicleDetails, isVehicleLookupValidations = false) {
|
||||||
|
|
@ -26,6 +26,7 @@ export class VehicleLookupLicensePage extends BasePage {
|
||||||
await this.continueButton.click({ timeout: 1000 });
|
await this.continueButton.click({ timeout: 1000 });
|
||||||
await expect(this.plateNoMatchError).toBeVisible();
|
await expect(this.plateNoMatchError).toBeVisible();
|
||||||
await this.licensePlateNumTextBox.fill(vehicleDetails.licensePlateNumber[1]);
|
await this.licensePlateNumTextBox.fill(vehicleDetails.licensePlateNumber[1]);
|
||||||
|
await this.licensePlateStateDrpDwn.selectOption(vehicleDetails.licensePlateState![1]);
|
||||||
await this.continueButton.click({ timeout: 1000 });
|
await this.continueButton.click({ timeout: 1000 });
|
||||||
await expect(this.plateMismatchAlert).toBeVisible();
|
await expect(this.plateMismatchAlert).toBeVisible();
|
||||||
await this.licensePlateNumTextBox.fill(vehicleDetails.licensePlateNumber[2]);
|
await this.licensePlateNumTextBox.fill(vehicleDetails.licensePlateNumber[2]);
|
||||||
|
|
|
||||||
|
|
@ -19,7 +19,7 @@ export class VehicleLookupPage extends BasePage {
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.vinLookupButton = page.getByLabel('Provide my VIN manually', { exact: true });
|
this.vinLookupButton = page.getByLabel('Provide my VIN', { exact: true });
|
||||||
this.addressLookupButton = page.getByLabel('Provide my home address', { exact: true });
|
this.addressLookupButton = page.getByLabel('Provide my home address', { exact: true });
|
||||||
this.licenseLookupButton = page.getByLabel('Provide my license plate #', { exact: true });
|
this.licenseLookupButton = page.getByLabel('Provide my license plate #', { exact: true });
|
||||||
this.vinLookupPage = new VinLookupPage(page);
|
this.vinLookupPage = new VinLookupPage(page);
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,6 @@
|
||||||
import { Page } from "@playwright/test";
|
import { expect, type Locator, type Page } from "@playwright/test";
|
||||||
import { PartQuestionsPage } from "./PartQuestionsPage";
|
import { PartQuestionsPage } from "./PartQuestionsPage";
|
||||||
|
import { IPartQuestion } from '@business-logic/types/CustomerDetails';
|
||||||
|
|
||||||
export default class VehiclePartQuestionsPage extends PartQuestionsPage{
|
export default class VehiclePartQuestionsPage extends PartQuestionsPage{
|
||||||
issPageValue = 'vehicle-parts';
|
issPageValue = 'vehicle-parts';
|
||||||
|
|
@ -7,4 +8,16 @@ export default class VehiclePartQuestionsPage extends PartQuestionsPage{
|
||||||
constructor(page: Page) {
|
constructor(page: Page) {
|
||||||
super(page);
|
super(page);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async selectPartQuestionResponses(partQuestions: IPartQuestion[]) {
|
||||||
|
for (const pq of partQuestions) {
|
||||||
|
const parentobject=this.page.locator(`fieldset[aria-labelledby="${pq.partQuestionType}"]`);
|
||||||
|
const partQuestionOptionButton = parentobject.locator(`[buttonlabel="${pq.optionToSelect}"]`);
|
||||||
|
await partQuestionOptionButton.nth(0).click();
|
||||||
|
if (pq.secondaryQuestionOptionToSelect != null) {
|
||||||
|
const secondaryQuestionButton = parentobject.getByText(`${pq.secondaryQuestionOptionToSelect}`);
|
||||||
|
await secondaryQuestionButton.nth(1).click();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -16,6 +16,7 @@ export class WelcomePage extends BasePage {
|
||||||
readonly city: Locator;
|
readonly city: Locator;
|
||||||
readonly state: Locator;
|
readonly state: Locator;
|
||||||
readonly cookieCloseButton: Locator;
|
readonly cookieCloseButton: Locator;
|
||||||
|
readonly GetStartedButton: Locator;
|
||||||
url = process.env['BASE_URL']! + '/?issPage=welcome-page';
|
url = process.env['BASE_URL']! + '/?issPage=welcome-page';
|
||||||
issPageValue = 'welcome-page';
|
issPageValue = 'welcome-page';
|
||||||
|
|
||||||
|
|
@ -24,13 +25,14 @@ export class WelcomePage extends BasePage {
|
||||||
this.page = page;
|
this.page = page;
|
||||||
this.policyNumber = page.getByRole('textbox', { name: 'Policy number' });
|
this.policyNumber = page.getByRole('textbox', { name: 'Policy number' });
|
||||||
this.policyZip = page.getByRole('textbox', { name: 'Policy ZIP' });
|
this.policyZip = page.getByRole('textbox', { name: 'Policy ZIP' });
|
||||||
this.damageDate = page.getByRole('textbox', { name: 'When did the damage occur?<' });
|
this.damageDate = page.locator('#dateOfLossField');
|
||||||
this.damageCause = page.locator('#damageCauseQuestionField');
|
this.damageCause = page.locator('#damageCauseQuestionField');
|
||||||
this.phoneNumber = page.getByRole('textbox', { name: 'Best number to reach you' });
|
this.phoneNumber = page.getByRole('textbox', { name: 'Best number to reach you' });
|
||||||
this.emailAddress = page.getByRole('textbox', { name: 'Email address' });
|
this.emailAddress = page.getByRole('textbox', { name: 'Email address' });
|
||||||
this.city = page.getByRole('textbox', { name: 'In which city did the damage' });
|
this.city = page.getByRole('textbox', { name: 'In which city did the damage' });
|
||||||
this.state = page.locator('select[name="\\38 fdf9dc2e13e430eb57529499dceb3eb"]');
|
this.state = page.locator('select[name="\\38 fdf9dc2e13e430eb57529499dceb3eb"]');
|
||||||
this.cookieCloseButton = page.getByRole('button', { name: 'Close' });
|
this.cookieCloseButton = page.getByRole('button', { name: 'Close' });
|
||||||
|
this.GetStartedButton = page.getByRole('button', { name: 'Get Started' });
|
||||||
}
|
}
|
||||||
|
|
||||||
async goto(clientTag: string) {
|
async goto(clientTag: string) {
|
||||||
|
|
@ -66,18 +68,17 @@ export class WelcomePage extends BasePage {
|
||||||
|
|
||||||
async populatePage(customerDetails: ICustomerDetails, claimDetails: IClaimDetails, isFillCityInfo: boolean) {
|
async populatePage(customerDetails: ICustomerDetails, claimDetails: IClaimDetails, isFillCityInfo: boolean) {
|
||||||
await this.policyNumber.fill(claimDetails.policyNumber);
|
await this.policyNumber.fill(claimDetails.policyNumber);
|
||||||
await this.policyZip.fill(customerDetails.address.postalCode);
|
await this.phoneNumber.fill(customerDetails.phoneNumber);
|
||||||
await this.damageDate.click();
|
await this.damageDate.click();
|
||||||
await this.damageDate.fill(claimDetails.damageDate);
|
await this.damageDate.fill(claimDetails.damageDate);
|
||||||
await this.damageCause.selectOption(claimDetails.damageCause);
|
await this.damageCause.selectOption(claimDetails.damageCause);
|
||||||
await this.damageCause.press('Tab');
|
await this.damageCause.press('Tab');
|
||||||
await this.phoneNumber.fill(customerDetails.phoneNumber);
|
await this.policyZip.fill(customerDetails.address.postalCode);
|
||||||
// Phone number fixed 12/5. Can't start with 1 or 0
|
|
||||||
await this.emailAddress.fill(customerDetails.email);
|
|
||||||
|
|
||||||
if (isFillCityInfo) {
|
if (isFillCityInfo) {
|
||||||
await this.city.fill(customerDetails.address.city);
|
|
||||||
await this.state.selectOption(customerDetails.address.state);
|
await this.state.selectOption(customerDetails.address.state);
|
||||||
|
await this.city.fill(customerDetails.address.city);
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -88,6 +88,7 @@ export default defineConfig({
|
||||||
// baseURL: 'http://127.0.0.1:3000',
|
// baseURL: 'http://127.0.0.1:3000',
|
||||||
|
|
||||||
/* Collect trace when retrying the failed test. See https://playwright.dev/docs/trace-viewer */
|
/* Collect trace when retrying the failed test. See https://playwright.dev/docs/trace-viewer */
|
||||||
|
baseURL: process.env.BASE_URL || 'https://selfservice.test.glassclaim.com',
|
||||||
trace: 'on-first-retry',
|
trace: 'on-first-retry',
|
||||||
headless: process.env.CI ? true : false,
|
headless: process.env.CI ? true : false,
|
||||||
screenshot: "only-on-failure",
|
screenshot: "only-on-failure",
|
||||||
|
|
|
||||||
|
|
@ -1,11 +1,12 @@
|
||||||
import TestCase from "@business-logic/types/TestCase";
|
import TestCase from "@business-logic/types/TestCase";
|
||||||
import { expect, Page } from "@playwright/test";
|
import { expect, Page } from "@playwright/test";
|
||||||
|
import { getDefaultTestData } from "safelite-playwright-core";
|
||||||
import { addSmokeTagToRandomTest, prepareTest, test, TestInfo } from "@business-logic/types/Test";
|
import { addSmokeTagToRandomTest, prepareTest, test, TestInfo } from "@business-logic/types/Test";
|
||||||
import { RuleEngine, ValidationOptions } from "@business-logic/types/RuleEngine";
|
import { RuleEngine, ValidationOptions } from "@business-logic/types/RuleEngine";
|
||||||
import { ICustomerDetails } from "@business-logic/types/CustomerDetails";
|
import { ICustomerDetails } from "@business-logic/types/CustomerDetails";
|
||||||
import essentialHpTestCases from "./0016_EssentialRepairInShop";
|
import essentialHpTestCases from "./0016_EssentialRepairInShop";
|
||||||
import essentialReplaceTestCases from "./0013_EssentialReplace";
|
import essentialReplaceTestCases from "./0013_EssentialReplace";
|
||||||
import { BailoutCode, VehicleDamage, VehicleLookupType } from "@business-logic/types/Enums";
|
import { BailoutCode, ServiceLocation, VehicleDamage, VehicleLookupType } from "@business-logic/types/Enums";
|
||||||
import essentialTpaNotEnabledTestCases from "./0003_EssentialTpaNotEnabledBailout";
|
import essentialTpaNotEnabledTestCases from "./0003_EssentialTpaNotEnabledBailout";
|
||||||
import essentialDoNotSeeShopTestCases from "./0011_EssentialDoNotSeeShopBailout";
|
import essentialDoNotSeeShopTestCases from "./0011_EssentialDoNotSeeShopBailout";
|
||||||
import essentialVehicleNotFoundTestCases from "./0010_EssentialVehicleNotFoundBailout";
|
import essentialVehicleNotFoundTestCases from "./0010_EssentialVehicleNotFoundBailout";
|
||||||
|
|
@ -58,7 +59,7 @@ import advancedScenario0025TestCases from "./advanced/0025a_VehicleByVINUnverifi
|
||||||
import advancedScenario0026aTestCases from "./advanced/0026a_NoDeductibleAdasBailout5";
|
import advancedScenario0026aTestCases from "./advanced/0026a_NoDeductibleAdasBailout5";
|
||||||
import advancedScenario0028aTestCases from "./advanced/0028a_ItacCancelMyClaim";
|
import advancedScenario0028aTestCases from "./advanced/0028a_ItacCancelMyClaim";
|
||||||
import advancedScenario0029aTestCases from "./advanced/0029a_HeavyVehicleBailout";
|
import advancedScenario0029aTestCases from "./advanced/0029a_HeavyVehicleBailout";
|
||||||
import advancedScenario0030aTestCases from "./advanced/0030a_PartsServiceBailout";
|
import advancedScenario0030aTestCases from "./advanced/0030a_APIErrorBailout";
|
||||||
import advancedScenario0031aTestCases from "./advanced/0031a_ReplaceServiceableBigTruck";
|
import advancedScenario0031aTestCases from "./advanced/0031a_ReplaceServiceableBigTruck";
|
||||||
import advancedScenario0032aTestCases from "./advanced/0032a_DeclineNonServiceableBigTruck";
|
import advancedScenario0032aTestCases from "./advanced/0032a_DeclineNonServiceableBigTruck";
|
||||||
|
|
||||||
|
|
@ -382,8 +383,8 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
// Destructure data for easy access
|
// Destructure data for easy access
|
||||||
const { customerDetails, claimDetails, vehicleDetails, vehicleDamage,
|
const { customerDetails, claimDetails, vehicleDetails, vehicleDamage,
|
||||||
appointmentDetails, isSafelite, endorsements,
|
appointmentDetails, isSafelite, endorsements,
|
||||||
partQuestions, paymentDetails, isNoComp, isItac, isRecalNotification,
|
partQuestions, paymentDetails, isNoComp, isItac, isRecalNotification, isUnverifiedPolicyAfterVehicleLookup,
|
||||||
isRecalWarning, servicePackage, hasStateLawPopup, otherVehiclesOnPolicy,
|
isRecalWarning, servicePackage, hasOemEndorsement, hasStateLawPopup, otherVehiclesOnPolicy,
|
||||||
isSeparateApptsWarning, vehiclePartQuestions, editVehicleDetails, isAddressLookupValidations,
|
isSeparateApptsWarning, vehiclePartQuestions, editVehicleDetails, isAddressLookupValidations,
|
||||||
hasMilitaryWarning, capabilityQuestions, isUseVehicleOnPolicy,
|
hasMilitaryWarning, capabilityQuestions, isUseVehicleOnPolicy,
|
||||||
isVehicleLookupValidations, isMoldingQuestion, isNonServiceable, isNonServiceableVin } = testCase.testData;
|
isVehicleLookupValidations, isMoldingQuestion, isNonServiceable, isNonServiceableVin } = testCase.testData;
|
||||||
|
|
@ -401,9 +402,9 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
vehiclePartQuestionsPage, capabilityQuestionsPage, moldingQuestionsPage, addressLookupPage } = testCase.pages;
|
vehiclePartQuestionsPage, capabilityQuestionsPage, moldingQuestionsPage, addressLookupPage } = testCase.pages;
|
||||||
|
|
||||||
// Destructure bailout flags
|
// Destructure bailout flags
|
||||||
const { isVehicleSelectBailout, isDoNotSeeMyShopBailout, isTpaNotEnabledBailout,
|
const { isVehicleSelectBailout, isTpaNotEnabledBailout,
|
||||||
isPartsServiceErrorBailout, isVehicleLookupBailout, isPriceServiceErrorBailout,
|
isAPIErrorBailout, isVehicleLookupBailout, isPriceServiceErrorBailout,
|
||||||
isRequestCallbackBailout } = testCase.testData.bailoutFlags || {};
|
isRequestCallbackBailout, isHeavyTruckVehicleBailout, isCoverageCancelledByUser } = testCase.testData.bailoutFlags || {};
|
||||||
|
|
||||||
const repairTypes: VehicleDamage[] = [
|
const repairTypes: VehicleDamage[] = [
|
||||||
VehicleDamage.WindshieldOneChip,
|
VehicleDamage.WindshieldOneChip,
|
||||||
|
|
@ -420,7 +421,7 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
|
|
||||||
await test.step('WelcomePage >> Populate Customer Details', async () => {
|
await test.step('WelcomePage >> Populate Customer Details', async () => {
|
||||||
await welcomePage.populatePage(customerDetails!, claimDetails!, await welcomePage.hasCityInfo());
|
await welcomePage.populatePage(customerDetails!, claimDetails!, await welcomePage.hasCityInfo());
|
||||||
await welcomePage.nextPage();
|
await welcomePage.GetStartedButton.click();
|
||||||
});
|
});
|
||||||
|
|
||||||
if (testCase.testData.isDuplicateClaim) {
|
if (testCase.testData.isDuplicateClaim) {
|
||||||
|
|
@ -445,26 +446,35 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (!(isUseVehicleOnPolicy ?? true)) {
|
if (!(isUseVehicleOnPolicy ?? true)) {
|
||||||
await policyVehiclesPage.selectVehicleNotListed();
|
await policyVehiclesPage.addAnotherVehicle();
|
||||||
await policyVehiclesPage.nextPage();
|
await policyVehiclesPage.nextPage();
|
||||||
await vehicleSelectionPage.selectVehicle(vehicleDetails!);
|
await vehicleSelectionPage.selectVehicle(vehicleDetails!);
|
||||||
await policyVehiclesPage.nextPage();
|
await policyVehiclesPage.nextPage();
|
||||||
|
|
||||||
|
await test.step('PolicyHolderDetailsPage >> Enter customer data', async () => {
|
||||||
|
await policyHolderDetailsPage.validateURL(policyHolderDetailsPage.issPageValue);
|
||||||
|
await policyHolderDetailsPage.fillCustomerDetails(customerDetails!);
|
||||||
|
await policyHolderDetailsPage.nextPage();
|
||||||
|
});
|
||||||
} else {
|
} else {
|
||||||
// Select vehicle
|
// Select vehicle
|
||||||
await policyVehiclesPage.selectVehicle(vehicleDetails!);
|
await policyVehiclesPage.selectVehicle(vehicleDetails!);
|
||||||
|
|
||||||
|
await policyVehiclesPage.nextPage();
|
||||||
|
await policyVehiclesPage.logReferralNumber();
|
||||||
|
|
||||||
|
if (isNonServiceable && isHeavyTruckVehicleBailout) {
|
||||||
|
await bailoutPage.validateURL(bailoutPage.issPageValue);
|
||||||
|
await bailoutPage.validateBailoutDetails(customerDetails!, BailoutCode.HeavyTruckVehicle);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (isNonServiceable) {
|
if (isNonServiceable) {
|
||||||
await policyVehiclesPage.assertNonServiceableAlertBehavior();
|
await policyVehiclesPage.assertNonServiceableAlertBehavior();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
await policyVehiclesPage.nextPage();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
if (isNonServiceable) {
|
if (hasEndorsements) {
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (hasEndorsements) {
|
|
||||||
await test.step('EndorsementsPage >> Select Endorsements', async () => {
|
await test.step('EndorsementsPage >> Select Endorsements', async () => {
|
||||||
await endorsementsPage.validateURL(endorsementsPage.issPageValue);
|
await endorsementsPage.validateURL(endorsementsPage.issPageValue);
|
||||||
await endorsementsPage.verifyEndorsements(endorsements);
|
await endorsementsPage.verifyEndorsements(endorsements);
|
||||||
|
|
@ -472,29 +482,22 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
await endorsementsPage.nextPage();
|
await endorsementsPage.nextPage();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
await test.step('PolicyHolderDetailsPage >> Enter customer data', async () => {
|
||||||
} else {
|
await policyHolderDetailsPage.validateURL(policyHolderDetailsPage.issPageValue);
|
||||||
await policyVehiclesPage.logReferralNumber();
|
await policyHolderDetailsPage.fillCustomerDetails(customerDetails!);
|
||||||
await test.step('PolicyHolderDetailsPage >> Enter customer data', async () => {
|
await policyHolderDetailsPage.nextPage();
|
||||||
await policyHolderDetailsPage.validateURL(policyHolderDetailsPage.issPageValue);
|
|
||||||
await policyHolderDetailsPage.fillCustomerDetails(customerDetails!);
|
|
||||||
await policyHolderDetailsPage.nextPage();
|
|
||||||
});
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
if (isNonServiceable) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (isVehicleLookupBailout) {
|
if (isVehicleLookupBailout) {
|
||||||
forceAPIError(page, '/vehicle/api/v1/vehicle/lookup')
|
forceAPIError(page, '/vehicle/api/v1/vehicle/lookup')
|
||||||
}
|
}
|
||||||
|
|
||||||
await test.step('VehicleDetailsPage >> Select Vehicle', async () => {
|
|
||||||
await vehicleSelectionPage.validateURL(vehicleSelectionPage.issPageValue);
|
|
||||||
await vehicleSelectionPage.selectVehicle(vehicleDetails!);
|
|
||||||
if (isNonServiceable) {
|
|
||||||
await vehicleSelectionPage.assertNonServiceableAlertBehavior();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
await vehicleSelectionPage.nextPage();
|
|
||||||
});
|
|
||||||
|
|
||||||
if (isNonServiceable) {
|
if (isNonServiceable) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
@ -508,20 +511,21 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (editVehicleDetails) {
|
// Essential flow when policy is not found
|
||||||
isPolicyFound = false; // Flow proceeds as unverified
|
if (isPolicyFound === false) {
|
||||||
testCase.testData.isPolicyFound = false;
|
testCase.testData.isPolicyFound = false;
|
||||||
await test.step('VehicleDamagePage >> Click Edit Vehicle', async () => {
|
|
||||||
await vehicleDamagePage.validateURL(vehicleDamagePage.issPageValue);
|
|
||||||
await vehicleDamagePage.editVehicleButton.click();
|
|
||||||
});
|
|
||||||
|
|
||||||
await test.step('VehicleDetailsPage >> Select edited vehicle', async () => {
|
await test.step('VehicleSelectionPage >> Select vehicle for essential flow', async () => {
|
||||||
await test.step('VehicleDetailsPage >> Select Vehicle', async () => {
|
|
||||||
await vehicleSelectionPage.validateURL(vehicleSelectionPage.issPageValue);
|
await vehicleSelectionPage.validateURL(vehicleSelectionPage.issPageValue);
|
||||||
await vehicleSelectionPage.selectVehicle(editVehicleDetails);
|
await vehicleSelectionPage.selectVehicle(vehicleDetails!);
|
||||||
await vehicleSelectionPage.nextPage();
|
await vehicleSelectionPage.nextPage();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
await test.step('PolicyHolderDetailsPage >> Enter customer data', async () => {
|
||||||
|
await policyHolderDetailsPage.validateURL(policyHolderDetailsPage.issPageValue);
|
||||||
|
await policyHolderDetailsPage.fillCustomerDetails(customerDetails!);
|
||||||
|
|
||||||
|
await policyHolderDetailsPage.nextPage();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -534,7 +538,7 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
await vehicleDamagePage.nextPage();
|
await vehicleDamagePage.nextPage();
|
||||||
});
|
});
|
||||||
|
|
||||||
if (isPartsServiceErrorBailout) {
|
if (isAPIErrorBailout) {
|
||||||
await test.step('VehicleLookupPage >> Select Lookup Type', async () => {
|
await test.step('VehicleLookupPage >> Select Lookup Type', async () => {
|
||||||
await vehicleLookupPage.validateURL(vehicleLookupPage.issPageValue);
|
await vehicleLookupPage.validateURL(vehicleLookupPage.issPageValue);
|
||||||
await vehicleLookupPage.vehicleLookup(vehicleDetails!);
|
await vehicleLookupPage.vehicleLookup(vehicleDetails!);
|
||||||
|
|
@ -545,9 +549,9 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
forceAPIError(page, '/parts/api/v1/parts')
|
forceAPIError(page, '/parts/api/v1/parts')
|
||||||
await vinLookupPage.nextPage();
|
await vinLookupPage.nextPage();
|
||||||
});
|
});
|
||||||
await test.step('BailoutPage >> Parts Service Error Bailout', async () => {
|
await test.step('BailoutPage >> API error occurred bailout', async () => {
|
||||||
await bailoutPage.validateURL(bailoutPage.issPageValue);
|
await bailoutPage.validateURL(bailoutPage.issPageValue);
|
||||||
await bailoutPage.validateBailoutDetails(customerDetails!, BailoutCode.PartsServiceError);
|
await bailoutPage.validateBailoutDetails(customerDetails!, BailoutCode.ApiError);
|
||||||
return;
|
return;
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
|
|
@ -584,10 +588,14 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
await test.step('Address Lookup validations >> Vehicle Lookup by address: ' + customerDetails!.address.street, async () => {
|
await test.step('Address Lookup validations >> Vehicle Lookup by address: ' + customerDetails!.address.street, async () => {
|
||||||
if (Array.isArray(vehicleDetails?.address)) {
|
if (Array.isArray(vehicleDetails?.address)) {
|
||||||
await addressLookupPage.validateURL(addressLookupPage.issPageValue);
|
await addressLookupPage.validateURL(addressLookupPage.issPageValue);
|
||||||
await addressLookupPage.validateAddressLookupAlerts(vehicleDetails?.address);
|
await addressLookupPage.validateAddressLookupAlerts(vehicleDetails?.address!);
|
||||||
await addressLookupPage.nextPage();
|
await addressLookupPage.nextPage();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
await test.step('Address Vehicles >> Next page', async () => {
|
||||||
|
await addressLookupPage.nextPage();
|
||||||
|
});
|
||||||
} else {
|
} else {
|
||||||
await test.step('VehicleLookupAddressPage >> Lookup by address: ' + customerDetails!.address.street, async () => {
|
await test.step('VehicleLookupAddressPage >> Lookup by address: ' + customerDetails!.address.street, async () => {
|
||||||
await vehicleLookupAddressPage.validateURL(vehicleLookupAddressPage.issPageValue);
|
await vehicleLookupAddressPage.validateURL(vehicleLookupAddressPage.issPageValue);
|
||||||
|
|
@ -627,6 +635,7 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isMoldingQuestion) {
|
if (isMoldingQuestion) {
|
||||||
await test.step('Molding Questions Page >> Select Yes', async () => {
|
await test.step('Molding Questions Page >> Select Yes', async () => {
|
||||||
await moldingQuestionsPage.validateURL(moldingQuestionsPage.issPageValue);
|
await moldingQuestionsPage.validateURL(moldingQuestionsPage.issPageValue);
|
||||||
|
|
@ -637,6 +646,7 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
await moldingQuestionsPage.nextPage();
|
await moldingQuestionsPage.nextPage();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
if (capabilityQuestions && capabilityQuestions.length > 0) {
|
if (capabilityQuestions && capabilityQuestions.length > 0) {
|
||||||
await capabilityQuestionsPage.validateURL(capabilityQuestionsPage.issPageValue);
|
await capabilityQuestionsPage.validateURL(capabilityQuestionsPage.issPageValue);
|
||||||
await capabilityQuestionsPage.validatePartQuestions(capabilityQuestions);
|
await capabilityQuestionsPage.validatePartQuestions(capabilityQuestions);
|
||||||
|
|
@ -645,6 +655,7 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (partQuestions && partQuestions.length > 0) {
|
if (partQuestions && partQuestions.length > 0) {
|
||||||
|
let partQuestionsPage = testCase.pages.partQuestionsPage;
|
||||||
await partQuestionsPage.validateURL(partQuestionsPage.issPageValue);
|
await partQuestionsPage.validateURL(partQuestionsPage.issPageValue);
|
||||||
await partQuestionsPage.validatePartQuestions(partQuestions);
|
await partQuestionsPage.validatePartQuestions(partQuestions);
|
||||||
await partQuestionsPage.selectPartQuestionResponses(partQuestions);
|
await partQuestionsPage.selectPartQuestionResponses(partQuestions);
|
||||||
|
|
@ -653,60 +664,96 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
|
|
||||||
if (vehiclePartQuestions && vehiclePartQuestions.length > 0) {
|
if (vehiclePartQuestions && vehiclePartQuestions.length > 0) {
|
||||||
await vehiclePartQuestionsPage.validateURL(vehiclePartQuestionsPage.issPageValue);
|
await vehiclePartQuestionsPage.validateURL(vehiclePartQuestionsPage.issPageValue);
|
||||||
await vehiclePartQuestionsPage.validatePartQuestions(vehiclePartQuestions);
|
|
||||||
await vehiclePartQuestionsPage.selectPartQuestionResponses(vehiclePartQuestions);
|
await vehiclePartQuestionsPage.selectPartQuestionResponses(vehiclePartQuestions);
|
||||||
await vehiclePartQuestionsPage.nextPage();
|
await vehiclePartQuestionsPage.nextPage();
|
||||||
}
|
}
|
||||||
if (isRequestCallbackBailout) {
|
|
||||||
await test.step('CoverageStatementPage >> Cancel My claim', async () => {
|
if (isCoverageCancelledByUser) {
|
||||||
|
await test.step('CoverageStatementPage >> Cancel my claim', async () => {
|
||||||
await coverageStatementPage.validateURL(coverageStatementPage.issPageValue);
|
await coverageStatementPage.validateURL(coverageStatementPage.issPageValue);
|
||||||
await coverageStatementPage.cancelMyClaim();
|
await coverageStatementPage.cancelMyClaim();
|
||||||
});
|
});
|
||||||
|
|
||||||
await test.step('BailoutPage >> Request Callback Bailout', async () => {
|
await test.step('BailoutPage >> User canceled claim on ITAC/No Comp coverage statement', async () => {
|
||||||
await bailoutPage.validateURL(bailoutPage.issPageValue);
|
await bailoutPage.validateURL(bailoutPage.issPageValue);
|
||||||
await bailoutPage.validateBailoutDetails(customerDetails!, BailoutCode.RequestCallback);
|
await bailoutPage.validateBailoutDetails(customerDetails!, BailoutCode.CoverageCancelledByUser);
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
await test.step('CoverageStatementPage >> Next page', async () => {
|
await test.step('CoverageStatementPage >> Next page', async () => {
|
||||||
await coverageStatementPage.validateURL(coverageStatementPage.issPageValue);
|
await coverageStatementPage.validateURL(coverageStatementPage.issPageValue);
|
||||||
// Confirm no coverage
|
|
||||||
if (isPolicyFound && (isItac || isNoComp)) {
|
if (hasOemEndorsement) {
|
||||||
await coverageStatementPage.continueToScheduleButton.click();
|
await coverageStatementPage.validateOEMBullet();
|
||||||
|
}
|
||||||
|
// For essential/unverified flows
|
||||||
|
if (!isPolicyFound) {
|
||||||
|
await coverageStatementPage.handleUnverifiedFlow(claimDetails!);
|
||||||
}
|
}
|
||||||
|
|
||||||
await coverageStatementPage.nextPage();
|
// For No Comp flows
|
||||||
|
if (isPolicyFound && isNoComp === true) {
|
||||||
|
await coverageStatementPage.handleNoCompFlow();
|
||||||
|
}
|
||||||
|
|
||||||
|
// For ITAC flows
|
||||||
|
if (isPolicyFound && isItac === true) {
|
||||||
|
await coverageStatementPage.handleITACFlow();
|
||||||
|
}
|
||||||
|
|
||||||
|
// For replacements with deductible
|
||||||
|
if (isPolicyFound && claimDetails?.policyDeductible! > 0 && claimDetails?.policyDeductible !== 9999 && testCase.testData.isUnverifiedPolicyAfterVehicleLookup !== true) {
|
||||||
|
await coverageStatementPage.handleReplacementWithDeductibleFlow(claimDetails!);
|
||||||
|
}
|
||||||
|
|
||||||
|
// For replacements or repairs with 0 deductible
|
||||||
|
if (isPolicyFound && claimDetails?.policyDeductible === 0) {
|
||||||
|
await coverageStatementPage.handleReplacementOrRepairWithNoDeductibleFlow(claimDetails!, VehicleDamage!);
|
||||||
|
}
|
||||||
|
|
||||||
|
// For unverified policy after vehicle lookup
|
||||||
|
if (isPolicyFound && testCase.testData.isUnverifiedPolicyAfterVehicleLookup === true) {
|
||||||
|
await coverageStatementPage.handleUnverifiedPolicyAfterVehicleLookupFlow();
|
||||||
|
}
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
if (hasStateLawPopup) {
|
if (hasStateLawPopup) {
|
||||||
await test.step('ProviderPreferencePage >> Dismiss state law popup', async () => {
|
await test.step('ProviderPreferencePage >> Dismiss state law popup', async () => {
|
||||||
await providerPreferencePage.validateURL(providerPreferencePage.issPageValue);
|
await providerPreferencePage.validateURL(providerPreferencePage.issPageValue);
|
||||||
await providerPreferencePage.validateStateLawModalIsVisible();
|
if (vehicleDamage!.includes(VehicleDamage.WindshieldCrack)) {
|
||||||
await providerPreferencePage.gotItButton.click();
|
await providerPreferencePage.stateLawModalOkayButton.click();
|
||||||
});
|
} else {
|
||||||
|
await providerPreferencePage.stateLawModalOkayButton.click();
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!isPolicyFound || !(isItac || isNoComp)) {
|
if (!isPolicyFound || !(isItac || isNoComp) && !isUnverifiedPolicyAfterVehicleLookup) {
|
||||||
await test.step('ProviderPreferencePage >> Select Provider ' + isSafelite ? "Safelite" : "Other shops(Non-Safelite)", async () => {
|
await test.step('ProviderPreferencePage >> Select Provider ' + isSafelite ? "Safelite" : "Other shops(Non-Safelite)", async () => {
|
||||||
await providerPreferencePage.validateURL(providerPreferencePage.issPageValue);
|
await providerPreferencePage.validateURL(providerPreferencePage.issPageValue);
|
||||||
await providerPreferencePage.selectProvider(isSafelite);
|
await providerPreferencePage.selectProvider(isSafelite);
|
||||||
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
// validations for Recal warning mesage
|
if (isSafelite && isUnverifiedPolicyAfterVehicleLookup) {
|
||||||
if (isRecalWarning) {
|
await test.step('ProviderPreferencePage >> Select Provider ' + isSafelite ? "Safelite" : "Other shops(Non-Safelite)", async () => {
|
||||||
await serviceLocationPage.validateURL(serviceLocationPage.issPageValue);
|
await providerPreferencePage.validateURL(providerPreferencePage.issPageValue);
|
||||||
await serviceLocationPage.validateRecalWarning();
|
await providerPreferencePage.selectProvider(isSafelite);
|
||||||
|
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
// if isRecalNotifidation flag true additional step to acknowledge Recal notification.
|
if (!isSafelite && isUnverifiedPolicyAfterVehicleLookup) {
|
||||||
if (isRecalNotification) {
|
await test.step('ProviderPreferencePage >> Schedule TPA without Adas', async () => {
|
||||||
await providerPreferencePage.validateURL(providerPreferencePage.issPageValue);
|
await providerPreferencePage.validateURL(providerPreferencePage.issPageValue);
|
||||||
await providerPreferencePage.acknowledgeRecalNotificaiton();
|
await providerPreferencePage.scheduleTPAWithoutAdas();
|
||||||
|
});
|
||||||
}
|
}
|
||||||
// If No-Comp or ITAC, ProviderPreferencePage does not appear
|
// If No-Comp or ITAC, ProviderPreferencePage does not appear
|
||||||
if (!isPolicyFound || !(isItac || isNoComp)) {
|
if (!isPolicyFound || !(isItac || isNoComp) || isUnverifiedPolicyAfterVehicleLookup) {
|
||||||
|
|
||||||
|
|
||||||
if (!isSafelite) {
|
if (!isSafelite) {
|
||||||
|
|
@ -728,16 +775,6 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isDoNotSeeMyShopBailout) {
|
|
||||||
await test.step('TpaSearchPage >> Select "Do Not See My Shop"', async () => {
|
|
||||||
await tpaSearchPage.validateURL(tpaSearchPage.issPageValue);
|
|
||||||
await tpaSearchPage.selectDoNotSeeMyShop();
|
|
||||||
});
|
|
||||||
await bailoutPage.validateURL(bailoutPage.issPageValue);
|
|
||||||
await bailoutPage.validateBailoutDetails(customerDetails!, BailoutCode.DoNotSeeMyShop);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
await test.step('TpaSearchPage >> TPA Search', async () => {
|
await test.step('TpaSearchPage >> TPA Search', async () => {
|
||||||
await tpaSearchPage.validateURL(tpaSearchPage.issPageValue);
|
await tpaSearchPage.validateURL(tpaSearchPage.issPageValue);
|
||||||
await tpaSearchPage.selectFirstLocation();
|
await tpaSearchPage.selectFirstLocation();
|
||||||
|
|
@ -745,9 +782,12 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
});
|
});
|
||||||
|
|
||||||
await test.step('TpaSubmitPage >> TPA Submit', async () => {
|
await test.step('TpaSubmitPage >> TPA Submit', async () => {
|
||||||
// TODO: Validations
|
|
||||||
await tpaSubmitPage.validateURL(tpaSubmitPage.issPageValue);
|
await tpaSubmitPage.validateURL(tpaSubmitPage.issPageValue);
|
||||||
|
if (!isUnverifiedPolicyAfterVehicleLookup) {
|
||||||
|
await tpaSubmitPage.validateDeductible(claimDetails!);
|
||||||
|
} else {
|
||||||
await tpaSubmitPage.nextPage();
|
await tpaSubmitPage.nextPage();
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
await test.step('TpaConfirmationPage >> TPA Confirmation', async () => {
|
await test.step('TpaConfirmationPage >> TPA Confirmation', async () => {
|
||||||
|
|
@ -756,43 +796,41 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
return;
|
return;
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
}
|
}}
|
||||||
}
|
|
||||||
|
|
||||||
await test.step('ServiceLocationPage >> Select service location', async () => {
|
|
||||||
await serviceLocationPage.validateURL(serviceLocationPage.issPageValue);
|
|
||||||
await serviceLocationPage.selectLocation(appointmentDetails!);
|
|
||||||
if (hasMilitaryWarning) {
|
|
||||||
await expect.soft(serviceLocationPage.militaryWarningMessage).toBeVisible();
|
|
||||||
}
|
|
||||||
await serviceLocationPage.nextPage();
|
|
||||||
});
|
|
||||||
|
|
||||||
await test.step('SchedulePage >> Select day and time', async () => {
|
await test.step('SchedulePage >> Select day and time', async () => {
|
||||||
await schedulePage.validateURL(schedulePage.issPageValue);
|
await schedulePage.validateURL(schedulePage.issPageValue);
|
||||||
customerDetails!.apptDate = await schedulePage.scheduleFirstAppointment(appointmentDetails!.serviceLocation);
|
|
||||||
});
|
|
||||||
|
|
||||||
await test.step('ContactDetailsPage >> Validate contact details', async () => {
|
if (appointmentDetails?.serviceLocation === ServiceLocation.Mobile) {
|
||||||
const expectedContactDetails: Partial<ICustomerDetails> = {
|
await schedulePage.scheduleMobile(appointmentDetails);
|
||||||
firstName: customerDetails!.firstName,
|
|
||||||
lastName: customerDetails!.lastName,
|
|
||||||
email: customerDetails!.email,
|
|
||||||
phoneNumber: customerDetails!.phoneNumber
|
|
||||||
};
|
|
||||||
await contactDetailsPage.validateURL(contactDetailsPage.issPageValue);
|
|
||||||
const actualContactDetails = await contactDetailsPage.getContactDetails();
|
|
||||||
expect.soft(actualContactDetails).toEqual(expectedContactDetails);
|
|
||||||
|
|
||||||
await contactDetailsPage.fillNotes(customerDetails!.notes);
|
|
||||||
|
|
||||||
if (isPriceServiceErrorBailout) {
|
|
||||||
forceAPIError(page, '/price/api/v1/price/combined-quote');
|
|
||||||
}
|
}
|
||||||
|
|
||||||
await contactDetailsPage.nextPage();
|
if (appointmentDetails?.serviceLocation === ServiceLocation.InShop || appointmentDetails?.serviceLocation === ServiceLocation.DropOff) {
|
||||||
|
await schedulePage.scheduleInShop(appointmentDetails);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
|
await test.step('ServicePackagesPage >> Choose service package', async () => {
|
||||||
|
await servicePackagesPage.validateURL(servicePackagesPage.issPageValue);
|
||||||
|
await servicePackagesPage.selectServicePackage(servicePackage!);
|
||||||
|
});
|
||||||
|
|
||||||
|
if (appointmentDetails?.serviceLocation === ServiceLocation.Mobile) {
|
||||||
|
await test.step('ContactDetailsPage >> Validate contact details', async () => {
|
||||||
|
await contactDetailsPage.validateURL(contactDetailsPage.issPageValue);
|
||||||
|
|
||||||
|
|
||||||
|
await contactDetailsPage.fillContactDetails(customerDetails!);
|
||||||
|
if (appointmentDetails?.alternateMobileCity) {
|
||||||
|
await contactDetailsPage.fillAlternateMobileStreetAndCity(appointmentDetails?.alternateMobileStreetAddress!, appointmentDetails?.alternateMobileCity!);
|
||||||
|
}
|
||||||
|
|
||||||
|
await contactDetailsPage.nextPage();
|
||||||
|
});
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
if (isPriceServiceErrorBailout) {
|
if (isPriceServiceErrorBailout) {
|
||||||
await test.step('BailoutPage >> Price Service Error Bailout', async () => {
|
await test.step('BailoutPage >> Price Service Error Bailout', async () => {
|
||||||
await bailoutPage.validateURL(bailoutPage.issPageValue);
|
await bailoutPage.validateURL(bailoutPage.issPageValue);
|
||||||
|
|
@ -801,22 +839,29 @@ async function runWorkflow(page: Page, testCase: TestCase) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
await test.step('ServicePackagesPage >> Choose service package', async () => {
|
|
||||||
await servicePackagesPage.validateURL(servicePackagesPage.issPageValue);
|
|
||||||
customerDetails!.packagePrice = await servicePackagesPage.selectServicePackage(servicePackage!);
|
|
||||||
await servicePackagesPage.nextPage();
|
|
||||||
});
|
|
||||||
|
|
||||||
if (isPolicyFound && (isUseVehicleOnPolicy ?? true) && claimDetails!.policyDeductible > 0) {
|
if (isPolicyFound && (isUseVehicleOnPolicy ?? true) && claimDetails!.policyDeductible > 0) {
|
||||||
await test.step('PaymentMethodPage >> Execute Payment', async () => {
|
await test.step('PaymentMethodPage >> Execute Payment', async () => {
|
||||||
await paymentMethodPage.validateURL(paymentMethodPage.issPageValue);
|
await paymentMethodPage.validateURL(paymentMethodPage.issPageValue);
|
||||||
await paymentMethodPage.executePayment(paymentDetails!);
|
await paymentMethodPage.executePayment(paymentDetails!, claimDetails!, servicePackage!);
|
||||||
await paymentMethodPage.nextPage();
|
await paymentMethodPage.nextPage();
|
||||||
|
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
await test.step('PaymentMethodPage >> Skip to Order Confirmation', async () => {
|
await test.step('PaymentMethodPage >> Skip to Order Confirmation', async () => {
|
||||||
await paymentMethodPage.validateURL(paymentMethodPage.issPageValue);
|
await paymentMethodPage.validateURL(paymentMethodPage.issPageValue);
|
||||||
await paymentMethodPage.nextPage();
|
|
||||||
|
if (isPolicyFound && (isUseVehicleOnPolicy ?? true) && claimDetails!.policyDeductible === 0) {
|
||||||
|
await paymentMethodPage.submitOrderWithoutPIA();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!isPolicyFound) {
|
||||||
|
await paymentMethodPage.submitOrderWithoutPIA();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isPolicyFound && testCase.testData.isUnverifiedPolicyAfterVehicleLookup === true) {
|
||||||
|
await paymentMethodPage.submitOrderWithoutPIA();
|
||||||
|
}
|
||||||
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -21,10 +21,10 @@ const essentialReplaceStaticAdasData: Partial<ITestData> = {
|
||||||
phoneNumber: faker.helpers.fromRegExp(/[2-9][0-9][0-9]-[0-9][0-9][0-9]-[0-9][0-9][0-9][0-9]/),
|
phoneNumber: faker.helpers.fromRegExp(/[2-9][0-9][0-9]-[0-9][0-9][0-9]-[0-9][0-9][0-9][0-9]/),
|
||||||
notes: 'Automated Test',
|
notes: 'Automated Test',
|
||||||
address: {
|
address: {
|
||||||
street: faker.location.streetAddress(),
|
street: "123 Test Road",
|
||||||
city: 'Knoxville',
|
city: 'Columbus',
|
||||||
state: 'Tennessee',
|
state: 'OHIO',
|
||||||
postalCode: '37996',
|
postalCode: '43085',
|
||||||
country: 'United States'
|
country: 'United States'
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
|
||||||
|
|
@ -23,9 +23,9 @@ const essentialRepairInShopAcuraData: Partial<ITestData> = {
|
||||||
phoneNumber: faker.helpers.fromRegExp(/[2-9][0-9][0-9]-[0-9][0-9][0-9]-[0-9][0-9][0-9][0-9]/),
|
phoneNumber: faker.helpers.fromRegExp(/[2-9][0-9][0-9]-[0-9][0-9][0-9]-[0-9][0-9][0-9][0-9]/),
|
||||||
notes: 'Automated Test',
|
notes: 'Automated Test',
|
||||||
address: {
|
address: {
|
||||||
street: faker.location.streetAddress(),
|
street: '200 W. Oak Street',
|
||||||
city: 'Fort Collins',
|
city: 'Fort Collins',
|
||||||
state: 'Colorado',
|
state: 'COLORADO',
|
||||||
postalCode: '80526',
|
postalCode: '80526',
|
||||||
country: 'United States'
|
country: 'United States'
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -28,10 +28,10 @@ const essentialTpaEnabledData: Partial<ITestData> = {
|
||||||
notes: 'Automated Test',
|
notes: 'Automated Test',
|
||||||
address: {
|
address: {
|
||||||
// street: faker.location.streetAddress(),
|
// street: faker.location.streetAddress(),
|
||||||
street: '134 Woodlands Place',
|
street: '1343 Cameron Ave',
|
||||||
city: 'Dublin',
|
city: 'Lewis Center',
|
||||||
state: 'Florida',
|
state: 'OH',
|
||||||
postalCode: '32040',
|
postalCode: '43035',
|
||||||
country: 'United States'
|
country: 'United States'
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
@ -42,10 +42,10 @@ const essentialTpaEnabledData: Partial<ITestData> = {
|
||||||
damageCause: DamageType.Other
|
damageCause: DamageType.Other
|
||||||
},
|
},
|
||||||
vehicleDetails: {
|
vehicleDetails: {
|
||||||
year: '2022',
|
year: '2015',
|
||||||
make: 'Honda',
|
make: 'Honda',
|
||||||
model: 'Civic',
|
model: 'Accord',
|
||||||
style: '4 door hatchback'
|
style: '4 door sedan'
|
||||||
},
|
},
|
||||||
vehicleDamage: [
|
vehicleDamage: [
|
||||||
VehicleDamage.WindshieldThreeChips,
|
VehicleDamage.WindshieldThreeChips,
|
||||||
|
|
|
||||||
|
|
@ -16,7 +16,6 @@ const essentialDoNotSeeShopData: Partial<ITestData> = {
|
||||||
partQuestions: undefined,
|
partQuestions: undefined,
|
||||||
isSafelite: false,
|
isSafelite: false,
|
||||||
bailoutFlags: {
|
bailoutFlags: {
|
||||||
isDoNotSeeMyShopBailout: true
|
|
||||||
},
|
},
|
||||||
servicePackage: faker.helpers.enumValue(ServicePackage),
|
servicePackage: faker.helpers.enumValue(ServicePackage),
|
||||||
customerDetails: {
|
customerDetails: {
|
||||||
|
|
|
||||||
|
|
@ -23,7 +23,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0001a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0001a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0001a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0001a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0001Data: Partial<ITestData> = {
|
const advancedScenario0001Data: Partial<ITestData> = {
|
||||||
|
|
@ -31,7 +31,6 @@ const advancedScenario0001Data: Partial<ITestData> = {
|
||||||
isDuplicateClaim: false,
|
isDuplicateClaim: false,
|
||||||
isPolicyFound: true,
|
isPolicyFound: true,
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
hasStateLawPopup: true,
|
|
||||||
endorsements: undefined,
|
endorsements: undefined,
|
||||||
vehiclePartQuestions: [
|
vehiclePartQuestions: [
|
||||||
|
|
||||||
|
|
@ -60,7 +59,7 @@ const advancedScenario0001Data: Partial<ITestData> = {
|
||||||
shopAddress: undefined,
|
shopAddress: undefined,
|
||||||
appointmentDate: nextWeekday
|
appointmentDate: nextWeekday
|
||||||
},
|
},
|
||||||
paymentDetails: ClientData.getDefaultPaypalDetails()//ClientData.getDefaultCreditCardDetails()
|
paymentDetails: ClientData.getDefaultCreditCardDetails()
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: Add validation for deductible/covered amount
|
// TODO: Add validation for deductible/covered amount
|
||||||
|
|
|
||||||
|
|
@ -29,7 +29,7 @@ if ((process.env.ENABLE_MOCK_TESTING ?? 'false') === 'true') {
|
||||||
customerDetails.lastName = 'Cormier';
|
customerDetails.lastName = 'Cormier';
|
||||||
customerDetails.address.street = '69825 W Pine Street';
|
customerDetails.address.street = '69825 W Pine Street';
|
||||||
} else {
|
} else {
|
||||||
policyNumber = `~AutomatedScenario0002a${faker.string.uuid().substring(0, 6)}`;
|
policyNumber = `~AutomatedScenario0002a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`;
|
||||||
};
|
};
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0002a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0002a', customerDetails, policyNumber);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0003a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0003a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`;
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0003a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0003a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0003Data: Partial<ITestData> = {
|
const advancedScenario0003Data: Partial<ITestData> = {
|
||||||
|
|
@ -33,6 +33,7 @@ const advancedScenario0003Data: Partial<ITestData> = {
|
||||||
isDuplicateClaim: false,
|
isDuplicateClaim: false,
|
||||||
isPolicyFound: true,
|
isPolicyFound: true,
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
|
hasOemEndorsement: true,
|
||||||
hasStateLawPopup: false,
|
hasStateLawPopup: false,
|
||||||
endorsements: undefined,
|
endorsements: undefined,
|
||||||
vehiclePartQuestions: [
|
vehiclePartQuestions: [
|
||||||
|
|
@ -44,7 +45,7 @@ const advancedScenario0003Data: Partial<ITestData> = {
|
||||||
{
|
{
|
||||||
partQuestionType: PartQuestionType.PassengerRearColor,
|
partQuestionType: PartQuestionType.PassengerRearColor,
|
||||||
isOnPage: true,
|
isOnPage: true,
|
||||||
optionToSelect: 'Green Tint'
|
optionToSelect: 'Solar, Passenger side, Rear'
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
isSafelite: true,
|
isSafelite: true,
|
||||||
|
|
@ -53,7 +54,7 @@ const advancedScenario0003Data: Partial<ITestData> = {
|
||||||
claimDetails: {
|
claimDetails: {
|
||||||
policyNumber: policyNumber,
|
policyNumber: policyNumber,
|
||||||
policyDeductible: 50,
|
policyDeductible: 50,
|
||||||
damageDate: '2016-01-02',
|
damageDate: '2026-01-02',
|
||||||
damageCause: faker.helpers.enumValue(DamageType)
|
damageCause: faker.helpers.enumValue(DamageType)
|
||||||
},
|
},
|
||||||
policySoap: policySoap,
|
policySoap: policySoap,
|
||||||
|
|
|
||||||
|
|
@ -23,7 +23,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0004a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0004a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0004a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0004a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0004aData: Partial<ITestData> = {
|
const advancedScenario0004aData: Partial<ITestData> = {
|
||||||
|
|
@ -33,8 +33,7 @@ const advancedScenario0004aData: Partial<ITestData> = {
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
hasStateLawPopup: false,
|
hasStateLawPopup: false,
|
||||||
endorsements: undefined,
|
endorsements: undefined,
|
||||||
vehiclePartQuestions: [
|
partQuestions: [],
|
||||||
],
|
|
||||||
isSafelite: true,
|
isSafelite: true,
|
||||||
servicePackage: faker.helpers.enumValue(ServicePackage),
|
servicePackage: faker.helpers.enumValue(ServicePackage),
|
||||||
customerDetails: customerDetails,
|
customerDetails: customerDetails,
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0005a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0005a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0005a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0005a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0005Data: Partial<ITestData> = {
|
const advancedScenario0005Data: Partial<ITestData> = {
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0006a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0006a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0006a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0006a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0006Data: Partial<ITestData> = {
|
const advancedScenario0006Data: Partial<ITestData> = {
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0007a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0007a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0007a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0007a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0007Data: Partial<ITestData> = {
|
const advancedScenario0007Data: Partial<ITestData> = {
|
||||||
|
|
|
||||||
|
|
@ -12,7 +12,7 @@ const nextWeekday = getNextWeekday();
|
||||||
const customerAddress: IAddress = {
|
const customerAddress: IAddress = {
|
||||||
street: faker.location.streetAddress(),
|
street: faker.location.streetAddress(),
|
||||||
city: 'Hamden',
|
city: 'Hamden',
|
||||||
state: 'CT',
|
state: 'CONNECTICUT',
|
||||||
postalCode: '06517',
|
postalCode: '06517',
|
||||||
country: 'United States'
|
country: 'United States'
|
||||||
}
|
}
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0008a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0008a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0008a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0008a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0008Data: Partial<ITestData> = {
|
const advancedScenario0008Data: Partial<ITestData> = {
|
||||||
|
|
@ -33,7 +33,7 @@ const advancedScenario0008Data: Partial<ITestData> = {
|
||||||
isDuplicateClaim: false,
|
isDuplicateClaim: false,
|
||||||
isPolicyFound: true,
|
isPolicyFound: true,
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
hasStateLawPopup: true,
|
hasStateLawPopup: false,
|
||||||
endorsements: undefined,
|
endorsements: undefined,
|
||||||
vehiclePartQuestions: [
|
vehiclePartQuestions: [
|
||||||
// {
|
// {
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0009a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0009a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0009a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0009a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0009Data: Partial<ITestData> = {
|
const advancedScenario0009Data: Partial<ITestData> = {
|
||||||
|
|
@ -38,7 +38,7 @@ const advancedScenario0009Data: Partial<ITestData> = {
|
||||||
{
|
{
|
||||||
endorsementType: EndorsementType.Educator,
|
endorsementType: EndorsementType.Educator,
|
||||||
isOnPolicy: true,
|
isOnPolicy: true,
|
||||||
isClickYes: false
|
isClickYes: true
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
vehiclePartQuestions: [
|
vehiclePartQuestions: [
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0010a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0010a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0010a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0010a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0010Data: Partial<ITestData> = {
|
const advancedScenario0010Data: Partial<ITestData> = {
|
||||||
|
|
@ -92,7 +92,7 @@ for (const client of advancedClients) {
|
||||||
const data = {...advancedScenario0010Data};
|
const data = {...advancedScenario0010Data};
|
||||||
data.clientTag = client.clientTag;
|
data.clientTag = client.clientTag;
|
||||||
const tc = new TestCase({
|
const tc = new TestCase({
|
||||||
name: `0010a Advanced Repair No Deductible FL Rear Client: "${client.accountName}"`,
|
name: `0010a Advanced Replace No Deductible FL Rear Client: "${client.accountName}"`,
|
||||||
tags: [`@${client.clientTag}`, `@${client.accountName}`, '@Advanced'],
|
tags: [`@${client.clientTag}`, `@${client.accountName}`, '@Advanced'],
|
||||||
testData: data
|
testData: data
|
||||||
}, undefined, '0010a');
|
}, undefined, '0010a');
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0011a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0011a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0011a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0011a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0011Data: Partial<ITestData> = {
|
const advancedScenario0011Data: Partial<ITestData> = {
|
||||||
|
|
@ -33,13 +33,13 @@ const advancedScenario0011Data: Partial<ITestData> = {
|
||||||
isDuplicateClaim: false,
|
isDuplicateClaim: false,
|
||||||
isPolicyFound: true,
|
isPolicyFound: true,
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
isItac: true,
|
isItac: false,
|
||||||
hasStateLawPopup: false,
|
hasStateLawPopup: false,
|
||||||
endorsements: [
|
endorsements: [
|
||||||
{
|
{
|
||||||
endorsementType: EndorsementType.Educator,
|
endorsementType: EndorsementType.Educator,
|
||||||
isOnPolicy: true,
|
isOnPolicy: true,
|
||||||
isClickYes: false
|
isClickYes: true
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
partQuestions: undefined,
|
partQuestions: undefined,
|
||||||
|
|
@ -48,7 +48,7 @@ const advancedScenario0011Data: Partial<ITestData> = {
|
||||||
customerDetails: customerDetails,
|
customerDetails: customerDetails,
|
||||||
claimDetails: {
|
claimDetails: {
|
||||||
policyNumber: policyNumber,
|
policyNumber: policyNumber,
|
||||||
policyDeductible: 500,
|
policyDeductible: 0,
|
||||||
damageDate: '2023-03-01',
|
damageDate: '2023-03-01',
|
||||||
damageCause: faker.helpers.enumValue(DamageType)
|
damageCause: faker.helpers.enumValue(DamageType)
|
||||||
},
|
},
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0012a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0012a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0012a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0012a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0012Data: Partial<ITestData> = {
|
const advancedScenario0012Data: Partial<ITestData> = {
|
||||||
|
|
@ -48,7 +48,7 @@ const advancedScenario0012Data: Partial<ITestData> = {
|
||||||
customerDetails: customerDetails,
|
customerDetails: customerDetails,
|
||||||
claimDetails: {
|
claimDetails: {
|
||||||
policyNumber: policyNumber,
|
policyNumber: policyNumber,
|
||||||
policyDeductible: 500,
|
policyDeductible: 9999,
|
||||||
damageDate: '2023-09-01',
|
damageDate: '2023-09-01',
|
||||||
damageCause: faker.helpers.enumValue(DamageType)
|
damageCause: faker.helpers.enumValue(DamageType)
|
||||||
},
|
},
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import ClientData from "@business-logic/data/ClientData";
|
import ClientData from "@business-logic/data/ClientData";
|
||||||
import TestCase from "@business-logic/types/TestCase";
|
import TestCase from "@business-logic/types/TestCase";
|
||||||
import { DamageType, EndorsementType, ServiceLocation, ServicePackage, VehicleDamage } from "@business-logic/types/Enums";
|
import { DamageType, EndorsementType, PaymentType, ServiceLocation, ServicePackage, VehicleDamage } from "@business-logic/types/Enums";
|
||||||
import { ITestData } from "@business-logic/types/ITestData"
|
import { ITestData } from "@business-logic/types/ITestData"
|
||||||
import { faker } from "@faker-js/faker";
|
import { faker } from "@faker-js/faker";
|
||||||
import { getNextWeekday } from "@impl/utils/DateUtils";
|
import { getNextWeekday } from "@impl/utils/DateUtils";
|
||||||
|
|
@ -11,9 +11,9 @@ import { IAddress } from "@business-logic/types/IAddress";
|
||||||
const nextWeekday = getNextWeekday();
|
const nextWeekday = getNextWeekday();
|
||||||
const customerAddress: IAddress = {
|
const customerAddress: IAddress = {
|
||||||
street: faker.location.streetAddress(),
|
street: faker.location.streetAddress(),
|
||||||
city: 'Birmingham',
|
city: 'Worthington',
|
||||||
state: 'AL',
|
state: 'OH',
|
||||||
postalCode: '35118',
|
postalCode: '43085',
|
||||||
country: 'United States'
|
country: 'United States'
|
||||||
}
|
}
|
||||||
const customerDetails: ICustomerDetails = {
|
const customerDetails: ICustomerDetails = {
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0013a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0013a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0013a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0013a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0013Data: Partial<ITestData> = {
|
const advancedScenario0013Data: Partial<ITestData> = {
|
||||||
|
|
@ -33,13 +33,13 @@ const advancedScenario0013Data: Partial<ITestData> = {
|
||||||
isDuplicateClaim: false,
|
isDuplicateClaim: false,
|
||||||
isPolicyFound: true,
|
isPolicyFound: true,
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
isItac: true,
|
isItac: false,
|
||||||
hasStateLawPopup: false,
|
hasStateLawPopup: false,
|
||||||
endorsements: [
|
endorsements: [
|
||||||
{
|
{
|
||||||
endorsementType: EndorsementType.Educator,
|
endorsementType: EndorsementType.Educator,
|
||||||
isOnPolicy: true,
|
isOnPolicy: true,
|
||||||
isClickYes: false
|
isClickYes: true
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
vehiclePartQuestions: [
|
vehiclePartQuestions: [
|
||||||
|
|
@ -49,7 +49,7 @@ const advancedScenario0013Data: Partial<ITestData> = {
|
||||||
customerDetails: customerDetails,
|
customerDetails: customerDetails,
|
||||||
claimDetails: {
|
claimDetails: {
|
||||||
policyNumber: policyNumber,
|
policyNumber: policyNumber,
|
||||||
policyDeductible: 9999,
|
policyDeductible: 0,
|
||||||
damageDate: '2023-08-01',
|
damageDate: '2023-08-01',
|
||||||
damageCause: faker.helpers.enumValue(DamageType)
|
damageCause: faker.helpers.enumValue(DamageType)
|
||||||
},
|
},
|
||||||
|
|
@ -68,7 +68,9 @@ const advancedScenario0013Data: Partial<ITestData> = {
|
||||||
serviceAddress: customerAddress,
|
serviceAddress: customerAddress,
|
||||||
appointmentDate: nextWeekday
|
appointmentDate: nextWeekday
|
||||||
},
|
},
|
||||||
paymentDetails: ClientData.getDefaultCreditCardDetails()
|
paymentDetails: {
|
||||||
|
paymentType: PaymentType.PayAtService
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -80,7 +82,7 @@ for (const client of advancedClients) {
|
||||||
const data = { ...advancedScenario0013Data };
|
const data = { ...advancedScenario0013Data };
|
||||||
data.clientTag = client.clientTag;
|
data.clientTag = client.clientTag;
|
||||||
const tc = new TestCase({
|
const tc = new TestCase({
|
||||||
name: `0013a Advanced ITAC Mobile Client: "${client.accountName}"`,
|
name: `0013a Advanced $0 Deductible with Vaps Mobile Client: "${client.accountName}"`,
|
||||||
tags: [`@${client.clientTag}`, `@${client.accountName}`, '@Advanced'],
|
tags: [`@${client.clientTag}`, `@${client.accountName}`, '@Advanced'],
|
||||||
testData: data
|
testData: data
|
||||||
}, undefined, '0013a');
|
}, undefined, '0013a');
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0014a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0014a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0014a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0014a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0014Data: Partial<ITestData> = {
|
const advancedScenario0014Data: Partial<ITestData> = {
|
||||||
|
|
@ -33,13 +33,13 @@ const advancedScenario0014Data: Partial<ITestData> = {
|
||||||
isDuplicateClaim: false,
|
isDuplicateClaim: false,
|
||||||
isPolicyFound: true,
|
isPolicyFound: true,
|
||||||
isNoComp: true,
|
isNoComp: true,
|
||||||
isRecalWarning: true,
|
isRecalWarning: false,
|
||||||
hasStateLawPopup: false,
|
hasStateLawPopup: false,
|
||||||
endorsements: [
|
endorsements: [
|
||||||
{
|
{
|
||||||
endorsementType: EndorsementType.Educator,
|
endorsementType: EndorsementType.Educator,
|
||||||
isOnPolicy: true,
|
isOnPolicy: true,
|
||||||
isClickYes: true
|
isClickYes: false
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
partQuestions: undefined,
|
partQuestions: undefined,
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0015a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0015a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0015a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0015a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0015Data: Partial<ITestData> = {
|
const advancedScenario0015Data: Partial<ITestData> = {
|
||||||
|
|
@ -46,16 +46,16 @@ const advancedScenario0015Data: Partial<ITestData> = {
|
||||||
{
|
{
|
||||||
partQuestionType: PartQuestionType.WindshieldColor,
|
partQuestionType: PartQuestionType.WindshieldColor,
|
||||||
isOnPage: true,
|
isOnPage: true,
|
||||||
optionToSelect: 'Green Tint, Blue Shade'
|
optionToSelect: 'Heated glass, Heated glass Wiper Park'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
partQuestionType: PartQuestionType.DriverFrontColor,
|
partQuestionType: PartQuestionType.DriverFrontColor,
|
||||||
isOnPage: true,
|
isOnPage: true,
|
||||||
optionToSelect: 'Green Tint'
|
optionToSelect: 'Driver side, Front'
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
isSafelite: true,
|
isSafelite: true,
|
||||||
servicePackage: faker.helpers.enumValue(ServicePackage),
|
servicePackage: ServicePackage.Premium,
|
||||||
customerDetails: customerDetails,
|
customerDetails: customerDetails,
|
||||||
claimDetails: {
|
claimDetails: {
|
||||||
policyNumber: policyNumber,
|
policyNumber: policyNumber,
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0016a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0016a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0016a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0016a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0016Data: Partial<ITestData> = {
|
const advancedScenario0016Data: Partial<ITestData> = {
|
||||||
|
|
@ -39,38 +39,37 @@ const advancedScenario0016Data: Partial<ITestData> = {
|
||||||
{
|
{
|
||||||
partQuestionType: PartQuestionType.WindshieldColor,
|
partQuestionType: PartQuestionType.WindshieldColor,
|
||||||
isOnPage: true,
|
isOnPage: true,
|
||||||
optionToSelect: 'Green Tint'
|
optionToSelect: 'Solar, Third Visor Frit, soundproofing, Infrared Interlayer'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
partQuestionType: PartQuestionType.DriverFrontColor,
|
partQuestionType: PartQuestionType.DriverFrontColor,
|
||||||
isOnPage: true,
|
isOnPage: true,
|
||||||
optionToSelect: 'Green Tint'
|
optionToSelect: 'Solar, Driver side, Front'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
partQuestionType: PartQuestionType.DriverRearColor,
|
partQuestionType: PartQuestionType.DriverRearColor,
|
||||||
isOnPage: true,
|
isOnPage: true,
|
||||||
optionToSelect: 'Green Tint'
|
optionToSelect: 'Solar, Driver side, Rear'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
partQuestionType: PartQuestionType.DriverVentColor,
|
partQuestionType: PartQuestionType.DriverVentColor,
|
||||||
isOnPage: true,
|
isOnPage: true,
|
||||||
optionToSelect: 'Green Tint',
|
optionToSelect: 'Solar, Driver side, Rear'
|
||||||
secondaryQuestionOptionToSelect: 'solar, driver side, rear'
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
partQuestionType: PartQuestionType.PassengerFrontColor,
|
partQuestionType: PartQuestionType.PassengerFrontColor,
|
||||||
isOnPage: true,
|
isOnPage: true,
|
||||||
optionToSelect: 'Green Tint'
|
optionToSelect: 'Solar, Passenger side, Front'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
partQuestionType: PartQuestionType.PassengerRearColor,
|
partQuestionType: PartQuestionType.PassengerRearColor,
|
||||||
isOnPage: true,
|
isOnPage: true,
|
||||||
optionToSelect: 'Green Tint'
|
optionToSelect: 'Solar, Passenger side, Rear'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
partQuestionType: PartQuestionType.RearWindowColor,
|
partQuestionType: PartQuestionType.RearWindowColor,
|
||||||
isOnPage: true,
|
isOnPage: true,
|
||||||
optionToSelect: 'Green Tint'
|
optionToSelect: 'Heated glass, Solar'
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
isSafelite: true,
|
isSafelite: true,
|
||||||
|
|
@ -100,8 +99,8 @@ const advancedScenario0016Data: Partial<ITestData> = {
|
||||||
// VehicleDamage.PassengerVentGlass // TODO: Verify if this is intentionally not in UI
|
// VehicleDamage.PassengerVentGlass // TODO: Verify if this is intentionally not in UI
|
||||||
],
|
],
|
||||||
appointmentDetails: {
|
appointmentDetails: {
|
||||||
serviceLocation: ServiceLocation.Mobile,
|
serviceLocation: ServiceLocation.InShop,
|
||||||
serviceAddress: customerAddress,
|
serviceAddress: undefined,
|
||||||
appointmentDate: nextWeekday
|
appointmentDate: nextWeekday
|
||||||
},
|
},
|
||||||
paymentDetails: ClientData.getDefaultPaypalDetails()
|
paymentDetails: ClientData.getDefaultPaypalDetails()
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0017a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0017a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0017a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0017a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0017Data: Partial<ITestData> = {
|
const advancedScenario0017Data: Partial<ITestData> = {
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0018a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0018a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0018a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0018a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0018Data: Partial<ITestData> = {
|
const advancedScenario0018Data: Partial<ITestData> = {
|
||||||
|
|
|
||||||
|
|
@ -31,7 +31,7 @@ const vehicleDetails: IVehicleDetails = {
|
||||||
style: '4 door sedan'
|
style: '4 door sedan'
|
||||||
};
|
};
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0019a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0019a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0019a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0019a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0019Data: Partial<ITestData> = {
|
const advancedScenario0019Data: Partial<ITestData> = {
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0020a${faker.string.uuid().substring(0,6)}`;
|
const policyNumber = `~AutomatedScenario0020a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0020a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0020a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0020Data: Partial<ITestData> = {
|
const advancedScenario0020Data: Partial<ITestData> = {
|
||||||
|
|
@ -60,12 +60,14 @@ const advancedScenario0020Data: Partial<ITestData> = {
|
||||||
serviceLocation: ServiceLocation.Mobile,
|
serviceLocation: ServiceLocation.Mobile,
|
||||||
serviceAddress: {
|
serviceAddress: {
|
||||||
street: faker.location.streetAddress(),
|
street: faker.location.streetAddress(),
|
||||||
city: 'Goose Creek',
|
city: 'Worthington',
|
||||||
state: 'SC',
|
state: 'OH',
|
||||||
postalCode: '29445',
|
postalCode: '43085',
|
||||||
country: 'US'
|
country: 'US'
|
||||||
},
|
},
|
||||||
alternateServiceZip: '29445',
|
alternateServiceZip: '43085',
|
||||||
|
alternateMobileCity: 'Worthington',
|
||||||
|
alternateMobileStreetAddress: '177 Franklin Ave',
|
||||||
appointmentDate: nextWeekday
|
appointmentDate: nextWeekday
|
||||||
},
|
},
|
||||||
paymentDetails: {
|
paymentDetails: {
|
||||||
|
|
|
||||||
|
|
@ -23,13 +23,14 @@ const customerDetails: ICustomerDetails = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0021a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0021a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0021a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0021a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0021Data: Partial<ITestData> = {
|
const advancedScenario0021Data: Partial<ITestData> = {
|
||||||
clientTag: '',
|
clientTag: '',
|
||||||
isDuplicateClaim: false,
|
isDuplicateClaim: false,
|
||||||
isPolicyFound: true,
|
isPolicyFound: true,
|
||||||
|
isUnverifiedPolicyAfterVehicleLookup: true,
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
hasStateLawPopup: true,
|
hasStateLawPopup: true,
|
||||||
endorsements: undefined,
|
endorsements: undefined,
|
||||||
|
|
@ -54,8 +55,8 @@ const advancedScenario0021Data: Partial<ITestData> = {
|
||||||
model: 'RX 300',
|
model: 'RX 300',
|
||||||
style: undefined,
|
style: undefined,
|
||||||
vehicleLookupType: VehicleLookupType.LicensePlateNumber,
|
vehicleLookupType: VehicleLookupType.LicensePlateNumber,
|
||||||
licensePlateNumber: ['NoPlate753', 'BQ40903','1111'],
|
licensePlateNumber: ['NoPlate753', 'GAH2307','1111'],
|
||||||
licensePlateState: ['Illinois','Illinois','California'],
|
licensePlateState: ['Illinois','Ohio','California'],
|
||||||
},
|
},
|
||||||
vehicleDamage: [
|
vehicleDamage: [
|
||||||
VehicleDamage.WindshieldCrack,
|
VehicleDamage.WindshieldCrack,
|
||||||
|
|
|
||||||
|
|
@ -23,13 +23,14 @@ const customerDetails: ICustomerDetails = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0022a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0022a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0022a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0022a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0022Data: Partial<ITestData> = {
|
const advancedScenario0022Data: Partial<ITestData> = {
|
||||||
clientTag: '',
|
clientTag: '',
|
||||||
isDuplicateClaim: false,
|
isDuplicateClaim: false,
|
||||||
isPolicyFound: true,
|
isPolicyFound: true,
|
||||||
|
isUnverifiedPolicyAfterVehicleLookup: true,
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
hasStateLawPopup: true,
|
hasStateLawPopup: true,
|
||||||
endorsements: undefined,
|
endorsements: undefined,
|
||||||
|
|
|
||||||
|
|
@ -23,13 +23,14 @@ const customerDetails: ICustomerDetails = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0023a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0023a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0023a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0023a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0023Data: Partial<ITestData> = {
|
const advancedScenario0023Data: Partial<ITestData> = {
|
||||||
clientTag: '',
|
clientTag: '',
|
||||||
isDuplicateClaim: false,
|
isDuplicateClaim: false,
|
||||||
isPolicyFound: true,
|
isPolicyFound: true,
|
||||||
|
isUnverifiedPolicyAfterVehicleLookup: true,
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
hasStateLawPopup: true,
|
hasStateLawPopup: true,
|
||||||
endorsements: undefined,
|
endorsements: undefined,
|
||||||
|
|
|
||||||
|
|
@ -23,7 +23,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0024a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0024a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0024a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0024a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0024Data: Partial<ITestData> = {
|
const advancedScenario0024Data: Partial<ITestData> = {
|
||||||
|
|
@ -50,14 +50,14 @@ const advancedScenario0024Data: Partial<ITestData> = {
|
||||||
policySoap: policySoap,
|
policySoap: policySoap,
|
||||||
vehicleDetails: {
|
vehicleDetails: {
|
||||||
year: '2015',
|
year: '2015',
|
||||||
make: 'Ford',
|
make: 'Audi',
|
||||||
model: 'F Series F150',
|
model: 'A7',
|
||||||
style: '2 door super cab',
|
style: '4 door hatchback',
|
||||||
vehicleLookupType: VehicleLookupType.Address,
|
vehicleLookupType: VehicleLookupType.Address,
|
||||||
address: [
|
address: [
|
||||||
{ street: '9 Test Street', city: 'Columbus', state: 'OH', postalCode: '43220', lastName: 'Test' },
|
{ street: '9 Test Street', city: 'Columbus', state: 'OH', postalCode: '43220', lastName: 'Test' },
|
||||||
{ street: '8621 GREENLEAF AVE', city: 'Whittier', state: 'California', postalCode: '90602', lastName: 'Johnson' },
|
{ street: '8621 GREENLEAF AVE', city: 'Whittier', state: 'California', postalCode: '90602', lastName: 'Johnson' },
|
||||||
{ street: '10212 JEWEL CT', city: 'Conroe', state: 'Texas', postalCode: '77385', lastName: 'Reed' }
|
{ street: '6531 CANYON RANCH', city: 'Frisco', state: 'Texas', postalCode: '75036', lastName: 'TRAINOR' }
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
vehicleDamage: [
|
vehicleDamage: [
|
||||||
|
|
|
||||||
|
|
@ -15,7 +15,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
phoneNumber: '614-531-0031',
|
phoneNumber: '614-531-0031',
|
||||||
notes: 'Automated Test',
|
notes: 'Automated Test',
|
||||||
address: {
|
address: {
|
||||||
street: faker.location.streetAddress(),
|
street: '5273 Berrywood Dr',
|
||||||
city: 'Columbus',
|
city: 'Columbus',
|
||||||
state: 'OH',
|
state: 'OH',
|
||||||
postalCode: '43220',
|
postalCode: '43220',
|
||||||
|
|
@ -23,7 +23,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0025a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0025a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0025a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0025a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0025Data: Partial<ITestData> = {
|
const advancedScenario0025Data: Partial<ITestData> = {
|
||||||
|
|
|
||||||
|
|
@ -23,7 +23,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0026a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0026a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0026a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0026a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0026aData: Partial<ITestData> = {
|
const advancedScenario0026aData: Partial<ITestData> = {
|
||||||
|
|
@ -35,7 +35,6 @@ const advancedScenario0026aData: Partial<ITestData> = {
|
||||||
isRecalNotification: true,
|
isRecalNotification: true,
|
||||||
endorsements: undefined,
|
endorsements: undefined,
|
||||||
bailoutFlags: {
|
bailoutFlags: {
|
||||||
isDoNotSeeMyShopBailout: true
|
|
||||||
},
|
},
|
||||||
vehiclePartQuestions: [
|
vehiclePartQuestions: [
|
||||||
],
|
],
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0028a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0028a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0028a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0028a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0028aData: Partial<ITestData> = {
|
const advancedScenario0028aData: Partial<ITestData> = {
|
||||||
|
|
@ -36,7 +36,7 @@ const advancedScenario0028aData: Partial<ITestData> = {
|
||||||
isItac: true,
|
isItac: true,
|
||||||
hasStateLawPopup: false,
|
hasStateLawPopup: false,
|
||||||
bailoutFlags: {
|
bailoutFlags: {
|
||||||
isRequestCallbackBailout: true,
|
isCoverageCancelledByUser: true,
|
||||||
},
|
},
|
||||||
isVehicleSelectBailout: false,
|
isVehicleSelectBailout: false,
|
||||||
endorsements: [
|
endorsements: [
|
||||||
|
|
|
||||||
|
|
@ -23,21 +23,27 @@ const customerDetails: ICustomerDetails = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0029a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0029a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0029a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0029a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0029Data: Partial<ITestData> = {
|
const advancedScenario0029Data: Partial<ITestData> = {
|
||||||
clientTag: '',
|
clientTag: '',
|
||||||
isDuplicateClaim: false,
|
isDuplicateClaim: false,
|
||||||
isPolicyFound: true,
|
isPolicyFound: true,
|
||||||
|
isUnverifiedPolicyAfterVehicleLookup: true,
|
||||||
|
hasStateLawPopup: true,
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
endorsements: undefined,
|
endorsements: undefined,
|
||||||
|
vehiclePartQuestions: [
|
||||||
|
{
|
||||||
|
partQuestionType: PartQuestionType.WindshieldColor,
|
||||||
|
isOnPage: true,
|
||||||
|
optionToSelect: 'Heated glass, Encap, Asymmetrically Strengthen'
|
||||||
|
},
|
||||||
|
],
|
||||||
isUseVehicleOnPolicy: false,
|
isUseVehicleOnPolicy: false,
|
||||||
servicePackage: faker.helpers.enumValue(ServicePackage),
|
servicePackage: faker.helpers.enumValue(ServicePackage),
|
||||||
customerDetails: customerDetails,
|
customerDetails: customerDetails,
|
||||||
bailoutFlags: {
|
|
||||||
isHeavyTruckVehicleBailout: true,
|
|
||||||
},
|
|
||||||
claimDetails: {
|
claimDetails: {
|
||||||
policyNumber: policyNumber,
|
policyNumber: policyNumber,
|
||||||
policyDeductible: 500,
|
policyDeductible: 500,
|
||||||
|
|
@ -50,7 +56,7 @@ const advancedScenario0029Data: Partial<ITestData> = {
|
||||||
make: 'Freightliner',
|
make: 'Freightliner',
|
||||||
model: '114sd',
|
model: '114sd',
|
||||||
vehicleLookupType: VehicleLookupType.Vin,
|
vehicleLookupType: VehicleLookupType.Vin,
|
||||||
vin: '1FUJG3DV5HHJH2985',
|
vin: '1FVMG3DV5HHJA1388',
|
||||||
},
|
},
|
||||||
vehicleDamage: [
|
vehicleDamage: [
|
||||||
VehicleDamage.WindshieldCrack,
|
VehicleDamage.WindshieldCrack,
|
||||||
|
|
|
||||||
|
|
@ -10,10 +10,10 @@ import { IAddress } from "@business-logic/types/IAddress";
|
||||||
|
|
||||||
const nextWeekday = getNextWeekday();
|
const nextWeekday = getNextWeekday();
|
||||||
const customerAddress: IAddress = {
|
const customerAddress: IAddress = {
|
||||||
street: faker.location.streetAddress(),
|
street: '474 1st St',
|
||||||
city: 'Birmingham',
|
city: 'Lindsay',
|
||||||
state: 'AL',
|
state: 'CA',
|
||||||
postalCode: '35118',
|
postalCode: '93247',
|
||||||
country: 'United States'
|
country: 'United States'
|
||||||
}
|
}
|
||||||
const customerDetails: ICustomerDetails = {
|
const customerDetails: ICustomerDetails = {
|
||||||
|
|
@ -25,7 +25,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
address: customerAddress
|
address: customerAddress
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0030a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0030a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0030a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0030a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0030aData: Partial<ITestData> = {
|
const advancedScenario0030aData: Partial<ITestData> = {
|
||||||
|
|
@ -36,7 +36,7 @@ const advancedScenario0030aData: Partial<ITestData> = {
|
||||||
isItac: false,
|
isItac: false,
|
||||||
hasStateLawPopup: false,
|
hasStateLawPopup: false,
|
||||||
bailoutFlags: {
|
bailoutFlags: {
|
||||||
isPartsServiceErrorBailout: true,
|
isAPIErrorBailout: true,
|
||||||
},
|
},
|
||||||
|
|
||||||
vehiclePartQuestions: [
|
vehiclePartQuestions: [
|
||||||
|
|
@ -79,7 +79,7 @@ for (const client of advancedClients) {
|
||||||
const data = { ...advancedScenario0030aData };
|
const data = { ...advancedScenario0030aData };
|
||||||
data.clientTag = client.clientTag;
|
data.clientTag = client.clientTag;
|
||||||
const tc = new TestCase({
|
const tc = new TestCase({
|
||||||
name: `0030a Advanced ITAC Cancel My Claim: "${client.accountName}"`,
|
name: `0030a Advanced API Error Bailout: "${client.accountName}"`,
|
||||||
tags: [`@${client.clientTag}`, `@${client.accountName}`, '@Advanced', '@INSR-2057'],
|
tags: [`@${client.clientTag}`, `@${client.accountName}`, '@Advanced', '@INSR-2057'],
|
||||||
testData: data
|
testData: data
|
||||||
}, undefined, '0030a');
|
}, undefined, '0030a');
|
||||||
|
|
@ -23,7 +23,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0031a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0031a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0031a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0031a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0031Data: Partial<ITestData> = {
|
const advancedScenario0031Data: Partial<ITestData> = {
|
||||||
|
|
@ -33,19 +33,11 @@ const advancedScenario0031Data: Partial<ITestData> = {
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
hasStateLawPopup: false,
|
hasStateLawPopup: false,
|
||||||
endorsements: undefined,
|
endorsements: undefined,
|
||||||
partQuestions: [
|
|
||||||
{
|
|
||||||
partQuestionType: PartQuestionType.LaneKeepAssist,
|
|
||||||
isOnPage: true,
|
|
||||||
optionToSelect: 'Yes',
|
|
||||||
}
|
|
||||||
],
|
|
||||||
vehiclePartQuestions: [
|
vehiclePartQuestions: [
|
||||||
{
|
{
|
||||||
partQuestionType: PartQuestionType.WindshieldColor,
|
partQuestionType: PartQuestionType.WindshieldColor,
|
||||||
isOnPage: true,
|
isOnPage: true,
|
||||||
optionToSelect: 'Green Tint',
|
optionToSelect: 'One-Piece, With Lane Departure Warning System',
|
||||||
secondaryQuestionOptionToSelect: 'one-piece, w/lane departure warning system',
|
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
isSafelite: true,
|
isSafelite: true,
|
||||||
|
|
|
||||||
|
|
@ -23,7 +23,7 @@ const customerDetails: ICustomerDetails = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const policyNumber = `~AutomatedScenario0032a${faker.string.uuid().substring(0, 6)}`;
|
const policyNumber = `~AutomatedScenario0032a${crypto.randomUUID().replace(/-/g, '').slice(0, 16).toUpperCase()}`; // Ensure unique policy number for each test run since same key in request can cause 500 error
|
||||||
const policySoap = MockPolicyData.getPolicySoapByScenario('0032a', customerDetails, policyNumber);
|
const policySoap = MockPolicyData.getPolicySoapByScenario('0032a', customerDetails, policyNumber);
|
||||||
|
|
||||||
const advancedScenario0032Data: Partial<ITestData> = {
|
const advancedScenario0032Data: Partial<ITestData> = {
|
||||||
|
|
@ -33,6 +33,9 @@ const advancedScenario0032Data: Partial<ITestData> = {
|
||||||
isNoComp: false,
|
isNoComp: false,
|
||||||
hasStateLawPopup: false,
|
hasStateLawPopup: false,
|
||||||
endorsements: undefined,
|
endorsements: undefined,
|
||||||
|
bailoutFlags: {
|
||||||
|
isHeavyTruckVehicleBailout: true,
|
||||||
|
},
|
||||||
vehiclePartQuestions: [
|
vehiclePartQuestions: [
|
||||||
|
|
||||||
],
|
],
|
||||||
|
|
|
||||||
|
|
@ -17,7 +17,6 @@
|
||||||
"coverage/api/v1/coverage/register-claim": "0002a_Advanced_Replace_Deductible_Client/coverage/api/v1/coverage/register-claim.json",
|
"coverage/api/v1/coverage/register-claim": "0002a_Advanced_Replace_Deductible_Client/coverage/api/v1/coverage/register-claim.json",
|
||||||
"price/api/v1/price/order-items-with-itac-pricing": "0002a_Advanced_Replace_Deductible_Client/price/api/v1/price/order-items-with-itac-pricing.json",
|
"price/api/v1/price/order-items-with-itac-pricing": "0002a_Advanced_Replace_Deductible_Client/price/api/v1/price/order-items-with-itac-pricing.json",
|
||||||
"location/api/v1/location/providers/75023/Replace/100/550036/true/CR00056707/DW01571GTNNOEM": "0002a_Advanced_Replace_Deductible_Client/location/api/v1/location/providers/75023/Replace/100/550036/true/CR00056707/DW01571GTNNOEM.json",
|
"location/api/v1/location/providers/75023/Replace/100/550036/true/CR00056707/DW01571GTNNOEM": "0002a_Advanced_Replace_Deductible_Client/location/api/v1/location/providers/75023/Replace/100/550036/true/CR00056707/DW01571GTNNOEM.json",
|
||||||
"schedule/api/v1/schedule/shop-time-slots": "0002a_Advanced_Replace_Deductible_Client/schedule/api/v1/schedule/shop-time-slots.json",
|
|
||||||
"location/api/v1/location/alert-reasons/01813": "0002a_Advanced_Replace_Deductible_Client/location/api/v1/location/alert-reasons/01813.json",
|
"location/api/v1/location/alert-reasons/01813": "0002a_Advanced_Replace_Deductible_Client/location/api/v1/location/alert-reasons/01813.json",
|
||||||
"parts/api/v1/parts/rain-repel": "0002a_Advanced_Replace_Deductible_Client/parts/api/v1/parts/rain-repel.json",
|
"parts/api/v1/parts/rain-repel": "0002a_Advanced_Replace_Deductible_Client/parts/api/v1/parts/rain-repel.json",
|
||||||
"price/api/v1/price/combined-quote": "0002a_Advanced_Replace_Deductible_Client/price/api/v1/price/combined-quote.json"
|
"price/api/v1/price/combined-quote": "0002a_Advanced_Replace_Deductible_Client/price/api/v1/price/combined-quote.json"
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue