@tsed/cli-core
Version:
Build your CLI with TypeScript and Decorators
115 lines (114 loc) • 4.24 kB
JavaScript
import { stringify } from "node:querystring";
import { URL } from "node:url";
import { cleanObject } from "@tsed/core";
import { inject, injectable } from "@tsed/di";
import axios, {} from "axios";
import { CliHttpLogClient } from "./CliHttpLogClient.js";
import { CliProxyAgent } from "./CliProxyAgent.js";
export class CliHttpClient extends CliHttpLogClient {
constructor() {
super(...arguments);
this.cliProxyAgent = inject(CliProxyAgent);
this.proxySettingsInitialized = false;
}
static getParamsSerializer(params) {
return stringify(cleanObject(params));
}
async head(endpoint, options = {}) {
const { headers } = await axios(await this.getRequestParameters("HEAD", endpoint, options));
return headers;
}
async get(endpoint, options = {}) {
const result = await this.send(await this.getRequestParameters("GET", endpoint, options));
return this.mapResponse(result, options);
}
async post(endpoint, options = {}) {
const result = await this.send(await this.getRequestParameters("POST", endpoint, options));
return this.mapResponse(result, options);
}
async put(endpoint, options = {}) {
const result = await this.send(await this.getRequestParameters("PUT", endpoint, options));
return this.mapResponse(result, options);
}
async patch(endpoint, options = {}) {
const result = await this.send(await this.getRequestParameters("PATCH", endpoint, options));
return this.mapResponse(result, options);
}
async delete(endpoint, options = {}) {
const result = await this.send(await this.getRequestParameters("DELETE", endpoint, options));
return this.mapResponse(result, options);
}
async getRequestParameters(method, endpoint, options) {
const url = (this.host || "") + endpoint.replace(this.host || "", "");
await this.resolveProxySettingsOnce();
options = {
method,
...options,
url,
params: options.params || options.qs,
data: options.data,
headers: {
"Content-Type": "application/json",
Accept: "application/json",
...(options.headers || {})
}
};
await this.configureProxy(url, options);
return options;
}
async resolveProxySettingsOnce() {
if (this.proxySettingsInitialized) {
return;
}
if (!this.proxySettingsPromise) {
this.proxySettingsPromise = this.cliProxyAgent
.resolveProxySettings()
.catch(() => {
return;
})
.finally(() => {
this.proxySettingsInitialized = true;
});
}
await this.proxySettingsPromise;
}
async configureProxy(endpoint, options) {
const url = new URL(endpoint);
if (this.cliProxyAgent.hasProxy()) {
const protocol = url.protocol.replace(":", "");
switch (protocol) {
case "https":
options.httpsAgent = await this.cliProxyAgent.get(protocol);
options.proxy = false;
break;
case "http":
options.httpAgent = await this.cliProxyAgent.get(protocol);
options.proxy = false;
break;
default:
break;
}
}
}
async send(options) {
const startTime = new Date().getTime();
try {
const response = await axios({
paramsSerializer: CliHttpClient.getParamsSerializer,
...options
});
this.onSuccess({ startTime, ...options });
return response;
}
catch (error) {
this.onError(error, { startTime, ...options });
throw error;
}
}
mapResponse(result, options) {
const { withHeaders } = options;
const data = !withHeaders ? result?.data : result;
return withHeaders ? { data, headers: result?.headers } : data;
}
}
injectable(CliHttpClient);