193 lines
8.2 KiB
JavaScript
193 lines
8.2 KiB
JavaScript
import axios from "axios";
|
|
import analyticsMixIn from "@/mixins/analytics-mixin.js";
|
|
import baseMixin from "@/mixins/base-mixin.js";
|
|
import router from "@/router";
|
|
import store from "@/store";
|
|
|
|
import { applicationConfig } from "@/constants/application-config.js";
|
|
import { GaCategories, GaActions, GaLabels } from "@/constants/analytics";
|
|
import { getSessionKeyValue } from "@/helpers/heritage-integration/cookie-helper";
|
|
import { headerKeys } from "@/constants/header-keys";
|
|
import axiosResponseInterceptorMessages from "@/constants/axios-response-interceptor-messages.js";
|
|
import { endpoints } from "@/constants/endpoints";
|
|
import { getDeviceIdValue } from "@/helpers/heritage-integration/cookie-helper";
|
|
|
|
// Add a response interceptor for global axios error handing.
|
|
axios.interceptors.response.use(
|
|
(response) => response,
|
|
(error) => {
|
|
let rejectionError = "";
|
|
if (typeof error.response === "undefined") {
|
|
// The request was not made, could be a bad url, bad connection, or a CORS error.
|
|
rejectionError = {
|
|
response: error,
|
|
message: axiosResponseInterceptorMessages.NETWORK_ERROR,
|
|
};
|
|
} else if (error.response) {
|
|
// The request was made and the server responded with a status code
|
|
// that falls out of the range of 2xx
|
|
rejectionError = {
|
|
response: error.response,
|
|
message: axiosResponseInterceptorMessages.STATUS_CODE_ERROR,
|
|
};
|
|
} else if (error.request) {
|
|
// The request was made but no response was received
|
|
// `error.request` is an instance of XMLHttpRequest in the browser and an instance of
|
|
// http.ClientRequest in node.js
|
|
rejectionError = {
|
|
response: error.request,
|
|
message: axiosResponseInterceptorMessages.NO_RESPONSE_ERROR,
|
|
};
|
|
} else {
|
|
// Something happened in setting up the request that triggered an Error
|
|
rejectionError = {
|
|
response: error.message,
|
|
message: axiosResponseInterceptorMessages.GENERIC_ERROR,
|
|
};
|
|
}
|
|
|
|
return Promise.reject(rejectionError);
|
|
}
|
|
);
|
|
|
|
export default {
|
|
callHttpClient({
|
|
method,
|
|
endpoint,
|
|
payload,
|
|
logApiCall = false,
|
|
pageNameToLog = null,
|
|
additionalSuccessEventDataHandler,
|
|
}) {
|
|
return new Promise((resolve, reject) => {
|
|
const cfDistroUrl = applicationConfig.CONSUMER_CF_DISTRO;
|
|
const submittedOrder = baseMixin.methods.getSubmittedOrder();
|
|
const hasSubmittedOrder = baseMixin.methods.hasSubmittedOrder();
|
|
const order = hasSubmittedOrder ? submittedOrder : store.getters.order;
|
|
const payloadAndAnalyticsData = Object.assign({}, payload, { AppName: "FixMyGlass" });
|
|
const headers = {
|
|
[headerKeys.EXPERIMENT]: JSON.stringify(store.getters.experimentSettings),
|
|
[headerKeys.APPLICATION_NAME]: applicationConfig.APPLICATION_NAME,
|
|
[headerKeys.SESSION_SEQUENCE_NUMBER]: getSessionKeyValue(),
|
|
[headerKeys.REFERRAL_SEQUENCE_NUMBER]: order?.referralSequenceNumber,
|
|
[headerKeys.PAGE_NAME_TO_LOG]: pageNameToLog,
|
|
[headerKeys.TRANSACTION_ID]: crypto.randomUUID(),
|
|
[headerKeys.EON]: order?.eon,
|
|
[headerKeys.LOG_ENABLED]: store.getters.applicationUser?.loggingOption ?? false,
|
|
[headerKeys.DEVICE_ID]: getDeviceIdValue(),
|
|
};
|
|
|
|
axios({
|
|
method: method,
|
|
url: cfDistroUrl + endpoint,
|
|
data: payloadAndAnalyticsData,
|
|
crossDomain: true,
|
|
responseType: "json",
|
|
headers: headers,
|
|
}).then(
|
|
(response) => {
|
|
if (logApiCall) {
|
|
const endpointWithoutParams =
|
|
analyticsMixIn.methods.removeParamsFromEndpoint(endpoint);
|
|
const gaAction = `${pageNameToLog}_${endpointWithoutParams}`;
|
|
|
|
if (additionalSuccessEventDataHandler) {
|
|
const handlerResult = additionalSuccessEventDataHandler(response);
|
|
const additionalEntries = Array.isArray(handlerResult)
|
|
? handlerResult
|
|
: [handlerResult];
|
|
|
|
additionalEntries.forEach((entry) => {
|
|
if (entry === undefined || entry === null || entry === "") {
|
|
return;
|
|
}
|
|
|
|
analyticsMixIn.methods.pushEventToGA(
|
|
GaCategories.API_RESPONSE,
|
|
gaAction,
|
|
`${GaLabels.SUCCESS}_${entry}`,
|
|
true
|
|
);
|
|
});
|
|
} else {
|
|
analyticsMixIn.methods.pushEventToGA(
|
|
GaCategories.API_RESPONSE,
|
|
gaAction,
|
|
GaLabels.SUCCESS,
|
|
true
|
|
);
|
|
}
|
|
}
|
|
|
|
return resolve(response);
|
|
},
|
|
(error) => {
|
|
if (
|
|
endpoint.toLowerCase().includes(endpoints.LogFmgSessionData.url) ||
|
|
endpoint.toLowerCase().includes(endpoints.LogPageView.url) ||
|
|
endpoint.toLowerCase().includes(endpoints.LogCustomEvent.url) ||
|
|
endpoint.toLowerCase().includes(endpoints.LogPartQuestions.url)
|
|
) {
|
|
return resolve({ data: null, error: "Ignore errors when logging" });
|
|
} else {
|
|
if (logApiCall) {
|
|
analyticsMixIn.methods.pushEventToGA(
|
|
GaCategories.API_RESPONSE,
|
|
GaActions.RESULT,
|
|
`${GaLabels.ERROR}_${endpoint}`,
|
|
true
|
|
);
|
|
}
|
|
|
|
if (error.response.status && error.response.status != "404") {
|
|
// Do not route to error logic when no wipers found or no promo found (404s)
|
|
const errorPayload = {
|
|
cause: `Response error ${error.response.status}`,
|
|
currentPage: pageNameToLog,
|
|
endpoint: endpoint,
|
|
};
|
|
|
|
router.handleSoftError(errorPayload);
|
|
|
|
// do not log 404 errors from services because we return NotFound
|
|
// when a service doesn't return an object
|
|
global.$logger.logError(
|
|
`${method}: ${endpoint}: ${error.message}`,
|
|
error.response
|
|
);
|
|
}
|
|
|
|
return reject(error.response);
|
|
}
|
|
}
|
|
);
|
|
});
|
|
},
|
|
|
|
/* istanbul ignore next */
|
|
callMockHttpClient({ method, endpoint, payload }) {
|
|
// For Mock use only!
|
|
return new Promise((resolve, reject) => {
|
|
axios({
|
|
method: method,
|
|
url: endpoint,
|
|
crossDomain: true,
|
|
headers: {
|
|
"Content-Type": "application/x-www-form-urlencoded",
|
|
},
|
|
responseType: {},
|
|
data: payload,
|
|
}).then(
|
|
(response) => {
|
|
// simulate a delayed response
|
|
setTimeout(() => {
|
|
resolve(response);
|
|
}, 2000);
|
|
},
|
|
(error) => {
|
|
return reject(error.response);
|
|
}
|
|
);
|
|
});
|
|
},
|
|
};
|