@mks2508/coolify-mks-cli-mcp 0.5.0 → 0.6.0
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/dist/cli/coolify-state.d.ts +51 -0
- package/dist/cli/coolify-state.d.ts.map +1 -0
- package/dist/cli/index.js +2862 -631
- package/dist/coolify/config.d.ts +1 -1
- package/dist/coolify/config.d.ts.map +1 -1
- package/dist/coolify/index.d.ts +626 -12
- package/dist/coolify/index.d.ts.map +1 -1
- package/dist/coolify/types.d.ts +87 -3
- package/dist/coolify/types.d.ts.map +1 -1
- package/dist/dist-C4hIkHif.js +66 -0
- package/dist/dist-C4hIkHif.js.map +1 -0
- package/dist/dist-DEPvJhbP.js +3 -0
- package/dist/index.cjs +8511 -28542
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +32 -8
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +8470 -28506
- package/dist/index.js.map +1 -1
- package/dist/network.d.ts +75 -0
- package/dist/network.d.ts.map +1 -0
- package/dist/sdk.d.ts +356 -0
- package/dist/sdk.d.ts.map +1 -0
- package/dist/server/index.d.ts +9 -0
- package/dist/server/index.d.ts.map +1 -0
- package/dist/server/sse.js +3 -1
- package/dist/server/stdio.d.ts +0 -2
- package/dist/server/stdio.d.ts.map +1 -1
- package/dist/server/stdio.js +3307 -1618
- package/dist/tools/definitions.d.ts +1 -1
- package/dist/tools/definitions.d.ts.map +1 -1
- package/dist/tools/handlers.d.ts +6 -7
- package/dist/tools/handlers.d.ts.map +1 -1
- package/dist/tools/index.d.ts +8 -0
- package/dist/tools/index.d.ts.map +1 -0
- package/dist/trace.d.ts +71 -0
- package/dist/trace.d.ts.map +1 -0
- package/dist/utils/format.d.ts +1 -1
- package/dist/utils/format.d.ts.map +1 -1
- package/package.json +13 -7
- package/src/cli/actions.ts +162 -0
- package/src/cli/commands/active-deployments.ts +24 -0
- package/src/cli/commands/build-logs.ts +25 -22
- package/src/cli/commands/cancel-deploy.ts +35 -0
- package/src/cli/commands/config.ts +53 -47
- package/src/cli/commands/create.ts +74 -53
- package/src/cli/commands/databases.ts +63 -0
- package/src/cli/commands/db.ts +68 -0
- package/src/cli/commands/delete.ts +41 -29
- package/src/cli/commands/deploy.ts +42 -21
- package/src/cli/commands/deployments.ts +41 -31
- package/src/cli/commands/destinations.ts +19 -27
- package/src/cli/commands/diagnose.ts +139 -0
- package/src/cli/commands/env.ts +66 -41
- package/src/cli/commands/environments.ts +36 -32
- package/src/cli/commands/exec.ts +39 -0
- package/src/cli/commands/keys.ts +46 -0
- package/src/cli/commands/list.ts +29 -27
- package/src/cli/commands/logs.ts +33 -18
- package/src/cli/commands/network.ts +145 -0
- package/src/cli/commands/projects.ts +51 -39
- package/src/cli/commands/restart.ts +34 -18
- package/src/cli/commands/server-resources.ts +71 -0
- package/src/cli/commands/servers.ts +23 -23
- package/src/cli/commands/service-logs.ts +24 -16
- package/src/cli/commands/services.ts +63 -0
- package/src/cli/commands/show.ts +72 -41
- package/src/cli/commands/start.ts +34 -18
- package/src/cli/commands/stop.ts +34 -18
- package/src/cli/commands/svc.ts +68 -0
- package/src/cli/commands/teams.ts +60 -0
- package/src/cli/commands/update.ts +73 -49
- package/src/cli/commands/version.ts +37 -0
- package/src/cli/coolify-state.ts +88 -0
- package/src/cli/index.ts +383 -151
- package/src/coolify/config.ts +29 -27
- package/src/coolify/index.ts +1829 -123
- package/src/coolify/types.ts +217 -124
- package/src/index.ts +82 -868
- package/src/network.ts +298 -0
- package/src/sdk.ts +597 -0
- package/src/server/index.ts +13 -0
- package/src/server/sse.ts +33 -25
- package/src/server/stdio.ts +24 -27
- package/src/tools/definitions.ts +893 -264
- package/src/tools/handlers.ts +556 -748
- package/src/tools/index.ts +8 -0
- package/src/trace.ts +116 -0
- package/src/utils/format.ts +36 -33
|
@@ -6,10 +6,10 @@
|
|
|
6
6
|
* @module
|
|
7
7
|
*/
|
|
8
8
|
|
|
9
|
-
import { isErr } from
|
|
10
|
-
import chalk from
|
|
11
|
-
import Table from
|
|
12
|
-
import { getCoolifyService } from
|
|
9
|
+
import { isErr } from "@mks2508/no-throw";
|
|
10
|
+
import chalk from "chalk";
|
|
11
|
+
import Table from "cli-table3";
|
|
12
|
+
import { getCoolifyService } from "../../coolify/index.js";
|
|
13
13
|
|
|
14
14
|
/**
|
|
15
15
|
* Destinations command handler.
|
|
@@ -17,44 +17,36 @@ import { getCoolifyService } from '../../coolify/index.js'
|
|
|
17
17
|
* @param serverUuid - Server UUID
|
|
18
18
|
*/
|
|
19
19
|
export async function destinationsCommand(serverUuid: string) {
|
|
20
|
-
const coolify = getCoolifyService()
|
|
21
|
-
const initResult = await coolify.init()
|
|
20
|
+
const coolify = getCoolifyService();
|
|
21
|
+
const initResult = await coolify.init();
|
|
22
22
|
|
|
23
23
|
if (isErr(initResult)) {
|
|
24
|
-
console.error(chalk.red(`Error: ${initResult.error.message}`))
|
|
25
|
-
return
|
|
24
|
+
console.error(chalk.red(`Error: ${initResult.error.message}`));
|
|
25
|
+
return;
|
|
26
26
|
}
|
|
27
27
|
|
|
28
|
-
const result = await coolify.getServerDestinations(serverUuid)
|
|
28
|
+
const result = await coolify.getServerDestinations(serverUuid);
|
|
29
29
|
|
|
30
30
|
if (isErr(result)) {
|
|
31
|
-
console.error(chalk.red(`Error: ${result.error.message}`))
|
|
32
|
-
return
|
|
31
|
+
console.error(chalk.red(`Error: ${result.error.message}`));
|
|
32
|
+
return;
|
|
33
33
|
}
|
|
34
34
|
|
|
35
|
-
const destinations = result.value
|
|
35
|
+
const destinations = result.value;
|
|
36
36
|
|
|
37
37
|
if (destinations.length === 0) {
|
|
38
|
-
console.log(chalk.yellow(
|
|
39
|
-
return
|
|
38
|
+
console.log(chalk.yellow("No destinations found"));
|
|
39
|
+
return;
|
|
40
40
|
}
|
|
41
41
|
|
|
42
42
|
const table = new Table({
|
|
43
|
-
head: [
|
|
44
|
-
|
|
45
|
-
chalk.cyan('Name'),
|
|
46
|
-
chalk.cyan('Network'),
|
|
47
|
-
],
|
|
48
|
-
})
|
|
43
|
+
head: [chalk.cyan("UUID"), chalk.cyan("Name"), chalk.cyan("Network")],
|
|
44
|
+
});
|
|
49
45
|
|
|
50
46
|
for (const dest of destinations) {
|
|
51
|
-
table.push([
|
|
52
|
-
dest.uuid,
|
|
53
|
-
dest.name,
|
|
54
|
-
dest.network || 'N/A',
|
|
55
|
-
])
|
|
47
|
+
table.push([dest.uuid, dest.name, dest.network || "N/A"]);
|
|
56
48
|
}
|
|
57
49
|
|
|
58
|
-
console.log(table.toString())
|
|
59
|
-
console.log(chalk.gray(`Total: ${destinations.length} destination(s)`))
|
|
50
|
+
console.log(table.toString());
|
|
51
|
+
console.log(chalk.gray(`Total: ${destinations.length} destination(s)`));
|
|
60
52
|
}
|
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Diagnostic subcommands for CLI — all go through SDK.
|
|
3
|
+
*
|
|
4
|
+
* @module
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
import { chalk, getCliSdk, formatStatus } from "../actions.js";
|
|
8
|
+
import { resolveUuid } from "../coolify-state.js";
|
|
9
|
+
|
|
10
|
+
/** Diagnose an application. */
|
|
11
|
+
export async function diagnoseAppCommand(query?: string): Promise<void> {
|
|
12
|
+
const resolved = query || resolveUuid(undefined);
|
|
13
|
+
if (!resolved) {
|
|
14
|
+
console.error(
|
|
15
|
+
chalk.red("Error: No app name/UUID provided and no .coolify.json found"),
|
|
16
|
+
);
|
|
17
|
+
return;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
console.log(chalk.cyan(`Diagnosing application: ${resolved}...\n`));
|
|
21
|
+
|
|
22
|
+
try {
|
|
23
|
+
const { application, recentDeployments, envVarCount, recentLogs, issues } =
|
|
24
|
+
await getCliSdk().diagnose.app(resolved);
|
|
25
|
+
|
|
26
|
+
console.log(chalk.bold("Application:"));
|
|
27
|
+
console.log(` ${chalk.gray("Name:")} ${application.name}`);
|
|
28
|
+
console.log(` ${chalk.gray("UUID:")} ${application.uuid}`);
|
|
29
|
+
console.log(
|
|
30
|
+
` ${chalk.gray("Status:")} ${formatStatus(application.status)}`,
|
|
31
|
+
);
|
|
32
|
+
console.log(` ${chalk.gray("FQDN:")} ${application.fqdn || "none"}`);
|
|
33
|
+
console.log(` ${chalk.gray("Env vars:")} ${envVarCount}`);
|
|
34
|
+
|
|
35
|
+
if (recentDeployments.length > 0) {
|
|
36
|
+
console.log(chalk.bold("\nRecent Deployments:"));
|
|
37
|
+
for (const d of recentDeployments) {
|
|
38
|
+
const status = d.status?.includes("failed")
|
|
39
|
+
? chalk.red(d.status)
|
|
40
|
+
: chalk.green(d.status);
|
|
41
|
+
console.log(
|
|
42
|
+
` ${chalk.gray(d.uuid.slice(0, 12))} ${status} ${chalk.gray(new Date(d.created_at).toLocaleString())}`,
|
|
43
|
+
);
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
if (recentLogs.length > 0) {
|
|
48
|
+
console.log(chalk.bold("\nRecent Logs (last 5):"));
|
|
49
|
+
for (const line of recentLogs.slice(-5)) {
|
|
50
|
+
console.log(` ${chalk.gray(line)}`);
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
if (issues.length > 0) {
|
|
55
|
+
console.log(chalk.bold.red(`\nIssues (${issues.length}):`));
|
|
56
|
+
for (const issue of issues) {
|
|
57
|
+
console.log(` ${chalk.red("!")} ${issue}`);
|
|
58
|
+
}
|
|
59
|
+
} else {
|
|
60
|
+
console.log(chalk.bold.green("\nNo issues detected"));
|
|
61
|
+
}
|
|
62
|
+
} catch (error) {
|
|
63
|
+
console.error(
|
|
64
|
+
chalk.red(
|
|
65
|
+
`Error: ${error instanceof Error ? error.message : String(error)}`,
|
|
66
|
+
),
|
|
67
|
+
);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
/** Diagnose a server. */
|
|
72
|
+
export async function diagnoseServerCommand(query: string): Promise<void> {
|
|
73
|
+
console.log(chalk.cyan(`Diagnosing server: ${query}...\n`));
|
|
74
|
+
|
|
75
|
+
try {
|
|
76
|
+
const { server, resources, domains, issues } =
|
|
77
|
+
await getCliSdk().diagnose.server(query);
|
|
78
|
+
|
|
79
|
+
console.log(chalk.bold("Server:"));
|
|
80
|
+
console.log(` ${chalk.gray("Name:")} ${server.name}`);
|
|
81
|
+
console.log(` ${chalk.gray("UUID:")} ${server.uuid}`);
|
|
82
|
+
console.log(` ${chalk.gray("IP:")} ${server.ip || "-"}`);
|
|
83
|
+
console.log(
|
|
84
|
+
` ${chalk.gray("Reachable:")} ${server.is_reachable ? chalk.green("Yes") : chalk.red("No")}`,
|
|
85
|
+
);
|
|
86
|
+
console.log(` ${chalk.gray("Resources:")} ${resources.length}`);
|
|
87
|
+
console.log(` ${chalk.gray("Domains:")} ${domains.length}`);
|
|
88
|
+
|
|
89
|
+
if (issues.length > 0) {
|
|
90
|
+
console.log(chalk.bold.red(`\nIssues (${issues.length}):`));
|
|
91
|
+
for (const issue of issues) {
|
|
92
|
+
console.log(` ${chalk.red("!")} ${issue}`);
|
|
93
|
+
}
|
|
94
|
+
} else {
|
|
95
|
+
console.log(chalk.bold.green("\nNo issues detected"));
|
|
96
|
+
}
|
|
97
|
+
} catch (error) {
|
|
98
|
+
console.error(
|
|
99
|
+
chalk.red(
|
|
100
|
+
`Error: ${error instanceof Error ? error.message : String(error)}`,
|
|
101
|
+
),
|
|
102
|
+
);
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
/** Scan all infrastructure for issues. */
|
|
107
|
+
export async function scanIssuesCommand(): Promise<void> {
|
|
108
|
+
console.log(chalk.cyan("Scanning infrastructure...\n"));
|
|
109
|
+
|
|
110
|
+
try {
|
|
111
|
+
const { totalServers, totalApps, totalDatabases, totalServices, issues } =
|
|
112
|
+
await getCliSdk().diagnose.infrastructure();
|
|
113
|
+
|
|
114
|
+
console.log(chalk.bold("Infrastructure Summary:"));
|
|
115
|
+
console.log(` ${chalk.gray("Servers:")} ${totalServers}`);
|
|
116
|
+
console.log(` ${chalk.gray("Apps:")} ${totalApps}`);
|
|
117
|
+
console.log(` ${chalk.gray("Databases:")} ${totalDatabases}`);
|
|
118
|
+
console.log(` ${chalk.gray("Services:")} ${totalServices}`);
|
|
119
|
+
|
|
120
|
+
if (issues.length > 0) {
|
|
121
|
+
console.log(chalk.bold.red(`\nIssues (${issues.length}):`));
|
|
122
|
+
for (const issue of issues) {
|
|
123
|
+
console.log(
|
|
124
|
+
` ${chalk.red("!")} [${issue.type}] ${issue.resource} (${issue.uuid}): ${issue.message}`,
|
|
125
|
+
);
|
|
126
|
+
}
|
|
127
|
+
} else {
|
|
128
|
+
console.log(
|
|
129
|
+
chalk.bold.green("\nNo issues detected across all infrastructure"),
|
|
130
|
+
);
|
|
131
|
+
}
|
|
132
|
+
} catch (error) {
|
|
133
|
+
console.error(
|
|
134
|
+
chalk.red(
|
|
135
|
+
`Error: ${error instanceof Error ? error.message : String(error)}`,
|
|
136
|
+
),
|
|
137
|
+
);
|
|
138
|
+
}
|
|
139
|
+
}
|
package/src/cli/commands/env.ts
CHANGED
|
@@ -4,99 +4,124 @@
|
|
|
4
4
|
* @module
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
|
-
import { isErr } from
|
|
8
|
-
import chalk from
|
|
9
|
-
import { getCoolifyService } from
|
|
7
|
+
import { isErr } from "@mks2508/no-throw";
|
|
8
|
+
import chalk from "chalk";
|
|
9
|
+
import { getCoolifyService } from "../../coolify/index.js";
|
|
10
|
+
import { resolveUuid } from "../coolify-state.js";
|
|
10
11
|
|
|
11
12
|
interface IEnvCommandOptions {
|
|
12
|
-
set?: string
|
|
13
|
-
delete?: string
|
|
14
|
-
buildtime?: boolean
|
|
13
|
+
set?: string;
|
|
14
|
+
delete?: string;
|
|
15
|
+
buildtime?: boolean;
|
|
15
16
|
}
|
|
16
17
|
|
|
17
18
|
/**
|
|
18
19
|
* Env vars command handler.
|
|
20
|
+
* If no UUID is provided, reads from .coolify.json in the current directory.
|
|
19
21
|
*
|
|
20
|
-
* @param uuid - Application UUID
|
|
22
|
+
* @param uuid - Application UUID (optional if .coolify.json exists)
|
|
21
23
|
* @param options - Command options
|
|
22
24
|
*/
|
|
23
|
-
export async function envCommand(
|
|
24
|
-
|
|
25
|
-
|
|
25
|
+
export async function envCommand(
|
|
26
|
+
uuid: string | undefined,
|
|
27
|
+
options: IEnvCommandOptions = {},
|
|
28
|
+
) {
|
|
29
|
+
const resolvedUuid = resolveUuid(uuid);
|
|
30
|
+
if (!resolvedUuid) {
|
|
31
|
+
console.error(
|
|
32
|
+
chalk.red("Error: No UUID provided and no .coolify.json found"),
|
|
33
|
+
);
|
|
34
|
+
return;
|
|
35
|
+
}
|
|
36
|
+
uuid = resolvedUuid;
|
|
37
|
+
const coolify = getCoolifyService();
|
|
38
|
+
const initResult = await coolify.init();
|
|
26
39
|
|
|
27
40
|
if (isErr(initResult)) {
|
|
28
|
-
console.error(chalk.red(`Error: ${initResult.error.message}`))
|
|
29
|
-
return
|
|
41
|
+
console.error(chalk.red(`Error: ${initResult.error.message}`));
|
|
42
|
+
return;
|
|
30
43
|
}
|
|
31
44
|
|
|
32
45
|
// Handle --set KEY=VALUE
|
|
33
46
|
if (options.set) {
|
|
34
|
-
const [key, ...valueParts] = options.set.split(
|
|
35
|
-
const value = valueParts.join(
|
|
47
|
+
const [key, ...valueParts] = options.set.split("=");
|
|
48
|
+
const value = valueParts.join("="); // Handle values with = in them
|
|
36
49
|
|
|
37
50
|
if (!key || value === undefined) {
|
|
38
|
-
console.error(chalk.red(
|
|
39
|
-
return
|
|
51
|
+
console.error(chalk.red("Error: Invalid format. Use --set KEY=VALUE"));
|
|
52
|
+
return;
|
|
40
53
|
}
|
|
41
54
|
|
|
42
|
-
const result = await coolify.setEnvironmentVariable(
|
|
55
|
+
const result = await coolify.setEnvironmentVariable(
|
|
56
|
+
uuid,
|
|
57
|
+
key,
|
|
58
|
+
value,
|
|
59
|
+
options.buildtime ?? false,
|
|
60
|
+
);
|
|
43
61
|
|
|
44
62
|
if (isErr(result)) {
|
|
45
|
-
console.error(chalk.red(`Error: ${result.error.message}`))
|
|
46
|
-
return
|
|
63
|
+
console.error(chalk.red(`Error: ${result.error.message}`));
|
|
64
|
+
return;
|
|
47
65
|
}
|
|
48
66
|
|
|
49
|
-
console.log(chalk.green(`✓ Set ${chalk.bold(key)} for ${uuid
|
|
50
|
-
return
|
|
67
|
+
console.log(chalk.green(`✓ Set ${chalk.bold(key)} for ${uuid}`));
|
|
68
|
+
return;
|
|
51
69
|
}
|
|
52
70
|
|
|
53
71
|
// Handle --delete KEY
|
|
54
72
|
if (options.delete) {
|
|
55
|
-
const result = await coolify.deleteEnvironmentVariable(
|
|
73
|
+
const result = await coolify.deleteEnvironmentVariable(
|
|
74
|
+
uuid,
|
|
75
|
+
options.delete,
|
|
76
|
+
);
|
|
56
77
|
|
|
57
78
|
if (isErr(result)) {
|
|
58
|
-
console.error(chalk.red(`Error: ${result.error.message}`))
|
|
59
|
-
return
|
|
79
|
+
console.error(chalk.red(`Error: ${result.error.message}`));
|
|
80
|
+
return;
|
|
60
81
|
}
|
|
61
82
|
|
|
62
|
-
console.log(
|
|
63
|
-
|
|
83
|
+
console.log(
|
|
84
|
+
chalk.green(`✓ Deleted ${chalk.bold(options.delete)} from ${uuid}`),
|
|
85
|
+
);
|
|
86
|
+
return;
|
|
64
87
|
}
|
|
65
88
|
|
|
66
89
|
// Default: list env vars
|
|
67
|
-
const result = await coolify.getEnvironmentVariables(uuid)
|
|
90
|
+
const result = await coolify.getEnvironmentVariables(uuid);
|
|
68
91
|
|
|
69
92
|
if (isErr(result)) {
|
|
70
|
-
console.error(chalk.red(`Error: ${result.error.message}`))
|
|
71
|
-
return
|
|
93
|
+
console.error(chalk.red(`Error: ${result.error.message}`));
|
|
94
|
+
return;
|
|
72
95
|
}
|
|
73
96
|
|
|
74
|
-
const envVars = result.value
|
|
97
|
+
const envVars = result.value;
|
|
75
98
|
|
|
76
99
|
if (envVars.length === 0) {
|
|
77
|
-
console.log(chalk.yellow(
|
|
78
|
-
return
|
|
100
|
+
console.log(chalk.yellow("No environment variables found"));
|
|
101
|
+
return;
|
|
79
102
|
}
|
|
80
103
|
|
|
81
|
-
console.log(chalk.cyan(`Environment variables (${envVars.length}):\n`))
|
|
104
|
+
console.log(chalk.cyan(`Environment variables (${envVars.length}):\n`));
|
|
82
105
|
|
|
83
106
|
// Separar runtime de buildtime
|
|
84
|
-
const runtimeVars = envVars.filter(ev => ev.is_runtime)
|
|
85
|
-
const buildtimeVars = envVars.filter(ev => ev.is_buildtime)
|
|
107
|
+
const runtimeVars = envVars.filter((ev) => ev.is_runtime);
|
|
108
|
+
const buildtimeVars = envVars.filter((ev) => ev.is_buildtime);
|
|
86
109
|
|
|
87
110
|
if (runtimeVars.length > 0) {
|
|
88
|
-
console.log(chalk.yellow.bold(
|
|
111
|
+
console.log(chalk.yellow.bold("Runtime:"));
|
|
89
112
|
for (const ev of runtimeVars) {
|
|
90
|
-
const required = ev.is_required ? chalk.red(
|
|
91
|
-
console.log(
|
|
113
|
+
const required = ev.is_required ? chalk.red(" *") : "";
|
|
114
|
+
console.log(
|
|
115
|
+
` ${chalk.green(ev.key)}${required} = ${chalk.gray(ev.value)}`,
|
|
116
|
+
);
|
|
92
117
|
}
|
|
93
|
-
console.log()
|
|
118
|
+
console.log();
|
|
94
119
|
}
|
|
95
120
|
|
|
96
121
|
if (buildtimeVars.length > 0) {
|
|
97
|
-
console.log(chalk.blue.bold(
|
|
122
|
+
console.log(chalk.blue.bold("Buildtime:"));
|
|
98
123
|
for (const ev of buildtimeVars) {
|
|
99
|
-
console.log(` ${chalk.green(ev.key)} = ${chalk.gray(ev.value)}`)
|
|
124
|
+
console.log(` ${chalk.green(ev.key)} = ${chalk.gray(ev.value)}`);
|
|
100
125
|
}
|
|
101
126
|
}
|
|
102
127
|
}
|
|
@@ -4,11 +4,11 @@
|
|
|
4
4
|
* @module
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
|
-
import { isOk, isErr } from
|
|
8
|
-
import ora from
|
|
9
|
-
import chalk from
|
|
10
|
-
import Table from
|
|
11
|
-
import { getCoolifyService } from
|
|
7
|
+
import { isOk, isErr } from "@mks2508/no-throw";
|
|
8
|
+
import ora from "ora";
|
|
9
|
+
import chalk from "chalk";
|
|
10
|
+
import Table from "cli-table3";
|
|
11
|
+
import { getCoolifyService } from "../../coolify/index.js";
|
|
12
12
|
|
|
13
13
|
/**
|
|
14
14
|
* Environments command handler.
|
|
@@ -16,57 +16,61 @@ import { getCoolifyService } from '../../coolify/index.js'
|
|
|
16
16
|
* @param projectUuid - Project UUID to get environments for
|
|
17
17
|
* @param options - Command options
|
|
18
18
|
*/
|
|
19
|
-
export async function environmentsCommand(
|
|
20
|
-
|
|
19
|
+
export async function environmentsCommand(
|
|
20
|
+
projectUuid: string,
|
|
21
|
+
_options: { full?: boolean } = {},
|
|
22
|
+
) {
|
|
23
|
+
const spinner = ora("Connecting to Coolify...").start();
|
|
21
24
|
|
|
22
25
|
try {
|
|
23
|
-
const coolify = getCoolifyService()
|
|
24
|
-
const initResult = await coolify.init()
|
|
26
|
+
const coolify = getCoolifyService();
|
|
27
|
+
const initResult = await coolify.init();
|
|
25
28
|
|
|
26
29
|
if (isErr(initResult)) {
|
|
27
|
-
spinner.fail(
|
|
28
|
-
|
|
30
|
+
spinner.fail(
|
|
31
|
+
chalk.red(`Failed to initialize: ${initResult.error.message}`),
|
|
32
|
+
);
|
|
33
|
+
return;
|
|
29
34
|
}
|
|
30
35
|
|
|
31
|
-
spinner.text = `Fetching environments for project ${projectUuid
|
|
36
|
+
spinner.text = `Fetching environments for project ${projectUuid}...`;
|
|
32
37
|
|
|
33
|
-
const result = await coolify.getProjectEnvironments(projectUuid)
|
|
38
|
+
const result = await coolify.getProjectEnvironments(projectUuid);
|
|
34
39
|
|
|
35
40
|
if (isOk(result)) {
|
|
36
|
-
spinner.succeed(chalk.green(
|
|
41
|
+
spinner.succeed(chalk.green("Environments retrieved"));
|
|
37
42
|
|
|
38
|
-
const environments = result.value
|
|
43
|
+
const environments = result.value;
|
|
39
44
|
|
|
40
45
|
if (environments.length === 0) {
|
|
41
|
-
console.log(chalk.yellow(
|
|
42
|
-
return
|
|
46
|
+
console.log(chalk.yellow("No environments found for this project"));
|
|
47
|
+
return;
|
|
43
48
|
}
|
|
44
49
|
|
|
45
50
|
const table = new Table({
|
|
46
51
|
head: [
|
|
47
|
-
chalk.cyan(
|
|
48
|
-
chalk.cyan(
|
|
49
|
-
chalk.cyan(
|
|
52
|
+
chalk.cyan("UUID"),
|
|
53
|
+
chalk.cyan("Name"),
|
|
54
|
+
chalk.cyan("Description"),
|
|
50
55
|
],
|
|
51
|
-
|
|
52
|
-
})
|
|
56
|
+
});
|
|
53
57
|
|
|
54
58
|
for (const env of environments) {
|
|
55
|
-
table.push([
|
|
56
|
-
options.full ? env.uuid : env.uuid.slice(0, 8),
|
|
57
|
-
env.name,
|
|
58
|
-
env.description || '-',
|
|
59
|
-
])
|
|
59
|
+
table.push([env.uuid, env.name, env.description || "-"]);
|
|
60
60
|
}
|
|
61
61
|
|
|
62
|
-
console.log(table.toString())
|
|
63
|
-
console.log(chalk.gray(`Total: ${environments.length} environment(s)`))
|
|
62
|
+
console.log(table.toString());
|
|
63
|
+
console.log(chalk.gray(`Total: ${environments.length} environment(s)`));
|
|
64
64
|
} else {
|
|
65
|
-
spinner.fail(
|
|
65
|
+
spinner.fail(
|
|
66
|
+
chalk.red(`Failed to fetch environments: ${result.error.message}`),
|
|
67
|
+
);
|
|
66
68
|
}
|
|
67
69
|
} catch (error) {
|
|
68
70
|
spinner.fail(
|
|
69
|
-
chalk.red(
|
|
70
|
-
|
|
71
|
+
chalk.red(
|
|
72
|
+
`Error: ${error instanceof Error ? error.message : String(error)}`,
|
|
73
|
+
),
|
|
74
|
+
);
|
|
71
75
|
}
|
|
72
76
|
}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Execute command on application container — goes through SDK.
|
|
3
|
+
*
|
|
4
|
+
* @module
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
import { chalk, getCliSdk } from "../actions.js";
|
|
8
|
+
import { resolveUuid } from "../coolify-state.js";
|
|
9
|
+
|
|
10
|
+
/** Execute a command on an application's running container. */
|
|
11
|
+
export async function execCommand(
|
|
12
|
+
uuid: string | undefined,
|
|
13
|
+
command: string,
|
|
14
|
+
): Promise<void> {
|
|
15
|
+
const resolved = resolveUuid(uuid);
|
|
16
|
+
if (!resolved) {
|
|
17
|
+
console.error(
|
|
18
|
+
chalk.red("Error: No UUID provided and no .coolify.json found"),
|
|
19
|
+
);
|
|
20
|
+
return;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
console.log(chalk.gray(`Executing on ${resolved}: ${command}`));
|
|
24
|
+
|
|
25
|
+
try {
|
|
26
|
+
const result = await getCliSdk().applications.exec(resolved, command);
|
|
27
|
+
if (result.response) {
|
|
28
|
+
console.log(result.response);
|
|
29
|
+
} else if (result.message) {
|
|
30
|
+
console.log(chalk.green(result.message));
|
|
31
|
+
}
|
|
32
|
+
} catch (error) {
|
|
33
|
+
console.error(
|
|
34
|
+
chalk.red(
|
|
35
|
+
`Error: ${error instanceof Error ? error.message : String(error)}`,
|
|
36
|
+
),
|
|
37
|
+
);
|
|
38
|
+
}
|
|
39
|
+
}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* SSH Private key subcommands for CLI — all go through SDK.
|
|
3
|
+
*
|
|
4
|
+
* @module
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
import { runAction, runList, runGet, chalk } from "../actions.js";
|
|
8
|
+
import type { ICoolifyPrivateKey } from "../../coolify/types.js";
|
|
9
|
+
|
|
10
|
+
/** List all private keys. */
|
|
11
|
+
export const keysListCommand = () =>
|
|
12
|
+
runList<ICoolifyPrivateKey>("key(s)", (s) => s.keys.list(), [
|
|
13
|
+
{ header: "UUID", value: (k) => k.uuid },
|
|
14
|
+
{ header: "Name", value: (k) => k.name || "-" },
|
|
15
|
+
{ header: "Git?", value: (k) => (k.is_git_related ? "Yes" : "No") },
|
|
16
|
+
{
|
|
17
|
+
header: "Created",
|
|
18
|
+
value: (k) =>
|
|
19
|
+
k.created_at ? new Date(k.created_at).toLocaleDateString() : "-",
|
|
20
|
+
},
|
|
21
|
+
]);
|
|
22
|
+
|
|
23
|
+
/** Get private key details. */
|
|
24
|
+
export const keysGetCommand = (uuid: string) =>
|
|
25
|
+
runGet<ICoolifyPrivateKey>(
|
|
26
|
+
uuid,
|
|
27
|
+
"private key",
|
|
28
|
+
(s, u) => s.keys.get(u),
|
|
29
|
+
(key) => {
|
|
30
|
+
console.log(chalk.cyan("Private Key Details:"));
|
|
31
|
+
console.log(chalk.gray("UUID: ") + key.uuid);
|
|
32
|
+
console.log(chalk.gray("Name: ") + key.name);
|
|
33
|
+
console.log(
|
|
34
|
+
chalk.gray("Git-related:") + (key.is_git_related ? " Yes" : " No"),
|
|
35
|
+
);
|
|
36
|
+
},
|
|
37
|
+
);
|
|
38
|
+
|
|
39
|
+
/** Delete a private key. */
|
|
40
|
+
export const keysDeleteCommand = (uuid: string) =>
|
|
41
|
+
runAction(
|
|
42
|
+
uuid,
|
|
43
|
+
"Deleting private key",
|
|
44
|
+
(s, u) => s.keys.delete(u),
|
|
45
|
+
(u) => `Private key deleted: ${u}`,
|
|
46
|
+
);
|
package/src/cli/commands/list.ts
CHANGED
|
@@ -4,60 +4,62 @@
|
|
|
4
4
|
* @module
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
|
-
import { isErr } from
|
|
8
|
-
import chalk from
|
|
9
|
-
import Table from
|
|
10
|
-
import { getCoolifyService } from
|
|
11
|
-
import { formatStatus } from
|
|
7
|
+
import { isErr } from "@mks2508/no-throw";
|
|
8
|
+
import chalk from "chalk";
|
|
9
|
+
import Table from "cli-table3";
|
|
10
|
+
import { getCoolifyService } from "../../coolify/index.js";
|
|
11
|
+
import { formatStatus } from "../../utils/format.js";
|
|
12
12
|
|
|
13
13
|
/**
|
|
14
14
|
* List command handler.
|
|
15
15
|
*
|
|
16
16
|
* @param options - List options
|
|
17
17
|
*/
|
|
18
|
-
export async function listCommand(options: {
|
|
19
|
-
|
|
20
|
-
|
|
18
|
+
export async function listCommand(options: {
|
|
19
|
+
team?: string;
|
|
20
|
+
project?: string;
|
|
21
|
+
}) {
|
|
22
|
+
const coolify = getCoolifyService();
|
|
23
|
+
const initResult = await coolify.init();
|
|
21
24
|
|
|
22
25
|
if (isErr(initResult)) {
|
|
23
|
-
console.error(chalk.red(`Error: ${initResult.error.message}`))
|
|
24
|
-
return
|
|
26
|
+
console.error(chalk.red(`Error: ${initResult.error.message}`));
|
|
27
|
+
return;
|
|
25
28
|
}
|
|
26
29
|
|
|
27
|
-
const result = await coolify.listApplications(options.team, options.project)
|
|
30
|
+
const result = await coolify.listApplications(options.team, options.project);
|
|
28
31
|
|
|
29
32
|
if (isErr(result)) {
|
|
30
|
-
console.error(chalk.red(`Error: ${result.error.message}`))
|
|
31
|
-
return
|
|
33
|
+
console.error(chalk.red(`Error: ${result.error.message}`));
|
|
34
|
+
return;
|
|
32
35
|
}
|
|
33
36
|
|
|
34
|
-
const apps = result.value
|
|
37
|
+
const apps = result.value;
|
|
35
38
|
|
|
36
39
|
if (apps.length === 0) {
|
|
37
|
-
console.log(chalk.yellow(
|
|
38
|
-
return
|
|
40
|
+
console.log(chalk.yellow("No applications found"));
|
|
41
|
+
return;
|
|
39
42
|
}
|
|
40
43
|
|
|
41
44
|
// Usar ancho dinámico basado en el contenido
|
|
42
45
|
const table = new Table({
|
|
43
46
|
head: [
|
|
44
|
-
chalk.cyan(
|
|
45
|
-
chalk.cyan(
|
|
46
|
-
chalk.cyan(
|
|
47
|
-
chalk.cyan(
|
|
47
|
+
chalk.cyan("UUID"),
|
|
48
|
+
chalk.cyan("Name"),
|
|
49
|
+
chalk.cyan("Status"),
|
|
50
|
+
chalk.cyan("Server"),
|
|
48
51
|
],
|
|
49
|
-
|
|
50
|
-
})
|
|
52
|
+
});
|
|
51
53
|
|
|
52
54
|
for (const app of apps) {
|
|
53
55
|
table.push([
|
|
54
|
-
|
|
56
|
+
app.uuid,
|
|
55
57
|
app.name,
|
|
56
58
|
formatStatus(app.status),
|
|
57
|
-
app.destination?.server?.name ||
|
|
58
|
-
])
|
|
59
|
+
app.destination?.server?.name || "N/A",
|
|
60
|
+
]);
|
|
59
61
|
}
|
|
60
62
|
|
|
61
|
-
console.log(table.toString())
|
|
62
|
-
console.log(chalk.gray(`Total: ${apps.length} application(s)`))
|
|
63
|
+
console.log(table.toString());
|
|
64
|
+
console.log(chalk.gray(`Total: ${apps.length} application(s)`));
|
|
63
65
|
}
|