@cat-indev/catops-cli 0.0.1-alpha.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +1254 -0
- package/dist/bin/devops-cli.d.ts +2 -0
- package/dist/bin/devops-cli.js +132 -0
- package/dist/bin/devops-cli.js.map +1 -0
- package/dist/core/Context.d.ts +56 -0
- package/dist/core/Context.js +197 -0
- package/dist/core/Context.js.map +1 -0
- package/dist/core/Menu.d.ts +23 -0
- package/dist/core/Menu.js +160 -0
- package/dist/core/Menu.js.map +1 -0
- package/dist/core/Notifier.d.ts +42 -0
- package/dist/core/Notifier.js +128 -0
- package/dist/core/Notifier.js.map +1 -0
- package/dist/core/classifiers.d.ts +45 -0
- package/dist/core/classifiers.js +90 -0
- package/dist/core/classifiers.js.map +1 -0
- package/dist/core/logger.d.ts +8 -0
- package/dist/core/logger.js +37 -0
- package/dist/core/logger.js.map +1 -0
- package/dist/core/messages.d.ts +102 -0
- package/dist/core/messages.js +163 -0
- package/dist/core/messages.js.map +1 -0
- package/dist/core/prompt.d.ts +10 -0
- package/dist/core/prompt.js +87 -0
- package/dist/core/prompt.js.map +1 -0
- package/dist/core/senders.d.ts +27 -0
- package/dist/core/senders.js +109 -0
- package/dist/core/senders.js.map +1 -0
- package/dist/core/types.d.ts +135 -0
- package/dist/core/types.js +33 -0
- package/dist/core/types.js.map +1 -0
- package/dist/index.d.ts +20 -0
- package/dist/index.js +66 -0
- package/dist/index.js.map +1 -0
- package/dist/services/ansible.d.ts +12 -0
- package/dist/services/ansible.js +35 -0
- package/dist/services/ansible.js.map +1 -0
- package/dist/services/archive.d.ts +4 -0
- package/dist/services/archive.js +16 -0
- package/dist/services/archive.js.map +1 -0
- package/dist/services/argocd.d.ts +23 -0
- package/dist/services/argocd.js +48 -0
- package/dist/services/argocd.js.map +1 -0
- package/dist/services/az.d.ts +38 -0
- package/dist/services/az.js +51 -0
- package/dist/services/az.js.map +1 -0
- package/dist/services/azdo-api.d.ts +213 -0
- package/dist/services/azdo-api.js +247 -0
- package/dist/services/azdo-api.js.map +1 -0
- package/dist/services/azdo.d.ts +13 -0
- package/dist/services/azdo.js +57 -0
- package/dist/services/azdo.js.map +1 -0
- package/dist/services/docker.d.ts +21 -0
- package/dist/services/docker.js +36 -0
- package/dist/services/docker.js.map +1 -0
- package/dist/services/git.d.ts +9 -0
- package/dist/services/git.js +36 -0
- package/dist/services/git.js.map +1 -0
- package/dist/services/helm.d.ts +4 -0
- package/dist/services/helm.js +24 -0
- package/dist/services/helm.js.map +1 -0
- package/dist/services/http-types.d.ts +57 -0
- package/dist/services/http-types.js +3 -0
- package/dist/services/http-types.js.map +1 -0
- package/dist/services/http.d.ts +64 -0
- package/dist/services/http.js +288 -0
- package/dist/services/http.js.map +1 -0
- package/dist/services/index.d.ts +37 -0
- package/dist/services/index.js +88 -0
- package/dist/services/index.js.map +1 -0
- package/dist/services/kubectl.d.ts +137 -0
- package/dist/services/kubectl.js +271 -0
- package/dist/services/kubectl.js.map +1 -0
- package/dist/services/npm.d.ts +5 -0
- package/dist/services/npm.js +20 -0
- package/dist/services/npm.js.map +1 -0
- package/dist/services/oc.d.ts +156 -0
- package/dist/services/oc.js +309 -0
- package/dist/services/oc.js.map +1 -0
- package/dist/services/pipeline.d.ts +116 -0
- package/dist/services/pipeline.js +474 -0
- package/dist/services/pipeline.js.map +1 -0
- package/dist/services/shell.d.ts +28 -0
- package/dist/services/shell.js +206 -0
- package/dist/services/shell.js.map +1 -0
- package/dist/services/tekton.d.ts +16 -0
- package/dist/services/tekton.js +46 -0
- package/dist/services/tekton.js.map +1 -0
- package/dist/services/terraform.d.ts +31 -0
- package/dist/services/terraform.js +63 -0
- package/dist/services/terraform.js.map +1 -0
- package/package.json +58 -0
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
import type { ExecOptions, ExecResult } from "../core/types";
|
|
2
|
+
export interface OcOptions {
|
|
3
|
+
/** Ruta al archivo kubeconfig. Se pasa como --kubeconfig <path>. */
|
|
4
|
+
kubeconfig?: string;
|
|
5
|
+
/** Namespace/proyecto destino. Se pasa como -n <namespace>. */
|
|
6
|
+
namespace?: string;
|
|
7
|
+
/** retry/timeout/dryRun para esta llamada puntual (ver shell.exec). */
|
|
8
|
+
exec?: ExecOptions;
|
|
9
|
+
}
|
|
10
|
+
export interface OcLoginOptions extends OcOptions {
|
|
11
|
+
server: string;
|
|
12
|
+
token?: string;
|
|
13
|
+
username?: string;
|
|
14
|
+
password?: string;
|
|
15
|
+
insecureSkipTlsVerify?: boolean;
|
|
16
|
+
}
|
|
17
|
+
export interface OcStartBuildOptions extends OcOptions {
|
|
18
|
+
follow?: boolean;
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Ejemplo — 10 reintentos ante un login inestable:
|
|
22
|
+
* await ctx.services.oc.login({
|
|
23
|
+
* server: "https://api.cluster:6443",
|
|
24
|
+
* token: process.env.OC_TOKEN,
|
|
25
|
+
* exec: { retry: 10, retryDelay: 2000 }
|
|
26
|
+
* });
|
|
27
|
+
*/
|
|
28
|
+
export declare function login({ server, token, username, password, insecureSkipTlsVerify, ...options }: OcLoginOptions): Promise<ExecResult>;
|
|
29
|
+
export declare function project(name: string, options?: OcOptions): Promise<ExecResult>;
|
|
30
|
+
export declare function apply(file: string, options?: OcOptions): Promise<ExecResult>;
|
|
31
|
+
/**
|
|
32
|
+
* Igual que antes (`oc.get("pods", "-o", "wide")`), pero ahora también
|
|
33
|
+
* acepta OcOptions como último argumento:
|
|
34
|
+
* oc.get("pods", "-o", "wide", { namespace: "prod", exec: { retry: 3 } })
|
|
35
|
+
*/
|
|
36
|
+
export declare function get(...rawArgs: Array<string | OcOptions>): Promise<ExecResult>;
|
|
37
|
+
export declare function rollout(deployment: string, options?: OcOptions): Promise<ExecResult>;
|
|
38
|
+
export declare function newApp(...args: string[]): Promise<ExecResult>;
|
|
39
|
+
export declare function startBuild(buildConfig: string, { follow, ...options }?: OcStartBuildOptions): Promise<ExecResult>;
|
|
40
|
+
export declare function logs(pod: string, options?: OcOptions): Promise<ExecResult>;
|
|
41
|
+
export type DeploymentRolloutStatus = "success" | "failed" | "timeout";
|
|
42
|
+
export interface DeploymentWatchResult {
|
|
43
|
+
status: DeploymentRolloutStatus;
|
|
44
|
+
deployment: string;
|
|
45
|
+
elapsedMs: number;
|
|
46
|
+
restarts: number;
|
|
47
|
+
message: string;
|
|
48
|
+
}
|
|
49
|
+
/**
|
|
50
|
+
* Se lanza cuando `waitForDeployment` no llega a un rollout exitoso. Lleva
|
|
51
|
+
* `command: "oc"` para que `classifiers.byCommand({ oc: "kubernetes" })`
|
|
52
|
+
* lo clasifique automáticamente si usas el sistema de notificaciones.
|
|
53
|
+
*/
|
|
54
|
+
export declare class DeploymentRolloutError extends Error {
|
|
55
|
+
readonly command = "oc";
|
|
56
|
+
readonly status: DeploymentRolloutStatus;
|
|
57
|
+
readonly deployment: string;
|
|
58
|
+
readonly elapsedMs: number;
|
|
59
|
+
readonly restarts: number;
|
|
60
|
+
constructor(message: string, info: Omit<DeploymentWatchResult, "message">);
|
|
61
|
+
}
|
|
62
|
+
export interface WaitForDeploymentOptions extends OcOptions {
|
|
63
|
+
/** Nombre del deployment/deploymentconfig, sin prefijo de recurso. */
|
|
64
|
+
deployment: string;
|
|
65
|
+
/** "deployment" (k8s nativo, default) o "dc" (DeploymentConfig clásico de OpenShift). */
|
|
66
|
+
resourceType?: "deployment" | "dc";
|
|
67
|
+
/** Milisegundos totales antes de abortar y reportar error. Default: 300000 (5 min). */
|
|
68
|
+
timeout?: number;
|
|
69
|
+
/** Milisegundos entre cada chequeo. Default: 5000. */
|
|
70
|
+
pollInterval?: number;
|
|
71
|
+
/**
|
|
72
|
+
* Si el recurso entra en estado Failed, milisegundos a esperar para ver
|
|
73
|
+
* si se recupera solo antes de darlo por fallido. Default: `pollInterval * 6`.
|
|
74
|
+
*/
|
|
75
|
+
failedGracePeriod?: number;
|
|
76
|
+
/**
|
|
77
|
+
* Máximo de reinicios (sumados entre todos los pods/containers) tolerados
|
|
78
|
+
* antes de abortar inmediatamente. Si no se pasa, no se valida.
|
|
79
|
+
*/
|
|
80
|
+
maxRestarts?: number;
|
|
81
|
+
}
|
|
82
|
+
/**
|
|
83
|
+
* Valida cíclicamente el estado de un Deployment/DeploymentConfig hasta que:
|
|
84
|
+
* - llega a estado exitoso (replicas listas/actualizadas == replicas deseadas) -> resuelve,
|
|
85
|
+
* - supera `maxRestarts` reinicios acumulados -> lanza DeploymentRolloutError,
|
|
86
|
+
* - se queda en estado Failed más de `failedGracePeriod` sin recuperarse -> lanza DeploymentRolloutError,
|
|
87
|
+
* - o se cumple `timeout` sin éxito -> lanza DeploymentRolloutError.
|
|
88
|
+
*
|
|
89
|
+
* El polling se detiene ("se mata el proceso") apenas se detecta cualquiera
|
|
90
|
+
* de las condiciones de fallo, re-lanzando el error para que `ctx.run(...)`
|
|
91
|
+
* lo capture y lo reporte vía `ctx.notifier` si lo tienes configurado.
|
|
92
|
+
*/
|
|
93
|
+
export declare function waitForDeployment(options: WaitForDeploymentOptions): Promise<DeploymentWatchResult>;
|
|
94
|
+
export type DeploymentGroupStatus = "success" | "failed" | "timeout";
|
|
95
|
+
export interface DeploymentGroupFailure {
|
|
96
|
+
deployment: string;
|
|
97
|
+
status: DeploymentRolloutStatus;
|
|
98
|
+
message: string;
|
|
99
|
+
}
|
|
100
|
+
export interface DeploymentGroupWatchResult {
|
|
101
|
+
status: "success";
|
|
102
|
+
label: string;
|
|
103
|
+
elapsedMs: number;
|
|
104
|
+
deployments: DeploymentWatchResult[];
|
|
105
|
+
message: string;
|
|
106
|
+
}
|
|
107
|
+
/**
|
|
108
|
+
* Se lanza cuando `waitForDeploymentGroup` no logra que TODAS las instancias
|
|
109
|
+
* del grupo lleguen a estado exitoso. Lleva `command: "oc"` para que
|
|
110
|
+
* `classifiers.byCommand({ oc: "kubernetes" })` lo clasifique solo.
|
|
111
|
+
*/
|
|
112
|
+
export declare class DeploymentGroupRolloutError extends Error {
|
|
113
|
+
readonly command = "oc";
|
|
114
|
+
readonly label: string;
|
|
115
|
+
readonly elapsedMs: number;
|
|
116
|
+
readonly succeeded: string[];
|
|
117
|
+
readonly failed: DeploymentGroupFailure[];
|
|
118
|
+
constructor(message: string, info: {
|
|
119
|
+
label: string;
|
|
120
|
+
elapsedMs: number;
|
|
121
|
+
succeeded: string[];
|
|
122
|
+
failed: DeploymentGroupFailure[];
|
|
123
|
+
});
|
|
124
|
+
}
|
|
125
|
+
export interface WaitForDeploymentGroupOptions extends OcOptions {
|
|
126
|
+
/**
|
|
127
|
+
* Label que agrupa todas las instancias del despliegue. Puede ser el
|
|
128
|
+
* selector ya armado ("deployment-group=repository-14") o un objeto
|
|
129
|
+
* ({ "deployment-group": "repository-14" }).
|
|
130
|
+
*/
|
|
131
|
+
label: string | Record<string, string>;
|
|
132
|
+
/** "deployment" (k8s nativo, default) o "dc" (DeploymentConfig clásico de OpenShift). */
|
|
133
|
+
resourceType?: "deployment" | "dc";
|
|
134
|
+
/** Milisegundos totales antes de abortar el grupo entero. Default: 300000 (5 min). */
|
|
135
|
+
timeout?: number;
|
|
136
|
+
/** Milisegundos entre cada chequeo, por instancia. Default: 5000. */
|
|
137
|
+
pollInterval?: number;
|
|
138
|
+
/** Igual que en waitForDeployment, aplicado a cada instancia del grupo. */
|
|
139
|
+
failedGracePeriod?: number;
|
|
140
|
+
/** Igual que en waitForDeployment, aplicado a cada instancia del grupo. */
|
|
141
|
+
maxRestarts?: number;
|
|
142
|
+
}
|
|
143
|
+
/**
|
|
144
|
+
* Descubre todos los Deployments/DeploymentConfigs que compartan el `label`
|
|
145
|
+
* dado (p. ej. todas las instancias GitOps de un mismo repo, marcadas con
|
|
146
|
+
* `deployment-group: repository-14`) y espera a que TODAS lleguen a estado
|
|
147
|
+
* exitoso, corriendo `waitForDeployment` por cada una en paralelo con el
|
|
148
|
+
* mismo `timeout` global.
|
|
149
|
+
*
|
|
150
|
+
* Si alguna instancia falla (timeout individual, Failed sin recuperarse, o
|
|
151
|
+
* maxRestarts superado), se espera a que terminen las demás y se lanza
|
|
152
|
+
* `DeploymentGroupRolloutError` con el detalle de cuáles fallaron y cuáles sí
|
|
153
|
+
* llegaron a estado exitoso — listo para que `ctx.run(...)` lo capture y lo
|
|
154
|
+
* reporte vía `ctx.notifier`.
|
|
155
|
+
*/
|
|
156
|
+
export declare function waitForDeploymentGroup(options: WaitForDeploymentGroupOptions): Promise<DeploymentGroupWatchResult>;
|
|
@@ -0,0 +1,309 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.DeploymentGroupRolloutError = exports.DeploymentRolloutError = void 0;
|
|
4
|
+
exports.login = login;
|
|
5
|
+
exports.project = project;
|
|
6
|
+
exports.apply = apply;
|
|
7
|
+
exports.get = get;
|
|
8
|
+
exports.rollout = rollout;
|
|
9
|
+
exports.newApp = newApp;
|
|
10
|
+
exports.startBuild = startBuild;
|
|
11
|
+
exports.logs = logs;
|
|
12
|
+
exports.waitForDeployment = waitForDeployment;
|
|
13
|
+
exports.waitForDeploymentGroup = waitForDeploymentGroup;
|
|
14
|
+
const shell_1 = require("./shell");
|
|
15
|
+
function isOcOptions(value) {
|
|
16
|
+
return Boolean(value)
|
|
17
|
+
&& typeof value === "object"
|
|
18
|
+
&& !Array.isArray(value)
|
|
19
|
+
&& ("kubeconfig" in value || "namespace" in value || "exec" in value || Object.keys(value).length === 0);
|
|
20
|
+
}
|
|
21
|
+
function withGlobalFlags(args, options = {}) {
|
|
22
|
+
const result = [...args];
|
|
23
|
+
if (options.kubeconfig) {
|
|
24
|
+
result.push("--kubeconfig", options.kubeconfig);
|
|
25
|
+
}
|
|
26
|
+
if (options.namespace) {
|
|
27
|
+
result.push("-n", options.namespace);
|
|
28
|
+
}
|
|
29
|
+
return result;
|
|
30
|
+
}
|
|
31
|
+
/** Arma los args finales para shell.exec: flags (--kubeconfig/-n) + el objeto exec al final, si se pasó. */
|
|
32
|
+
function toExecArgs(args, options = {}) {
|
|
33
|
+
const withFlags = withGlobalFlags(args, options);
|
|
34
|
+
return options.exec ? [...withFlags, options.exec] : withFlags;
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Ejemplo — 10 reintentos ante un login inestable:
|
|
38
|
+
* await ctx.services.oc.login({
|
|
39
|
+
* server: "https://api.cluster:6443",
|
|
40
|
+
* token: process.env.OC_TOKEN,
|
|
41
|
+
* exec: { retry: 10, retryDelay: 2000 }
|
|
42
|
+
* });
|
|
43
|
+
*/
|
|
44
|
+
function login({ server, token, username, password, insecureSkipTlsVerify = false, ...options }) {
|
|
45
|
+
const args = ["login", server];
|
|
46
|
+
if (token) {
|
|
47
|
+
args.push("--token", token);
|
|
48
|
+
}
|
|
49
|
+
else {
|
|
50
|
+
args.push("-u", username ?? "", "-p", password ?? "");
|
|
51
|
+
}
|
|
52
|
+
if (insecureSkipTlsVerify) {
|
|
53
|
+
args.push("--insecure-skip-tls-verify");
|
|
54
|
+
}
|
|
55
|
+
return shell_1.shell.exec("oc", ...toExecArgs(args, options));
|
|
56
|
+
}
|
|
57
|
+
function project(name, options = {}) {
|
|
58
|
+
return shell_1.shell.exec("oc", ...toExecArgs(["project", name], options));
|
|
59
|
+
}
|
|
60
|
+
function apply(file, options = {}) {
|
|
61
|
+
return shell_1.shell.exec("oc", ...toExecArgs(["apply", "-f", file], options));
|
|
62
|
+
}
|
|
63
|
+
/**
|
|
64
|
+
* Igual que antes (`oc.get("pods", "-o", "wide")`), pero ahora también
|
|
65
|
+
* acepta OcOptions como último argumento:
|
|
66
|
+
* oc.get("pods", "-o", "wide", { namespace: "prod", exec: { retry: 3 } })
|
|
67
|
+
*/
|
|
68
|
+
function get(...rawArgs) {
|
|
69
|
+
let args = rawArgs;
|
|
70
|
+
let options = {};
|
|
71
|
+
const last = rawArgs[rawArgs.length - 1];
|
|
72
|
+
if (rawArgs.length && isOcOptions(last)) {
|
|
73
|
+
options = last;
|
|
74
|
+
args = rawArgs.slice(0, -1);
|
|
75
|
+
}
|
|
76
|
+
return shell_1.shell.exec("oc", "get", ...toExecArgs(args, options));
|
|
77
|
+
}
|
|
78
|
+
function rollout(deployment, options = {}) {
|
|
79
|
+
return shell_1.shell.exec("oc", ...toExecArgs(["rollout", "status", `dc/${deployment}`], options));
|
|
80
|
+
}
|
|
81
|
+
function newApp(...args) {
|
|
82
|
+
return shell_1.shell.exec("oc", "new-app", ...args);
|
|
83
|
+
}
|
|
84
|
+
function startBuild(buildConfig, { follow = true, ...options } = {}) {
|
|
85
|
+
const args = ["start-build", buildConfig];
|
|
86
|
+
if (follow) {
|
|
87
|
+
args.push("-F");
|
|
88
|
+
}
|
|
89
|
+
return shell_1.shell.exec("oc", ...toExecArgs(args, options));
|
|
90
|
+
}
|
|
91
|
+
function logs(pod, options = {}) {
|
|
92
|
+
return shell_1.shell.exec("oc", ...toExecArgs(["logs", pod], options));
|
|
93
|
+
}
|
|
94
|
+
// ---------------------------------------------------------------------------
|
|
95
|
+
// waitForDeployment — validación cíclica del rollout, para Deployment (k8s
|
|
96
|
+
// nativo) o DeploymentConfig (OpenShift clásico).
|
|
97
|
+
// ---------------------------------------------------------------------------
|
|
98
|
+
function sleep(ms) {
|
|
99
|
+
return new Promise(resolve => setTimeout(resolve, ms));
|
|
100
|
+
}
|
|
101
|
+
/**
|
|
102
|
+
* Se lanza cuando `waitForDeployment` no llega a un rollout exitoso. Lleva
|
|
103
|
+
* `command: "oc"` para que `classifiers.byCommand({ oc: "kubernetes" })`
|
|
104
|
+
* lo clasifique automáticamente si usas el sistema de notificaciones.
|
|
105
|
+
*/
|
|
106
|
+
class DeploymentRolloutError extends Error {
|
|
107
|
+
constructor(message, info) {
|
|
108
|
+
super(message);
|
|
109
|
+
this.command = "oc";
|
|
110
|
+
this.name = "DeploymentRolloutError";
|
|
111
|
+
this.status = info.status;
|
|
112
|
+
this.deployment = info.deployment;
|
|
113
|
+
this.elapsedMs = info.elapsedMs;
|
|
114
|
+
this.restarts = info.restarts;
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
exports.DeploymentRolloutError = DeploymentRolloutError;
|
|
118
|
+
function matchLabelsOf(selector) {
|
|
119
|
+
if (!selector)
|
|
120
|
+
return undefined;
|
|
121
|
+
if ("matchLabels" in selector) {
|
|
122
|
+
return selector.matchLabels;
|
|
123
|
+
}
|
|
124
|
+
return selector;
|
|
125
|
+
}
|
|
126
|
+
async function readWorkloadJSON(resourceType, name, options) {
|
|
127
|
+
const result = await get(`${resourceType}/${name}`, "-o", "json", options);
|
|
128
|
+
return JSON.parse(result.stdout);
|
|
129
|
+
}
|
|
130
|
+
async function countPodRestarts(matchLabels, options) {
|
|
131
|
+
if (!matchLabels || !Object.keys(matchLabels).length) {
|
|
132
|
+
return 0;
|
|
133
|
+
}
|
|
134
|
+
const selector = Object.entries(matchLabels)
|
|
135
|
+
.map(([key, value]) => `${key}=${value}`)
|
|
136
|
+
.join(",");
|
|
137
|
+
const result = await get("pods", "-l", selector, "-o", "json", options);
|
|
138
|
+
const parsed = JSON.parse(result.stdout);
|
|
139
|
+
return (parsed.items ?? []).reduce((total, pod) => {
|
|
140
|
+
const podRestarts = (pod.status?.containerStatuses ?? [])
|
|
141
|
+
.reduce((sum, container) => sum + (container.restartCount ?? 0), 0);
|
|
142
|
+
return total + podRestarts;
|
|
143
|
+
}, 0);
|
|
144
|
+
}
|
|
145
|
+
function isProgressingFailed(conditions) {
|
|
146
|
+
const progressing = conditions.find(c => c.type === "Progressing");
|
|
147
|
+
if (progressing?.status === "False")
|
|
148
|
+
return true;
|
|
149
|
+
return conditions.some(c => c.type === "ReplicaFailure" && c.status === "True");
|
|
150
|
+
}
|
|
151
|
+
/**
|
|
152
|
+
* Valida cíclicamente el estado de un Deployment/DeploymentConfig hasta que:
|
|
153
|
+
* - llega a estado exitoso (replicas listas/actualizadas == replicas deseadas) -> resuelve,
|
|
154
|
+
* - supera `maxRestarts` reinicios acumulados -> lanza DeploymentRolloutError,
|
|
155
|
+
* - se queda en estado Failed más de `failedGracePeriod` sin recuperarse -> lanza DeploymentRolloutError,
|
|
156
|
+
* - o se cumple `timeout` sin éxito -> lanza DeploymentRolloutError.
|
|
157
|
+
*
|
|
158
|
+
* El polling se detiene ("se mata el proceso") apenas se detecta cualquiera
|
|
159
|
+
* de las condiciones de fallo, re-lanzando el error para que `ctx.run(...)`
|
|
160
|
+
* lo capture y lo reporte vía `ctx.notifier` si lo tienes configurado.
|
|
161
|
+
*/
|
|
162
|
+
async function waitForDeployment(options) {
|
|
163
|
+
const { deployment, resourceType = "deployment", timeout = 300000, pollInterval = 5000, failedGracePeriod = pollInterval * 6, maxRestarts, ...ocOptions } = options;
|
|
164
|
+
const startedAt = Date.now();
|
|
165
|
+
let failedSince = null;
|
|
166
|
+
while (true) {
|
|
167
|
+
const elapsedMs = Date.now() - startedAt;
|
|
168
|
+
if (elapsedMs >= timeout) {
|
|
169
|
+
const message = `Timeout esperando el rollout de "${deployment}" (${timeout}ms)`;
|
|
170
|
+
throw new DeploymentRolloutError(message, { status: "timeout", deployment, elapsedMs, restarts: -1 });
|
|
171
|
+
}
|
|
172
|
+
let json;
|
|
173
|
+
try {
|
|
174
|
+
json = await readWorkloadJSON(resourceType, deployment, ocOptions);
|
|
175
|
+
}
|
|
176
|
+
catch {
|
|
177
|
+
// El recurso puede no existir todavía (justo después de un apply); reintenta.
|
|
178
|
+
await sleep(pollInterval);
|
|
179
|
+
continue;
|
|
180
|
+
}
|
|
181
|
+
const desired = json.spec?.replicas ?? 1;
|
|
182
|
+
const ready = json.status?.readyReplicas ?? json.status?.availableReplicas ?? 0;
|
|
183
|
+
const updated = json.status?.updatedReplicas ?? 0;
|
|
184
|
+
const conditions = json.status?.conditions ?? [];
|
|
185
|
+
const failed = isProgressingFailed(conditions);
|
|
186
|
+
const success = !failed && ready >= desired && updated >= desired;
|
|
187
|
+
let restarts = 0;
|
|
188
|
+
if (maxRestarts !== undefined) {
|
|
189
|
+
restarts = await countPodRestarts(matchLabelsOf(json.spec?.selector), ocOptions);
|
|
190
|
+
if (restarts > maxRestarts) {
|
|
191
|
+
const message = `"${deployment}" superó el máximo de reinicios permitido (${restarts} > ${maxRestarts})`;
|
|
192
|
+
throw new DeploymentRolloutError(message, { status: "failed", deployment, elapsedMs, restarts });
|
|
193
|
+
}
|
|
194
|
+
}
|
|
195
|
+
if (success) {
|
|
196
|
+
const message = `"${deployment}" alcanzó el estado esperado (${ready}/${desired} listas)`;
|
|
197
|
+
return { status: "success", deployment, elapsedMs, restarts, message };
|
|
198
|
+
}
|
|
199
|
+
if (failed) {
|
|
200
|
+
if (failedSince === null) {
|
|
201
|
+
failedSince = Date.now();
|
|
202
|
+
}
|
|
203
|
+
else if (Date.now() - failedSince >= failedGracePeriod) {
|
|
204
|
+
const message = `"${deployment}" quedó en estado Failed y no se recuperó en ${failedGracePeriod}ms`;
|
|
205
|
+
throw new DeploymentRolloutError(message, { status: "failed", deployment, elapsedMs, restarts });
|
|
206
|
+
}
|
|
207
|
+
}
|
|
208
|
+
else {
|
|
209
|
+
failedSince = null;
|
|
210
|
+
}
|
|
211
|
+
await sleep(pollInterval);
|
|
212
|
+
}
|
|
213
|
+
}
|
|
214
|
+
/**
|
|
215
|
+
* Se lanza cuando `waitForDeploymentGroup` no logra que TODAS las instancias
|
|
216
|
+
* del grupo lleguen a estado exitoso. Lleva `command: "oc"` para que
|
|
217
|
+
* `classifiers.byCommand({ oc: "kubernetes" })` lo clasifique solo.
|
|
218
|
+
*/
|
|
219
|
+
class DeploymentGroupRolloutError extends Error {
|
|
220
|
+
constructor(message, info) {
|
|
221
|
+
super(message);
|
|
222
|
+
this.command = "oc";
|
|
223
|
+
this.name = "DeploymentGroupRolloutError";
|
|
224
|
+
this.label = info.label;
|
|
225
|
+
this.elapsedMs = info.elapsedMs;
|
|
226
|
+
this.succeeded = info.succeeded;
|
|
227
|
+
this.failed = info.failed;
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
exports.DeploymentGroupRolloutError = DeploymentGroupRolloutError;
|
|
231
|
+
function toSelectorString(label) {
|
|
232
|
+
if (typeof label === "string")
|
|
233
|
+
return label;
|
|
234
|
+
return Object.entries(label)
|
|
235
|
+
.map(([key, value]) => `${key}=${value}`)
|
|
236
|
+
.join(",");
|
|
237
|
+
}
|
|
238
|
+
async function listWorkloadNames(resourceType, selector, options) {
|
|
239
|
+
const listCommand = resourceType === "dc" ? "dc" : "deployments";
|
|
240
|
+
const result = await get(listCommand, "-l", selector, "-o", "json", options);
|
|
241
|
+
const parsed = JSON.parse(result.stdout);
|
|
242
|
+
return (parsed.items ?? [])
|
|
243
|
+
.map(item => item.metadata?.name)
|
|
244
|
+
.filter((name) => Boolean(name));
|
|
245
|
+
}
|
|
246
|
+
/**
|
|
247
|
+
* Descubre todos los Deployments/DeploymentConfigs que compartan el `label`
|
|
248
|
+
* dado (p. ej. todas las instancias GitOps de un mismo repo, marcadas con
|
|
249
|
+
* `deployment-group: repository-14`) y espera a que TODAS lleguen a estado
|
|
250
|
+
* exitoso, corriendo `waitForDeployment` por cada una en paralelo con el
|
|
251
|
+
* mismo `timeout` global.
|
|
252
|
+
*
|
|
253
|
+
* Si alguna instancia falla (timeout individual, Failed sin recuperarse, o
|
|
254
|
+
* maxRestarts superado), se espera a que terminen las demás y se lanza
|
|
255
|
+
* `DeploymentGroupRolloutError` con el detalle de cuáles fallaron y cuáles sí
|
|
256
|
+
* llegaron a estado exitoso — listo para que `ctx.run(...)` lo capture y lo
|
|
257
|
+
* reporte vía `ctx.notifier`.
|
|
258
|
+
*/
|
|
259
|
+
async function waitForDeploymentGroup(options) {
|
|
260
|
+
const { label, resourceType = "deployment", timeout = 300000, pollInterval = 5000, failedGracePeriod = pollInterval * 6, maxRestarts, ...ocOptions } = options;
|
|
261
|
+
const selector = toSelectorString(label);
|
|
262
|
+
const startedAt = Date.now();
|
|
263
|
+
const names = await listWorkloadNames(resourceType, selector, ocOptions);
|
|
264
|
+
if (!names.length) {
|
|
265
|
+
const message = `No se encontraron ${resourceType === "dc" ? "deploymentconfigs" : "deployments"} con el label "${selector}"`;
|
|
266
|
+
throw new DeploymentGroupRolloutError(message, {
|
|
267
|
+
label: selector,
|
|
268
|
+
elapsedMs: Date.now() - startedAt,
|
|
269
|
+
succeeded: [],
|
|
270
|
+
failed: []
|
|
271
|
+
});
|
|
272
|
+
}
|
|
273
|
+
const remainingMs = () => Math.max(0, timeout - (Date.now() - startedAt));
|
|
274
|
+
const settled = await Promise.allSettled(names.map(deployment => waitForDeployment({
|
|
275
|
+
deployment,
|
|
276
|
+
resourceType,
|
|
277
|
+
timeout: remainingMs(),
|
|
278
|
+
pollInterval,
|
|
279
|
+
failedGracePeriod,
|
|
280
|
+
maxRestarts,
|
|
281
|
+
...ocOptions
|
|
282
|
+
})));
|
|
283
|
+
const succeeded = [];
|
|
284
|
+
const failed = [];
|
|
285
|
+
const deployments = [];
|
|
286
|
+
settled.forEach((outcome, index) => {
|
|
287
|
+
const name = names[index];
|
|
288
|
+
if (outcome.status === "fulfilled") {
|
|
289
|
+
succeeded.push(name);
|
|
290
|
+
deployments.push(outcome.value);
|
|
291
|
+
return;
|
|
292
|
+
}
|
|
293
|
+
const reason = outcome.reason;
|
|
294
|
+
failed.push({
|
|
295
|
+
deployment: name,
|
|
296
|
+
status: reason?.status ?? "failed",
|
|
297
|
+
message: reason?.message ?? String(outcome.reason)
|
|
298
|
+
});
|
|
299
|
+
});
|
|
300
|
+
const elapsedMs = Date.now() - startedAt;
|
|
301
|
+
if (failed.length) {
|
|
302
|
+
const summary = failed.map(f => `${f.deployment} (${f.status})`).join(", ");
|
|
303
|
+
const message = `${failed.length}/${names.length} instancias del grupo "${selector}" no llegaron a estado exitoso: ${summary}`;
|
|
304
|
+
throw new DeploymentGroupRolloutError(message, { label: selector, elapsedMs, succeeded, failed });
|
|
305
|
+
}
|
|
306
|
+
const message = `Las ${names.length} instancias del grupo "${selector}" alcanzaron el estado esperado`;
|
|
307
|
+
return { status: "success", label: selector, elapsedMs, deployments, message };
|
|
308
|
+
}
|
|
309
|
+
//# sourceMappingURL=oc.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"oc.js","sourceRoot":"","sources":["../../src/services/oc.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
import type { Context } from "../core/Context";
|
|
2
|
+
export type PipelineEntityStatus = "pending" | "running" | "success" | "failed" | "skipped";
|
|
3
|
+
export interface PipelineTaskBase {
|
|
4
|
+
depends?: string[];
|
|
5
|
+
metadata?: Record<string, unknown>;
|
|
6
|
+
}
|
|
7
|
+
export interface CallbackTaskConfig extends PipelineTaskBase {
|
|
8
|
+
exec: (ctx: Context, results: Record<string, unknown>) => unknown | Promise<unknown>;
|
|
9
|
+
}
|
|
10
|
+
export type PipelineTaskConfig = CallbackTaskConfig;
|
|
11
|
+
export interface PipelineJobConfig {
|
|
12
|
+
tasks?: Record<string, PipelineTaskConfig>;
|
|
13
|
+
depends?: string[];
|
|
14
|
+
metadata?: Record<string, unknown>;
|
|
15
|
+
}
|
|
16
|
+
export interface PipelineStageConfig {
|
|
17
|
+
jobs?: Record<string, PipelineJobConfig>;
|
|
18
|
+
depends?: string[];
|
|
19
|
+
metadata?: Record<string, unknown>;
|
|
20
|
+
}
|
|
21
|
+
export interface PipelineConfig {
|
|
22
|
+
stages?: Record<string, PipelineStageConfig>;
|
|
23
|
+
jobs?: Record<string, PipelineJobConfig>;
|
|
24
|
+
tasks?: Record<string, PipelineTaskConfig>;
|
|
25
|
+
metadata?: Record<string, unknown>;
|
|
26
|
+
ctx?: Context;
|
|
27
|
+
}
|
|
28
|
+
export interface PipelineRunResult {
|
|
29
|
+
status: "success" | "failed";
|
|
30
|
+
results: Record<string, unknown>;
|
|
31
|
+
error?: unknown;
|
|
32
|
+
duration: number;
|
|
33
|
+
}
|
|
34
|
+
export declare class PipelineResultsAccessor {
|
|
35
|
+
private readonly _pipelineResults;
|
|
36
|
+
private readonly _stageName;
|
|
37
|
+
private readonly _jobName;
|
|
38
|
+
constructor(pipelineResults: Record<string, unknown>, stageName: string, jobName: string);
|
|
39
|
+
resolve(name: string): unknown;
|
|
40
|
+
toProxy(): Record<string, unknown>;
|
|
41
|
+
}
|
|
42
|
+
export declare class PipelineTask {
|
|
43
|
+
readonly name: string;
|
|
44
|
+
readonly config: PipelineTaskConfig;
|
|
45
|
+
readonly depends: string[];
|
|
46
|
+
readonly metadata: Record<string, unknown>;
|
|
47
|
+
status: PipelineEntityStatus;
|
|
48
|
+
result: unknown;
|
|
49
|
+
error: unknown;
|
|
50
|
+
duration: number;
|
|
51
|
+
constructor(name: string, config: PipelineTaskConfig);
|
|
52
|
+
run(ctx: Context, resultsAccessor: Record<string, unknown>, stageName: string, jobName: string): Promise<void>;
|
|
53
|
+
private _execute;
|
|
54
|
+
reset(): void;
|
|
55
|
+
}
|
|
56
|
+
export declare class PipelineJob {
|
|
57
|
+
readonly name: string;
|
|
58
|
+
readonly tasks: Map<string, PipelineTask>;
|
|
59
|
+
readonly depends: string[];
|
|
60
|
+
readonly metadata: Record<string, unknown>;
|
|
61
|
+
status: PipelineEntityStatus;
|
|
62
|
+
results: Record<string, unknown>;
|
|
63
|
+
error: unknown;
|
|
64
|
+
duration: number;
|
|
65
|
+
constructor(name: string, config?: PipelineJobConfig);
|
|
66
|
+
task(nameOrConfig: string | PipelineTaskConfig, config?: PipelineTaskConfig): this;
|
|
67
|
+
getTask(name: string): PipelineTask | undefined;
|
|
68
|
+
getResults(): Record<string, unknown>;
|
|
69
|
+
run(ctx: Context, pipelineResults: Record<string, unknown>, stageName: string): Promise<void>;
|
|
70
|
+
reset(): void;
|
|
71
|
+
}
|
|
72
|
+
export declare class PipelineStage {
|
|
73
|
+
readonly name: string;
|
|
74
|
+
readonly jobs: Map<string, PipelineJob>;
|
|
75
|
+
readonly depends: string[];
|
|
76
|
+
readonly metadata: Record<string, unknown>;
|
|
77
|
+
status: PipelineEntityStatus;
|
|
78
|
+
results: Record<string, unknown>;
|
|
79
|
+
error: unknown;
|
|
80
|
+
duration: number;
|
|
81
|
+
constructor(name: string, config?: PipelineStageConfig);
|
|
82
|
+
job(nameOrConfig: string | PipelineJobConfig, config?: PipelineJobConfig): PipelineJob;
|
|
83
|
+
getJob(name: string): PipelineJob | undefined;
|
|
84
|
+
getResults(): Record<string, unknown>;
|
|
85
|
+
run(ctx: Context, pipelineResults: Record<string, unknown>): Promise<void>;
|
|
86
|
+
reset(): void;
|
|
87
|
+
}
|
|
88
|
+
export declare class Pipeline {
|
|
89
|
+
readonly name: string;
|
|
90
|
+
readonly stages: Map<string, PipelineStage>;
|
|
91
|
+
readonly metadata: Record<string, unknown>;
|
|
92
|
+
private ctx?;
|
|
93
|
+
private _results;
|
|
94
|
+
private _status;
|
|
95
|
+
private _error;
|
|
96
|
+
private _duration;
|
|
97
|
+
constructor(name: string, config?: PipelineConfig);
|
|
98
|
+
get status(): PipelineEntityStatus;
|
|
99
|
+
get results(): Record<string, unknown>;
|
|
100
|
+
get error(): unknown;
|
|
101
|
+
get duration(): number;
|
|
102
|
+
setContext(ctx: Context): this;
|
|
103
|
+
stage(nameOrConfig: string | PipelineStageConfig, config?: PipelineStageConfig): PipelineStage;
|
|
104
|
+
getStage(name: string): PipelineStage | undefined;
|
|
105
|
+
getResults(): Record<string, unknown>;
|
|
106
|
+
run(ctxOrResults?: Context | Record<string, unknown>): Promise<PipelineRunResult>;
|
|
107
|
+
reset(): void;
|
|
108
|
+
}
|
|
109
|
+
export declare class PipelineRegistry {
|
|
110
|
+
private pipelines;
|
|
111
|
+
define(nameOrConfig: string | PipelineConfig, config?: PipelineConfig): this;
|
|
112
|
+
get(name: string): Pipeline;
|
|
113
|
+
remove(name: string): boolean;
|
|
114
|
+
list(): string[];
|
|
115
|
+
run(name: string, ctx?: Context): Promise<PipelineRunResult>;
|
|
116
|
+
}
|