diff --git a/jest.config.js b/jest.config.js
index a511fdc02..fe6eeb04d 100644
--- a/jest.config.js
+++ b/jest.config.js
@@ -20,10 +20,8 @@ module.exports = {
"!src/layouts/reveal/**/*.vue",
"!src/layouts/estimate/**/*.vue",
// TODO REMOVE THESE AFTER WRITING UNIT TESTS
- "!src/layouts/address-vehicles/address-vehicles-question/address-vehicles-question.vue",
"!src/ux-components/alert/alert.vue",
"!src/helpers/validation-rules.js",
- "!src/common-components/question-chain/question-chain",
// END
], // ! means exclude from coverage.
testMatch: ["**/*.spec.(js|jsx|ts|tsx)|**/__tests__/*.(js|jsx|ts|tsx)"],
diff --git a/src/common-components/funnel-sub-header/funnel-sub-header.vue b/src/common-components/funnel-sub-header/funnel-sub-header.vue
index f8ac3134a..3ad7c71d3 100644
--- a/src/common-components/funnel-sub-header/funnel-sub-header.vue
+++ b/src/common-components/funnel-sub-header/funnel-sub-header.vue
@@ -29,20 +29,22 @@ export default {
name: "FunnelSubHeader",
props: {
hasBackButton: Boolean,
- backButtonAccessibleText: String,
cmsWidgetName: String,
},
components: {
buttonBack,
},
computed: {
- text(){
+ text() {
return this.getCmsContent(this.cmsWidgetName, 'HeaderText');
},
- subText(){
+ subText() {
return this.getCmsContent(this.cmsWidgetName, 'HeaderSubText');
},
- headerColor(){
+ backButtonAccessibleText() {
+ return this.getCmsContent(this.cmsWidgetName, 'BackButtonAccessibleText');
+ },
+ headerColor() {
return this.subText ? 'dark-header' : 'light-header';
}
},
diff --git a/src/common-components/question-chain/question-chain.spec.js b/src/common-components/question-chain/question-chain.spec.js
new file mode 100644
index 000000000..84795fac0
--- /dev/null
+++ b/src/common-components/question-chain/question-chain.spec.js
@@ -0,0 +1,241 @@
+import { shallowMount } from "@vue/test-utils";
+import questionChain from "@/common-components/question-chain/question-chain.vue";
+import { getMountOptions } from "@/helpers/unit-test-helper.js";
+import store from "@/store";
+jest.mock("@/store",()=>{return{};},{virtual:true});
+
+describe("Question Chain component", () => {
+
+ it("Should not emit a modelValue change when setting selectedValue if isNewModelValueComplete is false", () => {
+
+ //Arrange
+ const { wrapper } = setupMocks({ modelValueProp: [] });
+ wrapper.vm.currentQuestion = 6;
+ const answerReturned = [wrapper.vm.questions[wrapper.vm.currentQuestion].answers[0].Name.toString()];
+ const localThis = {
+ $emit: jest.fn(),
+ getNewModelValue: jest.fn(() => { return false })
+ }
+
+ //Act
+ questionChain.computed.selectedValue.set.call(localThis, answerReturned);
+
+ //Assert
+ expect(localThis.$emit).not.toBeCalled();
+ });
+
+ it("Should emit a modelValue change when setting selectedValue if isNewModelValueComplete is true", () => {
+
+ //Arrange
+ const { wrapper } = setupMocks({ modelValueProp: [] });
+ wrapper.vm.currentQuestion = 6;
+ const answerReturned = [wrapper.vm.questions[wrapper.vm.currentQuestion].answers[0].Name.toString()];
+ const localThis = {
+ $emit: jest.fn(),
+ getNewModelValue: jest.fn(() => { return true })
+ }
+
+ //Act
+ questionChain.computed.selectedValue.set.call(localThis, answerReturned);
+
+ //Assert
+ expect(localThis.$emit).toBeCalledWith("update:modelValue", true);
+ });
+
+ it("should return false if no returned answer is given", () => {
+
+ //Arrange
+ const { wrapper } = setupMocks({ modelValueProp: [] });
+ wrapper.vm.currentQuestion = 1;
+ const answerReturned = null;
+
+ //Act
+ const result = wrapper.vm.getNewModelValue(answerReturned);
+
+ //Assert
+ expect(result).toEqual(false);
+ });
+
+ it("should return false if the user's answer on the current question leads to another question", () => {
+
+ //Arrange
+ const { wrapper } = setupMocks({ modelValueProp: [] });
+ wrapper.vm.currentQuestion = 1;
+ const answerReturned = [wrapper.vm.questions[wrapper.vm.currentQuestion].answers[0].Name.toString()];
+
+ //Act
+ const result = wrapper.vm.getNewModelValue(answerReturned);
+
+ //Assert
+ expect(result).toEqual(false);
+ });
+
+ it("should return an object with the final answer if the user's answer on the current question is a part number", () => {
+
+ //Arrange
+ const { wrapper } = setupMocks({ modelValueProp: [] });
+ wrapper.vm.currentQuestion = 6;
+ const answerReturned = [wrapper.vm.questions[wrapper.vm.currentQuestion].answers[0].Name.toString()];
+
+ //Act
+ const result = wrapper.vm.getNewModelValue(answerReturned);
+
+ //Assert
+ expect(result).toEqual(
+ {
+ answerResult: 'DW02102',
+ answeredQuestions: [
+ {
+ questionText: 'Is your vehicle equipped with heated seats?',
+ selectedAnswerText: 'Yes'
+ }
+ ]
+ }
+ );
+
+ });
+
+});
+
+function setupMocks({
+ modelValueProp = "",
+ questionDataProp = {
+ "glassName": "Single",
+ "glassLocation": "Windshield",
+ "parts": null,
+ "partQuestions": [
+ {
+ "questionSequence": 1,
+ "questionText": "Is your Cherokee the Overland edition which can be identified by having a wood and leather wrapped steering wheel?",
+ "answers": [
+ {
+ "answerText": "Yes",
+ "nextQuestionSequence": 2,
+ "answerResult": ""
+ },
+ {
+ "answerText": "No",
+ "nextQuestionSequence": 3,
+ "answerResult": ""
+ }
+ ]
+ },
+ {
+ "questionSequence": 2,
+ "questionText": "Is your vehicle equipped with rain sensing wipers that adjust their speed automatically when it rains?",
+ "answers": [
+ {
+ "answerText": "Yes",
+ "nextQuestionSequence": null,
+ "answerResult": "DW02270"
+ },
+ {
+ "answerText": "No",
+ "nextQuestionSequence": null,
+ "answerResult": "DW02264"
+ }
+ ]
+ },
+ {
+ "questionSequence": 3,
+ "questionText": "Is your vehicle equipped with rain sensing wipers that adjust their speed automatically when it rains?",
+ "answers": [
+ {
+ "answerText": "Yes",
+ "nextQuestionSequence": null,
+ "answerResult": "DW02268"
+ },
+ {
+ "answerText": "No",
+ "nextQuestionSequence": 4,
+ "answerResult": ""
+ }
+ ]
+ },
+ {
+ "questionSequence": 4,
+ "questionText": "Is your vehicle equipped with automatic climate control which will change the fan speed automatically in order to maintain a set temperature?",
+ "answers": [
+ {
+ "answerText": "Yes",
+ "nextQuestionSequence": 5,
+ "answerResult": ""
+ },
+ {
+ "answerText": "No",
+ "nextQuestionSequence": 6,
+ "answerResult": ""
+ }
+ ]
+ },
+ {
+ "questionSequence": 5,
+ "questionText": "Is your vehicle equipped with heated seats?",
+ "answers": [
+ {
+ "answerText": "Yes",
+ "nextQuestionSequence": null,
+ "answerResult": "DW02104"
+ },
+ {
+ "answerText": "No",
+ "nextQuestionSequence": null,
+ "answerResult": "DW02103"
+ }
+ ]
+ },
+ {
+ "questionSequence": 6,
+ "questionText": "Is your vehicle equipped with heated seats?",
+ "answers": [
+ {
+ "answerText": "Yes",
+ "nextQuestionSequence": null,
+ "answerResult": "DW02102"
+ },
+ {
+ "answerText": "No",
+ "nextQuestionSequence": null,
+ "answerResult": "DW02101"
+ }
+ ]
+ }
+ ],
+ },
+ methodsToMock = [],
+}) {
+
+ //Mock store
+ store.dispatch = jest.fn(() => dataFromStoreApi);
+ store.getters = { vehicle: {year: 2019, make: 'honda', model: 'civc', style: '2 Door', category: 'CAR'} };
+ const mountOptions = getMountOptions({
+ store: {
+ dispatch: store.dispatch,
+ getters: store.getters,
+ },
+ });
+
+ //Mock props
+ const mockMixin = {
+ methods: {
+ getCmsContent: jest.fn()
+ }
+ }
+ mountOptions.propsData = {
+ modelValue: modelValueProp,
+ questionData: questionDataProp,
+ };
+ mountOptions.mixins = [mockMixin];
+
+ //Mock methods
+ methodsToMock.forEach((methodName) => {
+ questionChain.methods[methodName] = jest.fn();
+ });
+
+ const wrapper = shallowMount(questionChain, mountOptions);
+
+ //Mock CMS content
+ const cmsContent = {
+ };
+ return { wrapper, cmsContent };
+}
\ No newline at end of file
diff --git a/src/common-components/question-chain/question-chain.vue b/src/common-components/question-chain/question-chain.vue
index d605d7fde..ef56c4041 100644
--- a/src/common-components/question-chain/question-chain.vue
+++ b/src/common-components/question-chain/question-chain.vue
@@ -9,7 +9,7 @@
:groupName="`${questionData.glassName}-${questionData.glassLocation}-${i}`"
textPosition="text-start"
v-model="selectedValue"
- isRequired=true
+ :isRequired=true
:validationRules="validationRules"
:clearOnUnmount=false
/>
@@ -30,12 +30,14 @@ export default {
};
},
props: {
- questionData: Array,
+ questionData: Object,
validationRules: String,
- modelValue: String,
+ modelValue: Array,
},
computed: {
+
questions() {
+ console.log("answeredQuestions: ", this.answeredQuestions)
const questions = this.questionData.partQuestions.map((q, i) => {
return {
questionText: q.questionText,
@@ -52,7 +54,7 @@ export default {
}
});
// add an empty item to be array[0] since we start with 1
- questions.unshift({});
+ questions.unshift({ "DeliberatelyBlankObject": "This object has been added as a placeholder only for question #0"});
return questions;
},
selectedValue: {
diff --git a/src/layouts/address-vehicles/address-vehicles-question/address-vehicles-question.spec.js b/src/layouts/address-vehicles/address-vehicles-question/address-vehicles-question.spec.js
index eaa24c9d4..d030c7c76 100644
--- a/src/layouts/address-vehicles/address-vehicles-question/address-vehicles-question.spec.js
+++ b/src/layouts/address-vehicles/address-vehicles-question/address-vehicles-question.spec.js
@@ -1,7 +1,6 @@
import { shallowMount } from "@vue/test-utils";
import addressVehiclesQuestion from "@/layouts/address-vehicles/address-vehicles-question/address-vehicles-question";
-
describe("addressVehiclesQuestion.vue", () => {
it("Should return content for differentVehicleAlertHeader", () => {
diff --git a/src/layouts/vehicle-make/vehicle-make.vue b/src/layouts/vehicle-make/vehicle-make.vue
index aecd90a6f..0ed91b649 100644
--- a/src/layouts/vehicle-make/vehicle-make.vue
+++ b/src/layouts/vehicle-make/vehicle-make.vue
@@ -7,7 +7,6 @@