@sap/cli-core
Version:
Command-Line Interface (CLI) Core Module
84 lines (83 loc) • 3.41 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.create = void 0;
const config_1 = require("../../../config");
const http_1 = require("../../../utils/http");
const utils_1 = require("./utils");
const utils_2 = require("../authentication/oauth/tokenProvider/utils");
const logger_1 = require("../../../logger");
const constants_1 = require("../../../constants");
const getLogger = () => (0, logger_1.get)("commands.handler.fetch");
const removeCsrfTokenFromConfig = () => {
const config = (0, config_1.get)();
delete config[constants_1.X_CSRF_TOKEN];
};
// developer.mozilla.org/en-US/docs/Web/HTTP/Redirections
const REDIRECT_STATUS_CODES = [301, 302, 303, 307, 308];
const REDIRECT_WITHOUT_CHANGE = [307, 308];
const fetchData = async (method, path, parameterMappings, responsePostProcessor) => {
const config = (0, config_1.get)();
(0, utils_1.checkConfiguration)(config);
const conf = await (0, utils_1.buildHttpConfig)(method, path, parameterMappings);
const response = await (0, http_1.fetch)(conf);
removeCsrfTokenFromConfig();
await (0, utils_1.handleResponse)(response.data, response.headers);
if (responsePostProcessor) {
await responsePostProcessor(response);
}
};
const handle401 = async (method, path, parameterMappings) => {
const { debug, error } = getLogger();
debug("response status is 401, trying to refresh access_token");
try {
await (0, utils_2.refreshToken)(true);
await fetchData(method, path, parameterMappings);
debug("refreshing token and fetching data succeeded");
}
catch (errRefresh) {
error("refreshing token and fetching data again failed", errRefresh);
throw errRefresh;
}
};
const handleRedirect = async (error, method, redirect) => {
const location = error.response?.headers.location;
if (!location) {
throw new Error("location header is not present for redirect");
}
let newMethod = method;
if (!REDIRECT_WITHOUT_CHANGE.includes(error.response?.status)) {
newMethod = "GET";
}
await redirect(newMethod, location);
};
const handleError = async (error, method, redirect, path, parameterMappings) => {
const { error: logError } = getLogger();
logError("failed to fetch data", error);
if (error.response?.data && (0, config_1.get)().verbose) {
await (0, utils_1.handleResponseData)(error.response?.data);
}
if (error.response?.status === 401) {
await handle401(method, path, parameterMappings);
}
else if (REDIRECT_STATUS_CODES.includes(error.response?.status)) {
await handleRedirect(error, method, redirect);
}
else {
throw error;
}
};
const runRequest = (method, path, parameterMappings, responsePostProcessor) => async () => {
try {
await fetchData(method, path, parameterMappings, responsePostProcessor);
}
catch (errFetch) {
const redirect = (newMethod, location) => runRequest(newMethod, location, parameterMappings, responsePostProcessor)();
await handleError(errFetch, method, redirect, path, parameterMappings);
}
};
/* jscpd:ignore-start */
const create = (method, path, parameterMappings, responsePostProcessor) => {
/* jscpd:ignore-end */
return async () => runRequest(method, path, parameterMappings, responsePostProcessor);
};
exports.create = create;