Merge branch 'release/2024.12.12' into Feature/Digital/CSR-2338

This commit is contained in:
hiteshkumar87 2024-12-06 23:01:12 +05:30 committed by GitHub
commit 0875676dec
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
18 changed files with 117 additions and 40 deletions

View file

@ -102,6 +102,8 @@ const storeActions = {
RESET_SUBMITTED_ORDER: "resetSubmittedOrder", RESET_SUBMITTED_ORDER: "resetSubmittedOrder",
RESET_EXTERNAL_PARAMETER_STATE: "resetExternalParameterState", RESET_EXTERNAL_PARAMETER_STATE: "resetExternalParameterState",
UPDATE_EXTERNAL_PARAMETER_MMS: "updateExternalParameterMMS", UPDATE_EXTERNAL_PARAMETER_MMS: "updateExternalParameterMMS",
SAVE_LOGGING_OPTION: "saveLoggingOption",
}; };
export { storeActions }; export { storeActions };

View file

@ -84,6 +84,7 @@ const storeMutations = {
UPDATE_STATE_WITH_ORDER_INFORMATION: "updateStateWithOrderInformation", UPDATE_STATE_WITH_ORDER_INFORMATION: "updateStateWithOrderInformation",
UPDATE_SAVE_SESSION_PROMISE: "updateSaveSessionPromise", UPDATE_SAVE_SESSION_PROMISE: "updateSaveSessionPromise",
UPDATE_LAST_PAGE_VISITED: "updateLastPageVisited", UPDATE_LAST_PAGE_VISITED: "updateLastPageVisited",
UPDATE_LOGGING_OPTION: "updateLoggingOption",
// EXPERIMENT MUTATIONS // EXPERIMENT MUTATIONS
UPDATE_EXPERIMENTS: "updateExperiments", UPDATE_EXPERIMENTS: "updateExperiments",

View file

@ -199,6 +199,7 @@ export default {
shouldHideRecalibration: Boolean, shouldHideRecalibration: Boolean,
isItac: Boolean, isItac: Boolean,
isNoComp: Boolean, isNoComp: Boolean,
isExpandedOnLoad: Boolean,
}, },
data() { data() {
return { return {
@ -217,7 +218,7 @@ export default {
this.isExpanded = !this.isExpanded; this.isExpanded = !this.isExpanded;
}, },
updateIsExpandedWithDefault() { updateIsExpandedWithDefault() {
this.isExpanded = this.shouldHideRecalibration; this.isExpanded = this.isExpandedOnLoad;
}, },
getVapsPrice(packageName) { getVapsPrice(packageName) {
const vapsItems = this.getVapsCartItemsForSelectedPackage(packageName); const vapsItems = this.getVapsCartItemsForSelectedPackage(packageName);
@ -297,8 +298,8 @@ export default {
this.lineItems[category] = this.lineItems[category].filter( this.lineItems[category] = this.lineItems[category].filter(
(lineItemsToKeep) => lineItemsToKeep.cartItemType != cartItemType (lineItemsToKeep) => lineItemsToKeep.cartItemType != cartItemType
); );
if (category == cartItemCategories.VAPS) { if (category == cartItemCategories.VAPS || category == cartItemCategories.PROMOS) {
await this.dispatchStoreAction(storeActions.SAVE_VAPS, this.lineItems.vaps, false); this.saveVaps(this.lineItems);
} }
if (category == cartItemCategories.SUPPORTING_ITEMS) { if (category == cartItemCategories.SUPPORTING_ITEMS) {
await this.dispatchStoreAction( await this.dispatchStoreAction(
@ -331,9 +332,8 @@ export default {
}, },
computed: { computed: {
isCartReadyToLoad() { isCartReadyToLoad() {
var myReturn = this.shouldHideRecalibration !== null;
this.updateIsExpandedWithDefault(); this.updateIsExpandedWithDefault();
return myReturn; return this.isExpandedOnLoad !== null;
}, },
lineItems: { lineItems: {
get: function () { get: function () {
@ -749,8 +749,13 @@ export default {
recycleFeeCartItemName() { recycleFeeCartItemName() {
return this.getCmsContent("RecycleFeeTextWidget", "Text"); return this.getCmsContent("RecycleFeeTextWidget", "Text");
}, },
requiresRecycleFeeCartItem() { showRecycleFeeCartItem() {
return !this.isRepair; if (!this.isInsurance || this.isItac || this.isNoComp) {
// CASH, ITAC, NOCOMP ORDERS
return !this.isRepair;
} else {
return false;
}
}, },
recycleFeeCartItem() { recycleFeeCartItem() {
let cartItem = null; let cartItem = null;
@ -759,7 +764,7 @@ export default {
(supportingItem) => supportingItem.partType == partTypeStrings.REPLACE_FEE (supportingItem) => supportingItem.partType == partTypeStrings.REPLACE_FEE
); );
if (!recycleFeeLineItem && this.requiresRecycleFeeCartItem) { if (!recycleFeeLineItem && this.showRecycleFeeCartItem) {
recycleFeeLineItem = { recycleFeeLineItem = {
partNumber: partTypeStrings.RECYCLE_FEE, partNumber: partTypeStrings.RECYCLE_FEE,
partType: partTypeStrings.REPLACE_FEE, partType: partTypeStrings.REPLACE_FEE,

View file

@ -19,6 +19,11 @@ jest.mock("@/mixins/base-mixin", () => ({
return mockReturnsForStoreActions[action]; return mockReturnsForStoreActions[action];
} }
), ),
dispatchStoreAction: jest.fn(
(action, { promoCode, addableVaps }, pageNameToLog, someBool) => {
return mockReturnsForStoreActions[action];
}
),
}, },
})); }));
@ -286,6 +291,13 @@ describe("promo-modal-question.vue", () => {
(lineItemsToKeep) => (lineItemsToKeep) =>
getPromoCodeWithoutBundleIdentifier(lineItemsToKeep.promoCode) != promo getPromoCodeWithoutBundleIdentifier(lineItemsToKeep.promoCode) != promo
)); ));
await baseMixin.methods.dispatchStoreAction(
storeActions.SAVE_ACTIVE_AND_OR_INACTIVE_PROMOS,
{
activePromos: lineItems.promos,
},
false
);
//Assert //Assert
expect(existingPromo).toEqual(lineItems.promos); expect(existingPromo).toEqual(lineItems.promos);

View file

@ -10,7 +10,7 @@
:ref="modalName" :ref="modalName"
:headerText="modalHeaderText" :headerText="modalHeaderText"
:onModalClosedCallback="onModalClosed" :onModalClosedCallback="onModalClosed"
:onModalOpenedCallback="focusOnPromoInput" :onModalOpenedCallback="openModal"
:footerButtonText="modalFooterText" :footerButtonText="modalFooterText"
@footer-button-event="addPromoCode"> @footer-button-event="addPromoCode">
<promoQuestion <promoQuestion
@ -230,6 +230,13 @@ export default {
(lineItemsToKeep) => (lineItemsToKeep) =>
getPromoCodeWithoutBundleIdentifier(lineItemsToKeep.promoCode) != promo getPromoCodeWithoutBundleIdentifier(lineItemsToKeep.promoCode) != promo
); );
await baseMixin.methods.dispatchStoreAction(
storeActions.SAVE_ACTIVE_AND_OR_INACTIVE_PROMOS,
{
activePromos: this.lineItems.promos,
},
false
);
}, },
getErrorMessage(error, additionalInfo) { getErrorMessage(error, additionalInfo) {
switch (error) { switch (error) {

View file

@ -13,7 +13,7 @@ export function updateOrCreateFunnelCookie() {
// Set up cookie with all the props. // Set up cookie with all the props.
setFunnelCookieProperties({ setFunnelCookieProperties({
LastTouched: new Date().toUTCString(), LastTouched: new Date().toJSON(),
SavedSessionTimeoutDate: store.getters.applicationUser.savedSessionTimeout, SavedSessionTimeoutDate: store.getters.applicationUser.savedSessionTimeout,
DidHeritageFunnelUpdateLast: false, DidHeritageFunnelUpdateLast: false,
ShouldResetState: false, ShouldResetState: false,

View file

@ -43,5 +43,5 @@ Function to calculate the date for the saved session timeout.
export function getDateForSavedSessionTimeout() { export function getDateForSavedSessionTimeout() {
const currentDate = new Date(new Date().toUTCString()); const currentDate = new Date(new Date().toUTCString());
currentDate.setDate(currentDate.getDate() + applicationConfig.SAVED_SESSION_TIMEOUT_DAYS); currentDate.setDate(currentDate.getDate() + applicationConfig.SAVED_SESSION_TIMEOUT_DAYS);
return currentDate.toUTCString(); return currentDate.toJSON();
} }

View file

@ -81,7 +81,7 @@ describe("getDateForSavedSessionTimeout", () => {
currentDate.setDate(currentDate.getDate() + applicationConfig.SAVED_SESSION_TIMEOUT_DAYS); currentDate.setDate(currentDate.getDate() + applicationConfig.SAVED_SESSION_TIMEOUT_DAYS);
// Act // Act
const result = getDateForSavedSessionTimeout(); const result = new Date(getDateForSavedSessionTimeout()).toUTCString();
// Assert // Assert
expect(result).toEqual(currentDate.toUTCString()); expect(result).toEqual(currentDate.toUTCString());

View file

@ -45,7 +45,7 @@
class="duration-text-block" /> class="duration-text-block" />
</div> </div>
<hr /> <hr class="mt-4 mb-0" />
<cart <cart
v-if="ShowCart" v-if="ShowCart"
@ -60,6 +60,7 @@
:insuranceCompanyName="insuranceCompanyName" :insuranceCompanyName="insuranceCompanyName"
:showInsuranceCoverageAs="showInsuranceCoverageAs" :showInsuranceCoverageAs="showInsuranceCoverageAs"
:shouldHideRecalibration="shouldHideRecalibration" :shouldHideRecalibration="shouldHideRecalibration"
:isExpandedOnLoad="false"
:isItac="isItac" :isItac="isItac"
:isNoComp="isNoComp" /> :isNoComp="isNoComp" />
@ -111,6 +112,8 @@ import { containsRecalParts } from "@/helpers/recal-helper.js";
export default { export default {
name: "confirmation", name: "confirmation",
async beforeRouteEnter(to, from, next) { async beforeRouteEnter(to, from, next) {
const hasRecalPriceRemoveExperiment = await store.getters.shouldHideRecalibration;
await baseMixin.methods.dispatchStoreAction(storeActions.CREATE_SUBMITTED_ORDER); // This nulls the Store order await baseMixin.methods.dispatchStoreAction(storeActions.CREATE_SUBMITTED_ORDER); // This nulls the Store order
// Call APIs // Call APIs
@ -155,10 +158,6 @@ export default {
const isNoComp = submittedOrder?.policy?.isNoComp; const isNoComp = submittedOrder?.policy?.isNoComp;
const isItac = submittedOrder?.policy?.isItac; const isItac = submittedOrder?.policy?.isItac;
const isRecalibrationOnOrder = containsRecalParts(lineItemsFromSubmittedOrder); const isRecalibrationOnOrder = containsRecalParts(lineItemsFromSubmittedOrder);
const hasRecalPriceRemoveExperiment =
experimentMixin.methods
.getSettingValue(experimentSettings.RECAL_PRICE_REMOVE)
?.toLowerCase() === "true";
const shouldHideRecalibration = () => { const shouldHideRecalibration = () => {
if (isNoComp || isItac) { if (isNoComp || isItac) {

View file

@ -32,9 +32,10 @@
:showInsuranceCoverageAs="showInsuranceCoverageAs" :showInsuranceCoverageAs="showInsuranceCoverageAs"
:shouldHideRecalibration="shouldHideRecalibration" :shouldHideRecalibration="shouldHideRecalibration"
:isItac="isItac" :isItac="isItac"
:isNoComp="isNoComp" /> :isNoComp="isNoComp"
:isExpandedOnLoad="false" />
<hr class="my-5" /> <hr />
<div> <div>
<alert <alert
@ -46,16 +47,16 @@
v-bind:isDismissible="false" /> v-bind:isDismissible="false" />
</div> </div>
<div v-if="!isInsurance" class="questions-about-service my-5"> <div
v-if="isRecalibrationOnOrder && shouldHideRecalibration"
class="questions-about-service my-5">
<textBlock <textBlock
cmsWidgetName="QuestionsAboutYourServiceWidget" cmsWidgetName="QuestionsAboutYourServiceWidget"
justifyText="left" justifyText="left"
class="service-questions" /> class="service-questions" />
<textBlock cmsWidgetName="CallOrTextWidget" justifyText="left" /> <textBlock cmsWidgetName="CallOrTextWidget" justifyText="left" />
<hr class="my-5" /> <hr class="my-5" />
<div <div class="d-flex flex-row checkbox-group">
class="d-flex flex-row checkbox-group"
v-if="isRecalibrationOnOrder && shouldHideRecalibration">
<checkboxQuestion <checkboxQuestion
cmsWidgetName="RecalConfirmWidget" cmsWidgetName="RecalConfirmWidget"
class="mb-5" class="mb-5"

View file

@ -55,11 +55,13 @@
v-model="lineItems" v-model="lineItems"
servicePackageOptionsCmsName="ServicePackageTitle" servicePackageOptionsCmsName="ServicePackageTitle"
recyclingModalCmsWidgetName="RecycleModal" recyclingModalCmsWidgetName="RecycleModal"
:isInsurance="isInsurance"
:insuranceDeductible="currentDeductible" :insuranceDeductible="currentDeductible"
:insuranceCompanyName="insuranceCompanyName" :insuranceCompanyName="insuranceCompanyName"
:showInsuranceCoverageAs="showInsuranceCoverageAs" :showInsuranceCoverageAs="showInsuranceCoverageAs"
:isItac="isItac" :isItac="isItac"
:isNocomp="isNocomp" /> :isNoComp="isNoComp"
:isExpandedOnLoad="true" />
<hr class="mb-5" /> <hr class="mb-5" />

View file

@ -428,8 +428,11 @@ export default {
); );
}, },
shouldHideRecalibration() { shouldHideRecalibration() {
if (this.isInsuranceSelected) return false; return (
return (experimentMixin.methods.getSettingValue(experimentSettings.RECAL_PRICE_REMOVE)?.toLowerCase() === "true" && this.isRecalibrationOnOrder); experimentMixin.methods
.getSettingValue(experimentSettings.RECAL_PRICE_REMOVE)
?.toLowerCase() === "true" && this.isRecalibrationOnOrder
);
}, },
showAfterpayBanner() { showAfterpayBanner() {
return ( return (

View file

@ -436,7 +436,6 @@ export default {
policy.policyNumber !== ""; policy.policyNumber !== "";
const skipVin = await skipVinLookup(); const skipVin = await skipVinLookup();
if (vehicleChangedDuringPolicyLookupInHeritage) { if (vehicleChangedDuringPolicyLookupInHeritage) {
if (skipVin) { if (skipVin) {
this.$router.navigateWithSaving( this.$router.navigateWithSaving(
@ -455,13 +454,22 @@ export default {
{ [routerParams.DISPLAY_VEHICLE_CHANGE_ALERT]: false } { [routerParams.DISPLAY_VEHICLE_CHANGE_ALERT]: false }
); );
} else { } else {
this.$router.navigateWithSaving( if (store.getters.vehicle.vin) {
this.navigationScenarios this.$router.navigateWithSaving(
.CLICKED_FORWARD_WITH_REPLACE_AND_VERIFIED_INSURANCE, this.navigationScenarios
this.$route, .CLICKED_FORWARD_WITH_REPLACE_AND_VERIFIED_INSURANCE,
{}, this.$route,
{ [routerParams.DISPLAY_VEHICLE_CHANGE_ALERT]: false } {},
); { [routerParams.DISPLAY_VEHICLE_CHANGE_ALERT]: false }
);
} else {
this.$router.navigateWithSaving(
this.navigationScenarios.CLICKED_FORWARD_WITHOUT_VIN,
this.$route,
{},
{ [routerParams.DISPLAY_VEHICLE_CHANGE_ALERT]: false }
);
}
} }
} }
} }

View file

@ -460,6 +460,7 @@ async function navigate(
const promo = getQuerystringParameter(queryStrings.PROMO); const promo = getQuerystringParameter(queryStrings.PROMO);
const pageError = getQuerystringParameter(queryStrings.PAGE_ERROR); const pageError = getQuerystringParameter(queryStrings.PAGE_ERROR);
const logQs = getQuerystringParameter(queryStrings.LOG); const logQs = getQuerystringParameter(queryStrings.LOG);
baseMixin.methods.dispatchStoreAction(storeActions.SAVE_LOGGING_OPTION, logQs, false);
log("------------- router index.js navigate start -----------------"); log("------------- router index.js navigate start -----------------");
log(" --scenario: ", scenario); log(" --scenario: ", scenario);

View file

@ -41,7 +41,11 @@ import {
coverageTypeValue, coverageTypeValue,
coverageTypeEnum, coverageTypeEnum,
} from "@/constants/insurance"; } from "@/constants/insurance";
import { containsRecalParts, getTopLevelPartsWithRecal } from "@/helpers/recal-helper"; import {
containsRecalParts,
getTopLevelPartsWithRecal,
isRecalPartOrHasChildRecalPart,
} from "@/helpers/recal-helper";
import { externalParameterStatus } from "@/constants/external-parameters"; import { externalParameterStatus } from "@/constants/external-parameters";
import { experimentSettings } from "@/constants/experiments"; import { experimentSettings } from "@/constants/experiments";
import experimentMixin from "@/mixins/experiment-mixin.js"; import experimentMixin from "@/mixins/experiment-mixin.js";
@ -180,6 +184,7 @@ const getDefaultState = () => {
experiments: [], experiments: [],
triggeredSiteEntry: false, triggeredSiteEntry: false,
affiliateCookies: [], affiliateCookies: [],
loggingOption: false,
}, },
}; };
}; };
@ -410,6 +415,9 @@ export const mutations = {
updateLastPageVisited(state, lastPageVisited) { updateLastPageVisited(state, lastPageVisited) {
state.applicationUser.lastPageVisited = lastPageVisited; state.applicationUser.lastPageVisited = lastPageVisited;
}, },
updateLoggingOption(state, loggingOption) {
state.applicationUser.loggingOption = loggingOption;
},
// EVENT BUS MUTATIONS // EVENT BUS MUTATIONS
addEventToBus(state, event) { addEventToBus(state, event) {
state.applicationUser.eventBus.push(event); state.applicationUser.eventBus.push(event);
@ -685,6 +693,10 @@ export const mutations = {
!sessionInformation.order.payment.isInsurance && !sessionInformation.order.payment.isInsurance &&
!sessionInformation.order.serviceLocation.provider?.providerNumber !sessionInformation.order.serviceLocation.provider?.providerNumber
) { ) {
console.log(
"------------- updateStateWithOrderInformation reset isInsurance -----------------"
);
console.log(new Date() + " sessionInformation: " + JSON.stringify(sessionInformation));
state.order.payment.isInsurance = null; state.order.payment.isInsurance = null;
} else { } else {
state.order.payment.isInsurance = sessionInformation.order.payment.isInsurance; state.order.payment.isInsurance = sessionInformation.order.payment.isInsurance;
@ -1025,6 +1037,7 @@ export const actions = {
endpoint: endpoints.LookupVehicleByVin.url, endpoint: endpoints.LookupVehicleByVin.url,
payload: { payload: {
vin: vin, // EX "1J4GW58S4XC541166" vin: vin, // EX "1J4GW58S4XC541166"
logEnabled: context.getters.applicationUser.loggingOption,
}, },
logApiCall: true, logApiCall: true,
pageNameToLog: pageNameToLog, pageNameToLog: pageNameToLog,
@ -1651,9 +1664,10 @@ export const actions = {
const partialLineItemsObjects = context.getters.order.lineItems.glassParts?.map( const partialLineItemsObjects = context.getters.order.lineItems.glassParts?.map(
(lineItem) => ({ (lineItem) => ({
partNumber: lineItem.partNumber, partNumber: lineItem.partNumber,
recalibrationType: lineItem.recalibrationType recalibrationType:
? escapeRecalibrationType(lineItem.recalibrationType) lineItem.recalibrationType && isRecalPartOrHasChildRecalPart(lineItem)
: undefined, ? escapeRecalibrationType(lineItem.recalibrationType)
: undefined,
}) })
); );
@ -3009,6 +3023,15 @@ export const actions = {
); );
}, },
saveLoggingOption(context, loggingOption) {
var option = false;
if (loggingOption != null) {
option = loggingOption == "true" ? true : false;
}
context.commit(storeMutations.UPDATE_LOGGING_OPTION, option);
},
async getRecalPartsAndSaveToLineItems(context, { pageNameToLog }) { async getRecalPartsAndSaveToLineItems(context, { pageNameToLog }) {
// identify each part that needs recal // identify each part that needs recal
const glassParts = context.state.order?.lineItems?.glassParts const glassParts = context.state.order?.lineItems?.glassParts

View file

@ -404,6 +404,11 @@ describe("Actions", () => {
it("lookupVehicleByVin action, should return car data", async () => { it("lookupVehicleByVin action, should return car data", async () => {
// Arrange // Arrange
const context = state; const context = state;
context.getters = {
applicationUser: {
loggingOption: false,
},
};
// Act // Act
globalMethods.callHttpClient.mockImplementation(() => { globalMethods.callHttpClient.mockImplementation(() => {

View file

@ -10,7 +10,7 @@ body {
overflow-x: unset; overflow-x: unset;
} }
&.page-container-grouped-styles { &.page-container-grouped-styles {
height: 100vh; height: 100dvh;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
} }
@ -68,6 +68,14 @@ body {
height: 1px; height: 1px;
overflow: hidden; overflow: hidden;
} }
// Fix "iOS viewport scroll bug" issue on iPhone
// where bottom of page is covered by address bar
@media only screen and (min-device-width: 375px) and (max-device-width: 812px) and (-webkit-min-device-pixel-ratio: 3) and (orientation: portrait) {
.page-container-grouped-styles {
padding-bottom: 3rem;
}
}
} }
.modal-open { .modal-open {
.container-fluid { .container-fluid {

View file

@ -7,7 +7,7 @@
]" ]"
v-model="selectedValue"> v-model="selectedValue">
<div <div
class="button-content list-button-horizontal-content d-flex flex-column justify-content-center p-2"> class="button-content list-button-horizontal-content d-flex flex-column justify-content-center py-3 px-1">
<span class="m-0" :class="textPosition"> <span class="m-0" :class="textPosition">
{{ buttonLabel }} {{ buttonLabel }}
</span> </span>