diff --git a/src/common-components/modal/modal.vue b/src/common-components/modal/modal.vue index 9a8e6c211..e965b3e3f 100644 --- a/src/common-components/modal/modal.vue +++ b/src/common-components/modal/modal.vue @@ -60,11 +60,16 @@ export default { return this.getCmsContent(this.cmsWidgetName, "FooterText"); }, }, + methods: { + setupModalEventListener() { + const modal = document.querySelector("#" + this.cmsWidgetName); + modal.addEventListener("hidden.bs.modal", (event) => { + this.$refs.buttonMain.resetButtonStyle(); + }); + }, + }, mounted() { - const modal = document.querySelector("#" + this.cmsWidgetName); - modal.addEventListener("hidden.bs.modal", (event) => { - this.$refs.buttonMain.resetButtonStyle(); - }); + this.setupModalEventListener(); }, components: { buttonMain, diff --git a/src/layouts/quote/quote.vue b/src/layouts/quote/quote.vue index 424b864d8..6f9ef8be6 100644 --- a/src/layouts/quote/quote.vue +++ b/src/layouts/quote/quote.vue @@ -21,10 +21,11 @@ ref="servicePackage" cashCmsWidgetName="CashServicePackageQuestionWidget" insuranceCmsWidgetName="InsuranceServicePackageQuestionWidget" - v-model="selectedVaps" groupName="ServicePackageQuestion" :availableLineItems="availableLineItems" - :isInsuranceSelected="isInsuranceSelected" /> + :isInsuranceSelected="isInsuranceSelected" + @vapsItemsSelected="vapsItemsSelectedAction" /> + 0); + return ( + store.getters.order.damage.isRepair || + (store.getters.order.lineItems?.glassParts != null && + store.getters.order.lineItems.glassParts.length > 0) + ); }, getDefaultIsInsuranceSelectedValue() { const defaultIsInsuranceSelectedValue = this.$store.getters.order.payment.isInsurance; @@ -137,6 +141,9 @@ export default { : null; } }, + vapsItemsSelectedAction(vapsItemsSelected) { + this.selectedVaps = vapsItemsSelected; + }, backButtonAction() { vehicleQuestionsMixin.methods.navigateBack(this); }, diff --git a/src/layouts/quote/service-package-question/service-package-question.spec.js b/src/layouts/quote/service-package-question/service-package-question.spec.js index e0608e713..cd10b893f 100644 --- a/src/layouts/quote/service-package-question/service-package-question.spec.js +++ b/src/layouts/quote/service-package-question/service-package-question.spec.js @@ -58,7 +58,7 @@ describe("service-package-question.vue", () => { await nextTick(); // Assert - expect(wrapper.emitted()["update:modelValue"][0][0]).toEqual([ + expect(wrapper.emitted()["vapsItemsSelected"][0][0]).toEqual([ { description: null, partNumber: "RAIN DEFENSE", diff --git a/src/layouts/quote/service-package-question/service-package-question.vue b/src/layouts/quote/service-package-question/service-package-question.vue index 3c88b43c0..1c7f93e08 100644 --- a/src/layouts/quote/service-package-question/service-package-question.vue +++ b/src/layouts/quote/service-package-question/service-package-question.vue @@ -25,7 +25,6 @@ const packageNames = { export default { name: "servicePackageQuestion", props: { - modelValue: String, groupName: String, cashCmsWidgetName: String, insuranceCmsWidgetName: String, @@ -46,7 +45,7 @@ export default { }, selectedPackageName(newValue) { const VapsProductsInSelectedPackage = this.getVapsLineItemsForSelectedPackage(newValue); - this.$emit("update:modelValue", VapsProductsInSelectedPackage); + this.$emit("vapsItemsSelected", VapsProductsInSelectedPackage); }, }, computed: { diff --git a/src/layouts/vehicle-parts/vehicle-parts.spec.js b/src/layouts/vehicle-parts/vehicle-parts.spec.js index 66b8996e7..b885cc1c1 100644 --- a/src/layouts/vehicle-parts/vehicle-parts.spec.js +++ b/src/layouts/vehicle-parts/vehicle-parts.spec.js @@ -248,7 +248,9 @@ describe("vehicle-parts.vue", () => { (c) => c(wrapper.vm) ); - wrapper.vm.navigateBack(); + store.dispatch = jest.fn(() => {}); + + await wrapper.vm.navigateBack(); //Assert expect(wrapper.vm.$router.navigateWithoutSaving).toHaveBeenCalledWith( @@ -294,7 +296,8 @@ describe("vehicle-parts.vue", () => { (c) => c(wrapper.vm) ); - wrapper.vm.navigateBack(); + store.dispatch = jest.fn(() => {}); + await wrapper.vm.navigateBack(); //Assert expect(wrapper.vm.$router.navigateWithoutSaving).toHaveBeenCalledWith( diff --git a/src/mixins/vehicle-questions-mixin.js b/src/mixins/vehicle-questions-mixin.js index 493c5ef17..2ae850a6c 100644 --- a/src/mixins/vehicle-questions-mixin.js +++ b/src/mixins/vehicle-questions-mixin.js @@ -458,32 +458,42 @@ export default { } }, // Can't use `this` because navigateForward is also called from quote - navigateBack(vm) { - + async navigateBack(vm) { const self = vm ?? this; const currentPage = self.$route.query.fmgPage; - - const pageDataCapabilityQuestions = self.$store.getters.pageData(fmgPageValues.CAPABILITY_QUESTIONS); - const pageDataMoldingQuestions = self.$store.getters.pageData(fmgPageValues.MOLDING_QUESTIONS); + const pageDataCapabilityQuestions = self.$store.getters.pageData( + fmgPageValues.CAPABILITY_QUESTIONS + ); + const pageDataMoldingQuestions = self.$store.getters.pageData( + fmgPageValues.MOLDING_QUESTIONS + ); const pageDataVehicleParts = self.$store.getters.pageData(fmgPageValues.VEHICLE_PARTS); - const pageDataPartQuestions = self.$store.getters.pageData(fmgPageValues.PART_QUESTIONS); + const pageDataPartQuestions = self.$store.getters.pageData( + fmgPageValues.PART_QUESTIONS + ); const currentPartsOrQuestions = ( - (currentPage !== fmgPageValues.CAPABILITY_QUESTIONS ? pageDataCapabilityQuestions : null) ?? - (currentPage !== fmgPageValues.MOLDING_QUESTIONS ? pageDataMoldingQuestions : null) ?? + (currentPage !== fmgPageValues.CAPABILITY_QUESTIONS + ? pageDataCapabilityQuestions + : null) ?? + (currentPage !== fmgPageValues.MOLDING_QUESTIONS + ? pageDataMoldingQuestions + : null) ?? (currentPage !== fmgPageValues.VEHICLE_PARTS ? pageDataVehicleParts : null) ?? (currentPage !== fmgPageValues.PARTS_QUESTIONS ? pageDataPartQuestions : null) )?.partsOrQuestions; - + const hasPartQuestions = this.hasPartQuestions(currentPartsOrQuestions); - const hasGlassLocationWithMultipleParts = this.hasGlassLocationWithMultipleParts(currentPartsOrQuestions); + const hasGlassLocationWithMultipleParts = + this.hasGlassLocationWithMultipleParts(currentPartsOrQuestions); const hasChildPartQuestions = this.hasChildPartQuestions(currentPartsOrQuestions); const hasCapabilityQuestions = this.hasCapabilityQuestions(currentPartsOrQuestions); - + const skipVinLookup = await store.dispatch(storeActions.IS_VIN_OPTIONAL_VEHICLE); + let backNavigationScenario = self.$store.getters.vehicle.vin - ? navigationScenarios.CLICKED_BACK_WITH_VIN_AND_NO_MORE_QUESTIONS - : navigationScenarios.CLICKED_BACK_WITH_NO_VIN_NOR_QUESTIONS; - + ? navigationScenarios.CLICKED_BACK_WITH_VIN_AND_NO_MORE_QUESTIONS + : navigationScenarios.CLICKED_BACK_WITH_NO_VIN_NOR_QUESTIONS; + if ( hasCapabilityQuestions && this.currentPageComesAfterPage(currentPage, fmgPageValues.CAPABILITY_QUESTIONS) @@ -505,6 +515,8 @@ export default { this.currentPageComesAfterPage(currentPage, fmgPageValues.PART_QUESTIONS) ) { backNavigationScenario = navigationScenarios.CLICKED_BACK_WITH_PART_QUESTIONS; + } else if (skipVinLookup) { + backNavigationScenario = navigationScenarios.CLICKED_BACK_TO_GO_TO_ESTIMATE; } self.$router.navigateWithoutSaving(backNavigationScenario, self.$route); diff --git a/src/mixins/vehicle-questions-mixin.spec.js b/src/mixins/vehicle-questions-mixin.spec.js index 6747e618a..a9bf6f313 100644 --- a/src/mixins/vehicle-questions-mixin.spec.js +++ b/src/mixins/vehicle-questions-mixin.spec.js @@ -3,6 +3,7 @@ import { shallowMount } from "@vue/test-utils"; import { setupMocksForJsFiles, getMountOptions } from "@/helpers/unit-test-helper.js"; import { fmgPageValues } from "@/router/router-constants/fmgPage-values"; import { storeMutations } from "@/constants/store-mutations"; +import store from "@/store"; import { storeActions } from "@/constants/store-actions"; import { navigationScenarios } from "../router/router-constants/navigation-scenarios"; import { getters } from "@/store"; @@ -2259,12 +2260,13 @@ describe("vehicle-questions-mixin", () => { "current page is quote, there are no questions, and we don't have their vin => go to estimate" ); - test("current page is quote, there are no questions, and we have their vin => go to vin-lookup", () => { + test("current page is quote, there are no questions, and we have their vin => go to vin-lookup", async () => { // Arrange const { wrapper } = setupMocks({ fmgPage: fmgPageValues.QUOTE, hasVin: true }); // Act - wrapper.vm.navigateBack(); + store.dispatch = jest.fn(() => {}); + await wrapper.vm.navigateBack(); // Assert expect(wrapper.vm.$router.navigateWithoutSaving).toHaveBeenCalledWith( @@ -2273,13 +2275,14 @@ describe("vehicle-questions-mixin", () => { ); }); - test("current page is quote and there are capability questions => go to capability questions", () => { + test("current page is quote and there are capability questions => go to capability questions", async () => { // Arrange const { wrapper } = setupMocks({ fmgPage: fmgPageValues.QUOTE }); wrapper.vm.hasCapabilityQuestions = jest.fn().mockReturnValue(true); // Act - wrapper.vm.navigateBack(); + store.dispatch = jest.fn(() => {}); + await wrapper.vm.navigateBack(); // Assert expect(wrapper.vm.$router.navigateWithoutSaving).toHaveBeenCalledWith( @@ -2288,14 +2291,14 @@ describe("vehicle-questions-mixin", () => { ); }); - test("current page is quote and there are part questions and molding questions => go to molding questions", () => { + test("current page is quote and there are part questions and molding questions => go to molding questions", async () => { // Arrange const { wrapper } = setupMocks({ fmgPage: fmgPageValues.QUOTE }); wrapper.vm.hasPartQuestions = jest.fn().mockReturnValue(true); wrapper.vm.hasChildPartQuestions = jest.fn().mockReturnValue(true); // Act - wrapper.vm.navigateBack(); + await wrapper.vm.navigateBack(); // Assert expect(wrapper.vm.$router.navigateWithoutSaving).toHaveBeenCalledWith( @@ -2304,7 +2307,7 @@ describe("vehicle-questions-mixin", () => { ); }); - test("current page is molding questions and there are part questions, multiple parts to choose, and capability questions => go to vehicle-parts", () => { + test("current page is molding questions and there are part questions, multiple parts to choose, and capability questions => go to vehicle-parts", async () => { // Arrange const { wrapper } = setupMocks({ fmgPage: fmgPageValues.MOLDING_QUESTIONS }); wrapper.vm.hasPartQuestions = jest.fn().mockReturnValue(true); @@ -2313,7 +2316,8 @@ describe("vehicle-questions-mixin", () => { wrapper.vm.hasCapabilityQuestions = jest.fn().mockReturnValue(true); // Act - wrapper.vm.navigateBack(); + store.dispatch = jest.fn(() => {}); + await wrapper.vm.navigateBack(); // Assert expect(wrapper.vm.$router.navigateWithoutSaving).toHaveBeenCalledWith( @@ -2322,7 +2326,7 @@ describe("vehicle-questions-mixin", () => { ); }); - test("current page is molding questions and there are part questions and capability questions => go to part-questions", () => { + test("current page is molding questions and there are part questions and capability questions => go to part-questions", async () => { // Arrange const { wrapper } = setupMocks({ fmgPage: fmgPageValues.MOLDING_QUESTIONS }); wrapper.vm.hasPartQuestions = jest.fn().mockReturnValue(true); @@ -2331,7 +2335,8 @@ describe("vehicle-questions-mixin", () => { wrapper.vm.hasCapabilityQuestions = jest.fn().mockReturnValue(true); // Act - wrapper.vm.navigateBack(); + store.dispatch = jest.fn(() => {}); + await wrapper.vm.navigateBack(); // Assert expect(wrapper.vm.$router.navigateWithoutSaving).toHaveBeenCalledWith( diff --git a/src/router/router-constants/navigation-scenarios.js b/src/router/router-constants/navigation-scenarios.js index 6a1adf5da..d69806623 100644 --- a/src/router/router-constants/navigation-scenarios.js +++ b/src/router/router-constants/navigation-scenarios.js @@ -40,6 +40,7 @@ const navigationScenarios = { CLICKED_BACK_WITH_CAPABILITY_QUESTIONS: "CLICKED_BACK_WITH_CAPABILITY_QUESTIONS", CLICKED_BACK_WITH_VIN_AND_NO_MORE_QUESTIONS: "CLICKED_BACK_WITH_VIN_AND_NO_MORE_QUESTIONS", CLICKED_BACK_WITH_NO_VIN_NOR_QUESTIONS: "CLICKED_BACK_WITH_NO_VIN_NOR_QUESTIONS", + CLICKED_BACK_TO_GO_TO_ESTIMATE: "CLICKED_BACK_TO_GO_TO_ESTIMATE", }; export { navigationScenarios }; diff --git a/src/router/router-constants/routing-table.js b/src/router/router-constants/routing-table.js index a431e342e..aec0a9249 100644 --- a/src/router/router-constants/routing-table.js +++ b/src/router/router-constants/routing-table.js @@ -286,6 +286,10 @@ const routingTable = function (store) { scenario: navigationScenarios.CLICKED_FORWARD_WITH_NO_MORE_QUESTIONS, destinationFmgPageValue: fmgPageValues.QUOTE, }, + { + scenario: navigationScenarios.CLICKED_BACK_TO_GO_TO_ESTIMATE, + destinationFmgPageValue: fmgPageValues.ESTIMATE, + }, ], }, { @@ -319,6 +323,10 @@ const routingTable = function (store) { scenario: navigationScenarios.CLICKED_FORWARD_WITH_NO_MORE_QUESTIONS, destinationFmgPageValue: fmgPageValues.QUOTE, }, + { + scenario: navigationScenarios.CLICKED_BACK_TO_GO_TO_ESTIMATE, + destinationFmgPageValue: fmgPageValues.ESTIMATE, + }, ], }, { @@ -348,6 +356,10 @@ const routingTable = function (store) { scenario: navigationScenarios.CLICKED_FORWARD_WITH_NO_MORE_QUESTIONS, destinationFmgPageValue: fmgPageValues.QUOTE, }, + { + scenario: navigationScenarios.CLICKED_BACK_TO_GO_TO_ESTIMATE, + destinationFmgPageValue: fmgPageValues.ESTIMATE, + }, ], }, { @@ -377,6 +389,10 @@ const routingTable = function (store) { scenario: navigationScenarios.CLICKED_FORWARD_WITH_NO_MORE_QUESTIONS, destinationFmgPageValue: fmgPageValues.QUOTE, }, + { + scenario: navigationScenarios.CLICKED_BACK_TO_GO_TO_ESTIMATE, + destinationFmgPageValue: fmgPageValues.ESTIMATE, + }, ], }, {