@getmonoceros/workbench 1.33.7 → 1.34.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/bin.js +646 -274
- package/dist/bin.js.map +1 -1
- package/package.json +1 -1
package/dist/bin.js
CHANGED
|
@@ -2396,7 +2396,7 @@ var init_catalog = __esm({
|
|
|
2396
2396
|
override = process.env.MONOCEROS_BASE_IMAGE_OVERRIDE?.trim();
|
|
2397
2397
|
BASE_IMAGE = override && override.length > 0 ? override : DEFAULT_BASE_IMAGE;
|
|
2398
2398
|
RUNTIME_IMAGE_REPO = "ghcr.io/getmonoceros/monoceros-runtime";
|
|
2399
|
-
DEFAULT_RUNTIME_VERSION = true ? "1.
|
|
2399
|
+
DEFAULT_RUNTIME_VERSION = true ? "1.4.0" : readFileSync3(
|
|
2400
2400
|
fileURLToPath2(
|
|
2401
2401
|
new URL("../../../../images/runtime/VERSION", import.meta.url)
|
|
2402
2402
|
),
|
|
@@ -3668,7 +3668,11 @@ function buildDevcontainerJson(opts, dockerMode = "rootful") {
|
|
|
3668
3668
|
workspaceMount: `source=\${localWorkspaceFolder},target=/workspaces/${opts.name},type=bind,consistency=cached`,
|
|
3669
3669
|
workspaceFolder: `/workspaces/${opts.name}`
|
|
3670
3670
|
};
|
|
3671
|
-
const runArgs = [
|
|
3671
|
+
const runArgs = [
|
|
3672
|
+
"--cap-add=NET_ADMIN",
|
|
3673
|
+
`--name=monoceros-${opts.name}`,
|
|
3674
|
+
`--restart=${GROUP_RESTART_POLICY}`
|
|
3675
|
+
];
|
|
3672
3676
|
if (ports.length > 0) {
|
|
3673
3677
|
runArgs.push("--network=monoceros-proxy");
|
|
3674
3678
|
runArgs.push(`--network-alias=${opts.name}`);
|
|
@@ -3717,6 +3721,7 @@ function buildComposeYaml(opts, dockerMode = "rootful") {
|
|
|
3717
3721
|
lines.push(` image: ${resolveRuntimeImage(opts.runtimeVersion)}`);
|
|
3718
3722
|
lines.push(` container_name: monoceros-${opts.name}`);
|
|
3719
3723
|
lines.push(" command: 'sleep infinity'");
|
|
3724
|
+
lines.push(` restart: ${GROUP_RESTART_POLICY}`);
|
|
3720
3725
|
lines.push(" cap_add:");
|
|
3721
3726
|
lines.push(" - NET_ADMIN");
|
|
3722
3727
|
if (sshBridgePort !== null) {
|
|
@@ -3767,9 +3772,7 @@ function buildComposeYaml(opts, dockerMode = "rootful") {
|
|
|
3767
3772
|
if (svc.user !== void 0) {
|
|
3768
3773
|
lines.push(` user: ${composeScalar(svc.user)}`);
|
|
3769
3774
|
}
|
|
3770
|
-
|
|
3771
|
-
lines.push(` restart: ${svc.restart}`);
|
|
3772
|
-
}
|
|
3775
|
+
lines.push(` restart: ${svc.restart ?? GROUP_RESTART_POLICY}`);
|
|
3773
3776
|
if (svc.command !== void 0) {
|
|
3774
3777
|
lines.push(` command: ${composeScalar(svc.command)}`);
|
|
3775
3778
|
}
|
|
@@ -3929,6 +3932,10 @@ function buildPostCreateScript(opts) {
|
|
|
3929
3932
|
"# identity values in.",
|
|
3930
3933
|
`git config --global include.path "/workspaces/${opts.name}/.monoceros/gitconfig"`,
|
|
3931
3934
|
"",
|
|
3935
|
+
"# Container-global gitignore: keeps each app's .monoceros/ launch-config",
|
|
3936
|
+
"# dir out of the app repo by default. Per-app opt-in re-includes it.",
|
|
3937
|
+
`git config --global core.excludesFile "/workspaces/${opts.name}/.monoceros/global-gitignore"`,
|
|
3938
|
+
"",
|
|
3932
3939
|
"# Per-feature post-create hooks. Each Monoceros-curated feature",
|
|
3933
3940
|
"# may drop a script into /usr/local/share/monoceros/post-create.d/",
|
|
3934
3941
|
"# during its install.sh \u2014 typical job is a non-interactive login",
|
|
@@ -4069,7 +4076,11 @@ async function writeScaffold(opts, targetDir, scaffoldOpts = {}) {
|
|
|
4069
4076
|
}
|
|
4070
4077
|
await fs8.writeFile(
|
|
4071
4078
|
path11.join(monocerosDir, ".gitignore"),
|
|
4072
|
-
"git-credentials*\ngitconfig\n"
|
|
4079
|
+
"git-credentials*\ngitconfig\nglobal-gitignore\n"
|
|
4080
|
+
);
|
|
4081
|
+
await fs8.writeFile(
|
|
4082
|
+
path11.join(monocerosDir, "global-gitignore"),
|
|
4083
|
+
".monoceros/\n"
|
|
4073
4084
|
);
|
|
4074
4085
|
const devcontainerJson = buildDevcontainerJson(opts, dockerMode);
|
|
4075
4086
|
await writeIfChanged(
|
|
@@ -4149,7 +4160,7 @@ async function writeScaffold(opts, targetDir, scaffoldOpts = {}) {
|
|
|
4149
4160
|
JSON.stringify(mergeVscodeSettings(existingSettings), null, 2) + "\n"
|
|
4150
4161
|
);
|
|
4151
4162
|
}
|
|
4152
|
-
var APT_PACKAGE_NAME_RE2, FEATURE_REF_RE2, INSTALL_URL_RE2, REPO_URL_RE2, REPO_PATH_RE2, HOME_SUBPATH_RE, WORKSPACE_ROOT_LABEL, REPO_HOST_EXTENSIONS, ROOT_DENOISE_EXCLUDES;
|
|
4163
|
+
var APT_PACKAGE_NAME_RE2, FEATURE_REF_RE2, INSTALL_URL_RE2, REPO_URL_RE2, REPO_PATH_RE2, GROUP_RESTART_POLICY, HOME_SUBPATH_RE, WORKSPACE_ROOT_LABEL, REPO_HOST_EXTENSIONS, ROOT_DENOISE_EXCLUDES;
|
|
4153
4164
|
var init_scaffold = __esm({
|
|
4154
4165
|
"src/create/scaffold.ts"() {
|
|
4155
4166
|
"use strict";
|
|
@@ -4166,6 +4177,7 @@ var init_scaffold = __esm({
|
|
|
4166
4177
|
INSTALL_URL_RE2 = /^https:\/\/[A-Za-z0-9.\-_~/:?#[\]@!&'()*+,;=%]+$/;
|
|
4167
4178
|
REPO_URL_RE2 = /^[A-Za-z0-9@:/+_~.#=&?-]+$/;
|
|
4168
4179
|
REPO_PATH_RE2 = /^[A-Za-z0-9._-]+(\/[A-Za-z0-9._-]+)*$/;
|
|
4180
|
+
GROUP_RESTART_POLICY = "unless-stopped";
|
|
4169
4181
|
HOME_SUBPATH_RE = /^[A-Za-z0-9._-]+(\/[A-Za-z0-9._-]+)*$/;
|
|
4170
4182
|
WORKSPACE_ROOT_LABEL = "\u{1F984} Monoceros";
|
|
4171
4183
|
REPO_HOST_EXTENSIONS = {
|
|
@@ -4626,8 +4638,8 @@ function removeRepoFromDoc(doc, urlOrPath) {
|
|
|
4626
4638
|
if (!isMap2(item)) return false;
|
|
4627
4639
|
const url = item.get("url");
|
|
4628
4640
|
if (url === urlOrPath) return true;
|
|
4629
|
-
const
|
|
4630
|
-
const effectivePath = typeof
|
|
4641
|
+
const path32 = item.get("path");
|
|
4642
|
+
const effectivePath = typeof path32 === "string" ? path32 : typeof url === "string" ? deriveRepoName(url) : void 0;
|
|
4631
4643
|
return effectivePath === urlOrPath;
|
|
4632
4644
|
});
|
|
4633
4645
|
if (idx < 0) return false;
|
|
@@ -4750,7 +4762,7 @@ async function runAddRepo(input) {
|
|
|
4750
4762
|
"Missing repo URL. Usage: monoceros add-repo <containername> <url>."
|
|
4751
4763
|
);
|
|
4752
4764
|
}
|
|
4753
|
-
const
|
|
4765
|
+
const path32 = (input.path ?? deriveRepoName(url)).trim();
|
|
4754
4766
|
const hasName = typeof input.gitName === "string" && input.gitName.trim().length > 0;
|
|
4755
4767
|
const hasEmail = typeof input.gitEmail === "string" && input.gitEmail.trim().length > 0;
|
|
4756
4768
|
if (hasName !== hasEmail) {
|
|
@@ -4787,7 +4799,7 @@ async function runAddRepo(input) {
|
|
|
4787
4799
|
const providerToWrite = !canonical && explicitProvider ? explicitProvider : void 0;
|
|
4788
4800
|
const entry2 = {
|
|
4789
4801
|
url,
|
|
4790
|
-
path:
|
|
4802
|
+
path: path32,
|
|
4791
4803
|
...hasName && hasEmail ? {
|
|
4792
4804
|
gitUser: {
|
|
4793
4805
|
name: input.gitName.trim(),
|
|
@@ -6607,10 +6619,14 @@ function spawnBridgeDaemon(root) {
|
|
|
6607
6619
|
const self = process.argv[1];
|
|
6608
6620
|
if (!self) return;
|
|
6609
6621
|
mkdirSync(relayDir(root), { recursive: true });
|
|
6610
|
-
const child = spawn8(
|
|
6611
|
-
|
|
6612
|
-
|
|
6613
|
-
|
|
6622
|
+
const child = spawn8(
|
|
6623
|
+
process.execPath,
|
|
6624
|
+
[...process.execArgv, self, "__bridge", root],
|
|
6625
|
+
{
|
|
6626
|
+
detached: true,
|
|
6627
|
+
stdio: "ignore"
|
|
6628
|
+
}
|
|
6629
|
+
);
|
|
6614
6630
|
if (typeof child.pid === "number") {
|
|
6615
6631
|
try {
|
|
6616
6632
|
writeFileSync(bridgePidFile(root), String(child.pid));
|
|
@@ -7207,46 +7223,58 @@ function generateAgentsMd(input) {
|
|
|
7207
7223
|
lines.push("");
|
|
7208
7224
|
lines.push(
|
|
7209
7225
|
"When you build something that serves on a port (a web app, an API),",
|
|
7210
|
-
"
|
|
7211
|
-
"
|
|
7212
|
-
|
|
7213
|
-
`\`${input.containerName}.localhost\` returns 502 Bad Gateway.`
|
|
7226
|
+
"it must keep running after this session ends. A plain `npm start` (or",
|
|
7227
|
+
"any foreground start) dies the moment the user exits you or closes the",
|
|
7228
|
+
`terminal, and then \`${input.containerName}.localhost\` returns 502 Bad Gateway.`
|
|
7214
7229
|
);
|
|
7215
7230
|
lines.push("");
|
|
7216
7231
|
lines.push(
|
|
7217
|
-
"
|
|
7218
|
-
"
|
|
7219
|
-
"
|
|
7232
|
+
"Declare it in the app's own launch config at",
|
|
7233
|
+
"`projects/<app>/.monoceros/launch.json`, then start it with",
|
|
7234
|
+
"`monoceros-ctl`. Add or update an entry whenever you set up a",
|
|
7235
|
+
"long-running server. The file travels with the app, so the human can",
|
|
7236
|
+
"restart it later without knowing your start command:"
|
|
7220
7237
|
);
|
|
7221
7238
|
lines.push("");
|
|
7222
|
-
lines.push("```");
|
|
7239
|
+
lines.push("```json");
|
|
7240
|
+
lines.push("{");
|
|
7241
|
+
lines.push(' "configurations": [');
|
|
7223
7242
|
lines.push(
|
|
7224
|
-
`
|
|
7225
|
-
);
|
|
7226
|
-
lines.push(
|
|
7227
|
-
` exec <the project's start command> >/workspaces/${input.containerName}/logs/<app>.log 2>&1' </dev/null &`
|
|
7243
|
+
` { "name": "web", "command": "<the project's start command>", "port": ${input.ports[0]}, "default": true }`
|
|
7228
7244
|
);
|
|
7245
|
+
lines.push(" ]");
|
|
7246
|
+
lines.push("}");
|
|
7229
7247
|
lines.push("```");
|
|
7230
7248
|
lines.push("");
|
|
7231
7249
|
lines.push(
|
|
7232
|
-
"Use whatever start command the project actually uses (`npm
|
|
7233
|
-
"`./mvnw spring-boot:run`, `python
|
|
7234
|
-
"a language-specific one. `<app>` is
|
|
7250
|
+
"Use whatever start command the project actually uses (`npm run dev`,",
|
|
7251
|
+
"`./mvnw spring-boot:run`, `python manage.py runserver`, `go run .`, \u2026).",
|
|
7252
|
+
"Do not force a language-specific one. `<app>` is the path under",
|
|
7253
|
+
"`projects/`; `port` must be a port already exposed on the container."
|
|
7235
7254
|
);
|
|
7236
7255
|
lines.push("");
|
|
7237
|
-
lines.push("
|
|
7238
|
-
lines.push("like node under npm or java under maven):");
|
|
7256
|
+
lines.push("Start it, stop it, tail its log:");
|
|
7239
7257
|
lines.push("");
|
|
7240
7258
|
lines.push("```");
|
|
7259
|
+
lines.push("monoceros-ctl start <app>");
|
|
7260
|
+
lines.push("monoceros-ctl stop <app>");
|
|
7261
|
+
lines.push("monoceros-ctl logs <app>");
|
|
7262
|
+
lines.push("```");
|
|
7263
|
+
lines.push("");
|
|
7241
7264
|
lines.push(
|
|
7242
|
-
`
|
|
7265
|
+
"`start` launches it detached (it survives your session) and, when a",
|
|
7266
|
+
"`port` is set, waits until it actually listens before returning. Add",
|
|
7267
|
+
"`--target <name>` when the app declares more than one configuration.",
|
|
7268
|
+
"The human can do the same from the host with",
|
|
7269
|
+
`\`monoceros start ${input.containerName} <app>\` / \`monoceros stop ${input.containerName} <app>\`,`,
|
|
7270
|
+
`and follow output with \`monoceros logs ${input.containerName} <app>\`.`
|
|
7243
7271
|
);
|
|
7244
|
-
lines.push("```");
|
|
7245
7272
|
lines.push("");
|
|
7246
7273
|
lines.push(
|
|
7247
|
-
|
|
7248
|
-
"
|
|
7249
|
-
"the
|
|
7274
|
+
"The server must listen on `0.0.0.0` (not `127.0.0.1`) on the exposed",
|
|
7275
|
+
"port, or Traefik cannot reach it. You only have the ports already",
|
|
7276
|
+
"declared on the container; if you need another, ask the human to add it",
|
|
7277
|
+
`on the host (\`monoceros add-port ${input.containerName} <port>\`) and re-apply.`
|
|
7250
7278
|
);
|
|
7251
7279
|
lines.push("");
|
|
7252
7280
|
}
|
|
@@ -8657,7 +8685,7 @@ var CLI_VERSION;
|
|
|
8657
8685
|
var init_version = __esm({
|
|
8658
8686
|
"src/version.ts"() {
|
|
8659
8687
|
"use strict";
|
|
8660
|
-
CLI_VERSION = true ? "1.
|
|
8688
|
+
CLI_VERSION = true ? "1.34.0" : "dev";
|
|
8661
8689
|
}
|
|
8662
8690
|
});
|
|
8663
8691
|
|
|
@@ -8890,9 +8918,144 @@ var init_bridge = __esm({
|
|
|
8890
8918
|
}
|
|
8891
8919
|
});
|
|
8892
8920
|
|
|
8893
|
-
// src/
|
|
8894
|
-
import {
|
|
8921
|
+
// src/config/launch-config.ts
|
|
8922
|
+
import { promises as fs14 } from "fs";
|
|
8895
8923
|
import path24 from "path";
|
|
8924
|
+
function launchConfigPath(name, appRel, home) {
|
|
8925
|
+
return path24.join(
|
|
8926
|
+
containerDir(name, home),
|
|
8927
|
+
"projects",
|
|
8928
|
+
appRel,
|
|
8929
|
+
LAUNCH_DIRNAME,
|
|
8930
|
+
LAUNCH_FILENAME
|
|
8931
|
+
);
|
|
8932
|
+
}
|
|
8933
|
+
function validate(parsed, where) {
|
|
8934
|
+
if (typeof parsed !== "object" || parsed === null) {
|
|
8935
|
+
throw new Error(`${where}: expected a JSON object`);
|
|
8936
|
+
}
|
|
8937
|
+
const obj = parsed;
|
|
8938
|
+
if (!Array.isArray(obj.configurations)) {
|
|
8939
|
+
throw new Error(`${where}: missing "configurations" array`);
|
|
8940
|
+
}
|
|
8941
|
+
const seen = /* @__PURE__ */ new Set();
|
|
8942
|
+
let defaults = 0;
|
|
8943
|
+
const configurations = obj.configurations.map((raw, i) => {
|
|
8944
|
+
if (typeof raw !== "object" || raw === null) {
|
|
8945
|
+
throw new Error(`${where}: configuration #${i} is not an object`);
|
|
8946
|
+
}
|
|
8947
|
+
const t = raw;
|
|
8948
|
+
if (typeof t.name !== "string" || t.name.length === 0) {
|
|
8949
|
+
throw new Error(`${where}: configuration #${i} is missing "name"`);
|
|
8950
|
+
}
|
|
8951
|
+
if (seen.has(t.name)) {
|
|
8952
|
+
throw new Error(`${where}: duplicate target name "${t.name}"`);
|
|
8953
|
+
}
|
|
8954
|
+
seen.add(t.name);
|
|
8955
|
+
if (typeof t.command !== "string" || t.command.length === 0) {
|
|
8956
|
+
throw new Error(`${where}: target "${t.name}" is missing "command"`);
|
|
8957
|
+
}
|
|
8958
|
+
if (t.default === true) defaults += 1;
|
|
8959
|
+
return {
|
|
8960
|
+
name: t.name,
|
|
8961
|
+
command: t.command,
|
|
8962
|
+
...typeof t.cwd === "string" ? { cwd: t.cwd } : {},
|
|
8963
|
+
...typeof t.port === "number" ? { port: t.port } : {},
|
|
8964
|
+
...t.env && typeof t.env === "object" ? { env: t.env } : {},
|
|
8965
|
+
...t.default === true ? { default: true } : {}
|
|
8966
|
+
};
|
|
8967
|
+
});
|
|
8968
|
+
if (defaults > 1) {
|
|
8969
|
+
throw new Error(`${where}: more than one target marked "default"`);
|
|
8970
|
+
}
|
|
8971
|
+
return {
|
|
8972
|
+
version: typeof obj.version === "number" ? obj.version : 1,
|
|
8973
|
+
configurations
|
|
8974
|
+
};
|
|
8975
|
+
}
|
|
8976
|
+
async function readLaunchConfig(name, appRel, home) {
|
|
8977
|
+
const file = launchConfigPath(name, appRel, home);
|
|
8978
|
+
let content;
|
|
8979
|
+
try {
|
|
8980
|
+
content = await fs14.readFile(file, "utf8");
|
|
8981
|
+
} catch {
|
|
8982
|
+
return void 0;
|
|
8983
|
+
}
|
|
8984
|
+
let parsed;
|
|
8985
|
+
try {
|
|
8986
|
+
parsed = JSON.parse(content);
|
|
8987
|
+
} catch (err) {
|
|
8988
|
+
throw new Error(
|
|
8989
|
+
`${file}: invalid JSON (${err instanceof Error ? err.message : String(err)})`
|
|
8990
|
+
);
|
|
8991
|
+
}
|
|
8992
|
+
return validate(parsed, file);
|
|
8993
|
+
}
|
|
8994
|
+
function resolveTarget(config, targetName, appRel) {
|
|
8995
|
+
if (targetName) {
|
|
8996
|
+
const found = config.configurations.find((t) => t.name === targetName);
|
|
8997
|
+
if (!found) {
|
|
8998
|
+
throw new Error(
|
|
8999
|
+
`No target "${targetName}" in ${appRel} (have: ${config.configurations.map((t) => t.name).join(", ") || "none"})`
|
|
9000
|
+
);
|
|
9001
|
+
}
|
|
9002
|
+
return found;
|
|
9003
|
+
}
|
|
9004
|
+
const marked = config.configurations.find((t) => t.default);
|
|
9005
|
+
if (marked) return marked;
|
|
9006
|
+
if (config.configurations.length === 1) return config.configurations[0];
|
|
9007
|
+
throw new Error(
|
|
9008
|
+
`${appRel} has ${config.configurations.length} targets and no default \u2014 pass --target (${config.configurations.map((t) => t.name).join(", ")})`
|
|
9009
|
+
);
|
|
9010
|
+
}
|
|
9011
|
+
async function listApps(name, home) {
|
|
9012
|
+
const projectsRoot = path24.join(containerDir(name, home), "projects");
|
|
9013
|
+
const out = [];
|
|
9014
|
+
async function walk(at, rel, depth) {
|
|
9015
|
+
let entries;
|
|
9016
|
+
try {
|
|
9017
|
+
entries = await fs14.readdir(at, { withFileTypes: true });
|
|
9018
|
+
} catch {
|
|
9019
|
+
return;
|
|
9020
|
+
}
|
|
9021
|
+
const hasLaunch = entries.some(
|
|
9022
|
+
(e) => e.isDirectory() && e.name === LAUNCH_DIRNAME
|
|
9023
|
+
);
|
|
9024
|
+
if (hasLaunch) {
|
|
9025
|
+
try {
|
|
9026
|
+
await fs14.access(path24.join(at, LAUNCH_DIRNAME, LAUNCH_FILENAME));
|
|
9027
|
+
if (rel) out.push(rel);
|
|
9028
|
+
} catch {
|
|
9029
|
+
}
|
|
9030
|
+
}
|
|
9031
|
+
if (depth >= APP_SEARCH_MAX_DEPTH) return;
|
|
9032
|
+
for (const e of entries) {
|
|
9033
|
+
if (!e.isDirectory()) continue;
|
|
9034
|
+
if (e.name.startsWith(".")) continue;
|
|
9035
|
+
await walk(
|
|
9036
|
+
path24.join(at, e.name),
|
|
9037
|
+
rel ? `${rel}/${e.name}` : e.name,
|
|
9038
|
+
depth + 1
|
|
9039
|
+
);
|
|
9040
|
+
}
|
|
9041
|
+
}
|
|
9042
|
+
await walk(projectsRoot, "", 0);
|
|
9043
|
+
return out.sort();
|
|
9044
|
+
}
|
|
9045
|
+
var LAUNCH_DIRNAME, LAUNCH_FILENAME, APP_SEARCH_MAX_DEPTH;
|
|
9046
|
+
var init_launch_config = __esm({
|
|
9047
|
+
"src/config/launch-config.ts"() {
|
|
9048
|
+
"use strict";
|
|
9049
|
+
init_paths();
|
|
9050
|
+
LAUNCH_DIRNAME = ".monoceros";
|
|
9051
|
+
LAUNCH_FILENAME = "launch.json";
|
|
9052
|
+
APP_SEARCH_MAX_DEPTH = 4;
|
|
9053
|
+
}
|
|
9054
|
+
});
|
|
9055
|
+
|
|
9056
|
+
// src/completion/resolve.ts
|
|
9057
|
+
import { existsSync as existsSync15, promises as fs15 } from "fs";
|
|
9058
|
+
import path25 from "path";
|
|
8896
9059
|
async function resolveCompletions(line, point, opts = {}) {
|
|
8897
9060
|
const { prev, current } = parseCompletionLine(line, point);
|
|
8898
9061
|
const ctx = { prev, current, opts };
|
|
@@ -9041,9 +9204,9 @@ function filterPrefix(values, fragment) {
|
|
|
9041
9204
|
}
|
|
9042
9205
|
async function listContainerNames(ctx) {
|
|
9043
9206
|
const home = ctx.opts.monocerosHome ?? monocerosHome();
|
|
9044
|
-
const dir =
|
|
9207
|
+
const dir = path25.join(home, "container-configs");
|
|
9045
9208
|
if (!existsSync15(dir)) return [];
|
|
9046
|
-
const entries = await
|
|
9209
|
+
const entries = await fs15.readdir(dir);
|
|
9047
9210
|
return entries.filter((e) => e.endsWith(".yml")).map((e) => e.slice(0, -".yml".length)).sort();
|
|
9048
9211
|
}
|
|
9049
9212
|
function containerNameFromCtx(ctx) {
|
|
@@ -9055,12 +9218,42 @@ function containerNameFromCtx(ctx) {
|
|
|
9055
9218
|
}
|
|
9056
9219
|
return void 0;
|
|
9057
9220
|
}
|
|
9221
|
+
function positionalFromCtx(ctx, n) {
|
|
9222
|
+
const positionals = [];
|
|
9223
|
+
for (let i = 2; i < ctx.prev.length; i++) {
|
|
9224
|
+
const t = ctx.prev[i];
|
|
9225
|
+
if (t === "--") break;
|
|
9226
|
+
if (t.startsWith("-")) continue;
|
|
9227
|
+
positionals.push(t);
|
|
9228
|
+
}
|
|
9229
|
+
return positionals[n];
|
|
9230
|
+
}
|
|
9231
|
+
async function listAppCandidates(ctx) {
|
|
9232
|
+
const name = containerNameFromCtx(ctx);
|
|
9233
|
+
if (!name) return [];
|
|
9234
|
+
try {
|
|
9235
|
+
return await listApps(name, ctx.opts.monocerosHome);
|
|
9236
|
+
} catch {
|
|
9237
|
+
return [];
|
|
9238
|
+
}
|
|
9239
|
+
}
|
|
9240
|
+
async function listTargetCandidates(ctx) {
|
|
9241
|
+
const name = containerNameFromCtx(ctx);
|
|
9242
|
+
const app = positionalFromCtx(ctx, 1);
|
|
9243
|
+
if (!name || !app) return [];
|
|
9244
|
+
try {
|
|
9245
|
+
const cfg = await readLaunchConfig(name, app, ctx.opts.monocerosHome);
|
|
9246
|
+
return cfg ? cfg.configurations.map((t) => t.name) : [];
|
|
9247
|
+
} catch {
|
|
9248
|
+
return [];
|
|
9249
|
+
}
|
|
9250
|
+
}
|
|
9058
9251
|
async function collectDirs(dir, maxDepth) {
|
|
9059
9252
|
const out = [];
|
|
9060
9253
|
async function walk(at, rel, depth) {
|
|
9061
9254
|
let entries;
|
|
9062
9255
|
try {
|
|
9063
|
-
entries = await
|
|
9256
|
+
entries = await fs15.readdir(at, { withFileTypes: true });
|
|
9064
9257
|
} catch {
|
|
9065
9258
|
return;
|
|
9066
9259
|
}
|
|
@@ -9071,7 +9264,7 @@ async function collectDirs(dir, maxDepth) {
|
|
|
9071
9264
|
const childRel = rel ? `${rel}/${e.name}` : e.name;
|
|
9072
9265
|
out.push(childRel);
|
|
9073
9266
|
if (depth + 1 < maxDepth) {
|
|
9074
|
-
await walk(
|
|
9267
|
+
await walk(path25.join(at, e.name), childRel, depth + 1);
|
|
9075
9268
|
}
|
|
9076
9269
|
}
|
|
9077
9270
|
}
|
|
@@ -9079,9 +9272,9 @@ async function collectDirs(dir, maxDepth) {
|
|
|
9079
9272
|
return out;
|
|
9080
9273
|
}
|
|
9081
9274
|
async function listContainerWorkspaceDirs(home, name) {
|
|
9082
|
-
const root =
|
|
9275
|
+
const root = path25.join(home, "container", name);
|
|
9083
9276
|
const top = await collectDirs(root, 1);
|
|
9084
|
-
const projects = (await collectDirs(
|
|
9277
|
+
const projects = (await collectDirs(path25.join(root, "projects"), PROJECTS_DIR_MAX_DEPTH)).map((p) => `projects/${p}`);
|
|
9085
9278
|
return [.../* @__PURE__ */ new Set([...top, ...projects])].sort();
|
|
9086
9279
|
}
|
|
9087
9280
|
async function listRunInDirs(ctx) {
|
|
@@ -9157,6 +9350,7 @@ var init_resolve = __esm({
|
|
|
9157
9350
|
"src/completion/resolve.ts"() {
|
|
9158
9351
|
"use strict";
|
|
9159
9352
|
init_paths();
|
|
9353
|
+
init_launch_config();
|
|
9160
9354
|
init_components();
|
|
9161
9355
|
init_manifest();
|
|
9162
9356
|
init_catalog();
|
|
@@ -9166,6 +9360,7 @@ var init_resolve = __esm({
|
|
|
9166
9360
|
PROJECTS_DIR_MAX_DEPTH = 4;
|
|
9167
9361
|
ALL_COMMANDS = [
|
|
9168
9362
|
"init",
|
|
9363
|
+
"list-apps",
|
|
9169
9364
|
"list-components",
|
|
9170
9365
|
"shell",
|
|
9171
9366
|
"open",
|
|
@@ -9242,13 +9437,27 @@ var init_resolve = __esm({
|
|
|
9242
9437
|
positionals: [containerName],
|
|
9243
9438
|
flags: { "--in": { type: "value", values: (ctx) => listRunInDirs(ctx) } }
|
|
9244
9439
|
},
|
|
9245
|
-
logs: {
|
|
9440
|
+
logs: {
|
|
9441
|
+
positionals: [containerName, (ctx) => listAppCandidates(ctx)],
|
|
9442
|
+
flags: {
|
|
9443
|
+
"--target": { type: "value", values: (ctx) => listTargetCandidates(ctx) }
|
|
9444
|
+
}
|
|
9445
|
+
},
|
|
9246
9446
|
start: {
|
|
9247
|
-
positionals: [containerName],
|
|
9248
|
-
flags: {
|
|
9447
|
+
positionals: [containerName, (ctx) => listAppCandidates(ctx)],
|
|
9448
|
+
flags: {
|
|
9449
|
+
"--target": { type: "value", values: (ctx) => listTargetCandidates(ctx) },
|
|
9450
|
+
"--open": { type: "value", values: () => [...OPEN_TOOLS] }
|
|
9451
|
+
}
|
|
9452
|
+
},
|
|
9453
|
+
stop: {
|
|
9454
|
+
positionals: [containerName, (ctx) => listAppCandidates(ctx)],
|
|
9455
|
+
flags: {
|
|
9456
|
+
"--target": { type: "value", values: (ctx) => listTargetCandidates(ctx) }
|
|
9457
|
+
}
|
|
9249
9458
|
},
|
|
9250
|
-
stop: { positionals: [containerName] },
|
|
9251
9459
|
status: { positionals: [containerName] },
|
|
9460
|
+
"list-apps": { positionals: [containerName] },
|
|
9252
9461
|
"add-language": {
|
|
9253
9462
|
positionals: [containerName, () => listLanguageNames()]
|
|
9254
9463
|
},
|
|
@@ -9911,8 +10120,8 @@ var init_generator = __esm({
|
|
|
9911
10120
|
});
|
|
9912
10121
|
|
|
9913
10122
|
// src/init/index.ts
|
|
9914
|
-
import { existsSync as existsSync16, promises as
|
|
9915
|
-
import
|
|
10123
|
+
import { existsSync as existsSync16, promises as fs16 } from "fs";
|
|
10124
|
+
import path26 from "path";
|
|
9916
10125
|
import { consola as consola16 } from "consola";
|
|
9917
10126
|
async function runInit(opts) {
|
|
9918
10127
|
const home = opts.monocerosHome ?? monocerosHome();
|
|
@@ -9931,7 +10140,7 @@ async function runInit(opts) {
|
|
|
9931
10140
|
`Config already exists: ${dest}. Delete it manually before re-running \`monoceros init\` \u2014 this protects any hand-edits.`
|
|
9932
10141
|
);
|
|
9933
10142
|
}
|
|
9934
|
-
const componentsRoot = opts.workbenchRoot ?
|
|
10143
|
+
const componentsRoot = opts.workbenchRoot ? path26.join(opts.workbenchRoot, "components") : componentsRootDir();
|
|
9935
10144
|
const catalog = await loadComponentCatalog(componentsRoot);
|
|
9936
10145
|
if (catalog.size === 0) {
|
|
9937
10146
|
throw new Error(
|
|
@@ -9997,9 +10206,9 @@ async function runInit(opts) {
|
|
|
9997
10206
|
} else {
|
|
9998
10207
|
text = generateComposedYml(opts.name, composed, lookup, repos, ports);
|
|
9999
10208
|
}
|
|
10000
|
-
await
|
|
10209
|
+
await fs16.mkdir(containerConfigsDir(home), { recursive: true });
|
|
10001
10210
|
await ensureEnvGitignored(containerConfigsDir(home));
|
|
10002
|
-
await
|
|
10211
|
+
await fs16.writeFile(dest, text, "utf8");
|
|
10003
10212
|
const envPath = containerEnvPath(opts.name, home);
|
|
10004
10213
|
const seedVars = {};
|
|
10005
10214
|
for (const f of composed.features) {
|
|
@@ -10022,8 +10231,8 @@ async function runInit(opts) {
|
|
|
10022
10231
|
}
|
|
10023
10232
|
await ensureEnvVars(envPath, opts.name, seedVars);
|
|
10024
10233
|
const documented = !anyComposed;
|
|
10025
|
-
const ymlRel =
|
|
10026
|
-
const envRel =
|
|
10234
|
+
const ymlRel = path26.relative(home, dest);
|
|
10235
|
+
const envRel = path26.relative(home, envPath);
|
|
10027
10236
|
if (documented) {
|
|
10028
10237
|
logger.success(`Wrote documented default to ${ymlRel} and ${envRel}.`);
|
|
10029
10238
|
logger.info(
|
|
@@ -10301,6 +10510,75 @@ var init_init2 = __esm({
|
|
|
10301
10510
|
}
|
|
10302
10511
|
});
|
|
10303
10512
|
|
|
10513
|
+
// src/commands/list-apps.ts
|
|
10514
|
+
import { defineCommand as defineCommand14 } from "citty";
|
|
10515
|
+
import { consola as consola18 } from "consola";
|
|
10516
|
+
var listAppsCommand;
|
|
10517
|
+
var init_list_apps = __esm({
|
|
10518
|
+
"src/commands/list-apps.ts"() {
|
|
10519
|
+
"use strict";
|
|
10520
|
+
init_launch_config();
|
|
10521
|
+
init_format();
|
|
10522
|
+
listAppsCommand = defineCommand14({
|
|
10523
|
+
meta: {
|
|
10524
|
+
name: "list-apps",
|
|
10525
|
+
group: "discovery",
|
|
10526
|
+
description: "List the apps under the named container that declare a launch config (projects/<app>/.monoceros/launch.json), with their targets and which is the default. Pure host-side filesystem read \u2014 works with the container stopped. Parallels `list-components`."
|
|
10527
|
+
},
|
|
10528
|
+
args: {
|
|
10529
|
+
name: {
|
|
10530
|
+
type: "positional",
|
|
10531
|
+
description: "Container name (yml in $MONOCEROS_HOME/container-configs/).",
|
|
10532
|
+
required: true
|
|
10533
|
+
}
|
|
10534
|
+
},
|
|
10535
|
+
async run({ args }) {
|
|
10536
|
+
try {
|
|
10537
|
+
const apps = await listApps(args.name);
|
|
10538
|
+
if (apps.length === 0) {
|
|
10539
|
+
consola18.info(
|
|
10540
|
+
`No apps with a launch config under "${args.name}" (projects/<app>/.monoceros/launch.json).`
|
|
10541
|
+
);
|
|
10542
|
+
process.exit(0);
|
|
10543
|
+
}
|
|
10544
|
+
const fmt = colorsFor(process.stdout);
|
|
10545
|
+
const isTty2 = process.stdout.isTTY ?? false;
|
|
10546
|
+
for (const app of apps) {
|
|
10547
|
+
const cfg = await readLaunchConfig(args.name, app);
|
|
10548
|
+
if (!cfg) continue;
|
|
10549
|
+
if (isTty2) {
|
|
10550
|
+
process.stdout.write(`${fmt.cyan(app)}
|
|
10551
|
+
`);
|
|
10552
|
+
} else {
|
|
10553
|
+
process.stdout.write(`${app}
|
|
10554
|
+
`);
|
|
10555
|
+
}
|
|
10556
|
+
for (const t of cfg.configurations) {
|
|
10557
|
+
const flags = [];
|
|
10558
|
+
if (t.default) flags.push("default");
|
|
10559
|
+
if (typeof t.port === "number") flags.push(`port ${t.port}`);
|
|
10560
|
+
const suffix = flags.length > 0 ? ` (${flags.join(", ")})` : "";
|
|
10561
|
+
if (isTty2) {
|
|
10562
|
+
process.stdout.write(` ${t.name}${suffix}
|
|
10563
|
+
`);
|
|
10564
|
+
} else {
|
|
10565
|
+
process.stdout.write(
|
|
10566
|
+
`${app} ${t.name} ${t.default ? "default" : ""} ${t.port ?? ""}
|
|
10567
|
+
`
|
|
10568
|
+
);
|
|
10569
|
+
}
|
|
10570
|
+
}
|
|
10571
|
+
}
|
|
10572
|
+
process.exit(0);
|
|
10573
|
+
} catch (err) {
|
|
10574
|
+
consola18.error(err instanceof Error ? err.message : String(err));
|
|
10575
|
+
process.exit(1);
|
|
10576
|
+
}
|
|
10577
|
+
}
|
|
10578
|
+
});
|
|
10579
|
+
}
|
|
10580
|
+
});
|
|
10581
|
+
|
|
10304
10582
|
// src/catalog/expand.ts
|
|
10305
10583
|
function expandSelectable(catalog) {
|
|
10306
10584
|
const out = /* @__PURE__ */ new Map();
|
|
@@ -10409,8 +10687,8 @@ var init_catalog_json = __esm({
|
|
|
10409
10687
|
});
|
|
10410
10688
|
|
|
10411
10689
|
// src/commands/list-components.ts
|
|
10412
|
-
import { defineCommand as
|
|
10413
|
-
import { consola as
|
|
10690
|
+
import { defineCommand as defineCommand15 } from "citty";
|
|
10691
|
+
import { consola as consola19 } from "consola";
|
|
10414
10692
|
var CATEGORY_LABELS, CATEGORY_ORDER, listComponentsCommand;
|
|
10415
10693
|
var init_list_components = __esm({
|
|
10416
10694
|
"src/commands/list-components.ts"() {
|
|
@@ -10430,7 +10708,7 @@ var init_list_components = __esm({
|
|
|
10430
10708
|
"service",
|
|
10431
10709
|
"feature"
|
|
10432
10710
|
];
|
|
10433
|
-
listComponentsCommand =
|
|
10711
|
+
listComponentsCommand = defineCommand15({
|
|
10434
10712
|
meta: {
|
|
10435
10713
|
name: "list-components",
|
|
10436
10714
|
group: "discovery",
|
|
@@ -10453,7 +10731,7 @@ var init_list_components = __esm({
|
|
|
10453
10731
|
}
|
|
10454
10732
|
const catalog = expandSelectable(descriptors);
|
|
10455
10733
|
if (catalog.size === 0) {
|
|
10456
|
-
|
|
10734
|
+
consola19.warn(
|
|
10457
10735
|
"No components found. The workbench checkout looks incomplete."
|
|
10458
10736
|
);
|
|
10459
10737
|
process.exit(0);
|
|
@@ -10504,7 +10782,7 @@ var init_list_components = __esm({
|
|
|
10504
10782
|
}
|
|
10505
10783
|
process.exit(0);
|
|
10506
10784
|
} catch (err) {
|
|
10507
|
-
|
|
10785
|
+
consola19.error(err instanceof Error ? err.message : String(err));
|
|
10508
10786
|
process.exit(1);
|
|
10509
10787
|
}
|
|
10510
10788
|
}
|
|
@@ -10514,9 +10792,9 @@ var init_list_components = __esm({
|
|
|
10514
10792
|
|
|
10515
10793
|
// src/commands/logs.ts
|
|
10516
10794
|
import { spawn as spawn13 } from "child_process";
|
|
10517
|
-
import
|
|
10518
|
-
import
|
|
10519
|
-
import {
|
|
10795
|
+
import path27 from "path";
|
|
10796
|
+
import { defineCommand as defineCommand16 } from "citty";
|
|
10797
|
+
import { consola as consola20 } from "consola";
|
|
10520
10798
|
function tailLogFile(file, follow) {
|
|
10521
10799
|
const [cmd, args] = follow ? ["tail", ["-F", file]] : ["cat", [file]];
|
|
10522
10800
|
return new Promise((resolve, reject) => {
|
|
@@ -10530,13 +10808,14 @@ var init_logs = __esm({
|
|
|
10530
10808
|
"src/commands/logs.ts"() {
|
|
10531
10809
|
"use strict";
|
|
10532
10810
|
init_paths();
|
|
10811
|
+
init_launch_config();
|
|
10533
10812
|
init_compose();
|
|
10534
10813
|
init_dispatch();
|
|
10535
|
-
logsCommand =
|
|
10814
|
+
logsCommand = defineCommand16({
|
|
10536
10815
|
meta: {
|
|
10537
10816
|
name: "logs",
|
|
10538
10817
|
group: "run",
|
|
10539
|
-
description: "Tail logs from a compose service of the named dev-container, or from a long-running app started inside it
|
|
10818
|
+
description: "Tail logs from a compose service of the named dev-container, or from a long-running app started inside it. Pass --no-follow for a one-shot dump."
|
|
10540
10819
|
},
|
|
10541
10820
|
args: {
|
|
10542
10821
|
name: {
|
|
@@ -10544,9 +10823,14 @@ var init_logs = __esm({
|
|
|
10544
10823
|
description: "Container name (yml in $MONOCEROS_HOME/container-configs/).",
|
|
10545
10824
|
required: true
|
|
10546
10825
|
},
|
|
10547
|
-
|
|
10826
|
+
app: {
|
|
10827
|
+
type: "positional",
|
|
10828
|
+
description: "An app (a path under projects/ with .monoceros/launch.json) whose log to tail, or a compose service (e.g. postgres). Defaults to all compose services.",
|
|
10829
|
+
required: false
|
|
10830
|
+
},
|
|
10831
|
+
target: {
|
|
10548
10832
|
type: "string",
|
|
10549
|
-
description:
|
|
10833
|
+
description: 'Which launch target of the app to tail (defaults to its "default" target, or its only one).'
|
|
10550
10834
|
},
|
|
10551
10835
|
follow: {
|
|
10552
10836
|
type: "boolean",
|
|
@@ -10556,34 +10840,47 @@ var init_logs = __esm({
|
|
|
10556
10840
|
}
|
|
10557
10841
|
},
|
|
10558
10842
|
run({ args }) {
|
|
10559
|
-
const
|
|
10560
|
-
|
|
10561
|
-
|
|
10562
|
-
if (
|
|
10563
|
-
|
|
10843
|
+
const app = typeof args.app === "string" ? args.app : void 0;
|
|
10844
|
+
const target = typeof args.target === "string" ? args.target : void 0;
|
|
10845
|
+
return dispatch(async () => {
|
|
10846
|
+
if (app) {
|
|
10847
|
+
const cfg = await readLaunchConfig(args.name, app);
|
|
10848
|
+
if (cfg) {
|
|
10849
|
+
const t = resolveTarget(cfg, target, app);
|
|
10850
|
+
const logFile = path27.join(
|
|
10851
|
+
containerLogsDir(args.name),
|
|
10852
|
+
app,
|
|
10853
|
+
`${t.name}.log`
|
|
10854
|
+
);
|
|
10855
|
+
return tailLogFile(logFile, args.follow);
|
|
10856
|
+
}
|
|
10857
|
+
if (target) {
|
|
10858
|
+
consola20.warn(
|
|
10859
|
+
`No launch config for "${app}" \u2014 ignoring --target and treating "${app}" as a compose service.`
|
|
10860
|
+
);
|
|
10861
|
+
}
|
|
10862
|
+
return runLogs({
|
|
10863
|
+
root: containerDir(args.name),
|
|
10864
|
+
service: app,
|
|
10865
|
+
follow: args.follow
|
|
10866
|
+
});
|
|
10564
10867
|
}
|
|
10565
|
-
|
|
10566
|
-
|
|
10567
|
-
() => runLogs({
|
|
10568
|
-
root: containerDir(args.name),
|
|
10569
|
-
...service ? { service } : {},
|
|
10570
|
-
follow: args.follow
|
|
10571
|
-
})
|
|
10572
|
-
);
|
|
10868
|
+
return runLogs({ root: containerDir(args.name), follow: args.follow });
|
|
10869
|
+
});
|
|
10573
10870
|
}
|
|
10574
10871
|
});
|
|
10575
10872
|
}
|
|
10576
10873
|
});
|
|
10577
10874
|
|
|
10578
10875
|
// src/commands/open.ts
|
|
10579
|
-
import { defineCommand as
|
|
10876
|
+
import { defineCommand as defineCommand17 } from "citty";
|
|
10580
10877
|
var openCommand;
|
|
10581
10878
|
var init_open2 = __esm({
|
|
10582
10879
|
"src/commands/open.ts"() {
|
|
10583
10880
|
"use strict";
|
|
10584
10881
|
init_open();
|
|
10585
10882
|
init_dispatch();
|
|
10586
|
-
openCommand =
|
|
10883
|
+
openCommand = defineCommand17({
|
|
10587
10884
|
meta: {
|
|
10588
10885
|
name: "open",
|
|
10589
10886
|
group: "run",
|
|
@@ -10609,11 +10906,11 @@ var init_open2 = __esm({
|
|
|
10609
10906
|
});
|
|
10610
10907
|
|
|
10611
10908
|
// src/commands/port.ts
|
|
10612
|
-
import { defineCommand as
|
|
10613
|
-
import { consola as
|
|
10909
|
+
import { defineCommand as defineCommand18 } from "citty";
|
|
10910
|
+
import { consola as consola21 } from "consola";
|
|
10614
10911
|
async function runPortListing(opts) {
|
|
10615
10912
|
const out = opts.out ?? process.stdout;
|
|
10616
|
-
const info = opts.info ?? ((m) =>
|
|
10913
|
+
const info = opts.info ?? ((m) => consola21.info(m));
|
|
10617
10914
|
const parsed = await readConfig(
|
|
10618
10915
|
containerConfigPath(opts.name, opts.monocerosHome)
|
|
10619
10916
|
);
|
|
@@ -10671,7 +10968,7 @@ var init_port = __esm({
|
|
|
10671
10968
|
init_schema();
|
|
10672
10969
|
init_dynamic();
|
|
10673
10970
|
init_format();
|
|
10674
|
-
portCommand =
|
|
10971
|
+
portCommand = defineCommand18({
|
|
10675
10972
|
meta: {
|
|
10676
10973
|
name: "port",
|
|
10677
10974
|
group: "discovery",
|
|
@@ -10689,7 +10986,7 @@ var init_port = __esm({
|
|
|
10689
10986
|
const code = await runPortListing({ name: args.name });
|
|
10690
10987
|
process.exit(code);
|
|
10691
10988
|
} catch (err) {
|
|
10692
|
-
|
|
10989
|
+
consola21.error(err instanceof Error ? err.message : String(err));
|
|
10693
10990
|
process.exit(1);
|
|
10694
10991
|
}
|
|
10695
10992
|
}
|
|
@@ -10698,15 +10995,15 @@ var init_port = __esm({
|
|
|
10698
10995
|
});
|
|
10699
10996
|
|
|
10700
10997
|
// src/commands/remove-apt-packages.ts
|
|
10701
|
-
import { defineCommand as
|
|
10702
|
-
import { consola as
|
|
10998
|
+
import { defineCommand as defineCommand19 } from "citty";
|
|
10999
|
+
import { consola as consola22 } from "consola";
|
|
10703
11000
|
var removeAptPackagesCommand;
|
|
10704
11001
|
var init_remove_apt_packages = __esm({
|
|
10705
11002
|
"src/commands/remove-apt-packages.ts"() {
|
|
10706
11003
|
"use strict";
|
|
10707
11004
|
init_inner_args();
|
|
10708
11005
|
init_modify();
|
|
10709
|
-
removeAptPackagesCommand =
|
|
11006
|
+
removeAptPackagesCommand = defineCommand19({
|
|
10710
11007
|
meta: {
|
|
10711
11008
|
name: "remove-apt-packages",
|
|
10712
11009
|
group: "edit",
|
|
@@ -10728,7 +11025,7 @@ var init_remove_apt_packages = __esm({
|
|
|
10728
11025
|
async run({ args }) {
|
|
10729
11026
|
const packages = [...getInnerArgs()];
|
|
10730
11027
|
if (packages.length === 0) {
|
|
10731
|
-
|
|
11028
|
+
consola22.error(
|
|
10732
11029
|
"No package names given. Usage: `monoceros remove-apt-packages <containername> [--yes] -- <pkg> [<pkg> \u2026]`."
|
|
10733
11030
|
);
|
|
10734
11031
|
process.exit(1);
|
|
@@ -10741,7 +11038,7 @@ var init_remove_apt_packages = __esm({
|
|
|
10741
11038
|
});
|
|
10742
11039
|
process.exit(result.status === "aborted" ? 1 : 0);
|
|
10743
11040
|
} catch (err) {
|
|
10744
|
-
|
|
11041
|
+
consola22.error(err instanceof Error ? err.message : String(err));
|
|
10745
11042
|
process.exit(1);
|
|
10746
11043
|
}
|
|
10747
11044
|
}
|
|
@@ -10750,14 +11047,14 @@ var init_remove_apt_packages = __esm({
|
|
|
10750
11047
|
});
|
|
10751
11048
|
|
|
10752
11049
|
// src/commands/remove-feature.ts
|
|
10753
|
-
import { defineCommand as
|
|
10754
|
-
import { consola as
|
|
11050
|
+
import { defineCommand as defineCommand20 } from "citty";
|
|
11051
|
+
import { consola as consola23 } from "consola";
|
|
10755
11052
|
var removeFeatureCommand;
|
|
10756
11053
|
var init_remove_feature = __esm({
|
|
10757
11054
|
"src/commands/remove-feature.ts"() {
|
|
10758
11055
|
"use strict";
|
|
10759
11056
|
init_modify();
|
|
10760
|
-
removeFeatureCommand =
|
|
11057
|
+
removeFeatureCommand = defineCommand20({
|
|
10761
11058
|
meta: {
|
|
10762
11059
|
name: "remove-feature",
|
|
10763
11060
|
group: "edit",
|
|
@@ -10790,7 +11087,7 @@ var init_remove_feature = __esm({
|
|
|
10790
11087
|
});
|
|
10791
11088
|
process.exit(result.status === "aborted" ? 1 : 0);
|
|
10792
11089
|
} catch (err) {
|
|
10793
|
-
|
|
11090
|
+
consola23.error(err instanceof Error ? err.message : String(err));
|
|
10794
11091
|
process.exit(1);
|
|
10795
11092
|
}
|
|
10796
11093
|
}
|
|
@@ -10799,15 +11096,15 @@ var init_remove_feature = __esm({
|
|
|
10799
11096
|
});
|
|
10800
11097
|
|
|
10801
11098
|
// src/remove/index.ts
|
|
10802
|
-
import { existsSync as
|
|
10803
|
-
import
|
|
10804
|
-
import { consola as
|
|
11099
|
+
import { existsSync as existsSync17, promises as fs17 } from "fs";
|
|
11100
|
+
import path28 from "path";
|
|
11101
|
+
import { consola as consola24 } from "consola";
|
|
10805
11102
|
async function runRemove(opts) {
|
|
10806
11103
|
const home = opts.monocerosHome ?? monocerosHome();
|
|
10807
11104
|
const logger = opts.logger ?? {
|
|
10808
|
-
info: (msg) =>
|
|
10809
|
-
success: (msg) =>
|
|
10810
|
-
warn: (msg) =>
|
|
11105
|
+
info: (msg) => consola24.info(msg),
|
|
11106
|
+
success: (msg) => consola24.success(msg),
|
|
11107
|
+
warn: (msg) => consola24.warn(msg)
|
|
10811
11108
|
};
|
|
10812
11109
|
if (!REGEX.solutionName.test(opts.name)) {
|
|
10813
11110
|
throw new Error(
|
|
@@ -10817,9 +11114,9 @@ async function runRemove(opts) {
|
|
|
10817
11114
|
const ymlPath = containerConfigPath(opts.name, home);
|
|
10818
11115
|
const envPath = containerEnvPath(opts.name, home);
|
|
10819
11116
|
const containerPath = containerDir(opts.name, home);
|
|
10820
|
-
const hasYml =
|
|
10821
|
-
const hasEnv =
|
|
10822
|
-
const hasContainer =
|
|
11117
|
+
const hasYml = existsSync17(ymlPath);
|
|
11118
|
+
const hasEnv = existsSync17(envPath);
|
|
11119
|
+
const hasContainer = existsSync17(containerPath);
|
|
10823
11120
|
if (!hasYml && !hasContainer) {
|
|
10824
11121
|
throw new Error(
|
|
10825
11122
|
`Nothing to remove for '${opts.name}': neither ${ymlPath} nor ${containerPath} exists.`
|
|
@@ -10845,16 +11142,16 @@ async function runRemove(opts) {
|
|
|
10845
11142
|
let backupPath = null;
|
|
10846
11143
|
if (!opts.noBackup && (hasYml || hasContainer)) {
|
|
10847
11144
|
const ts = (opts.now ?? /* @__PURE__ */ new Date()).toISOString().replace(/[:.]/g, "-");
|
|
10848
|
-
backupPath =
|
|
10849
|
-
await
|
|
11145
|
+
backupPath = path28.join(home, "container-backups", `${opts.name}-${ts}`);
|
|
11146
|
+
await fs17.mkdir(backupPath, { recursive: true });
|
|
10850
11147
|
if (hasYml) {
|
|
10851
|
-
await
|
|
11148
|
+
await fs17.copyFile(ymlPath, path28.join(backupPath, `${opts.name}.yml`));
|
|
10852
11149
|
}
|
|
10853
11150
|
if (hasEnv) {
|
|
10854
|
-
await
|
|
11151
|
+
await fs17.copyFile(envPath, path28.join(backupPath, `${opts.name}.env`));
|
|
10855
11152
|
}
|
|
10856
11153
|
if (hasContainer) {
|
|
10857
|
-
await
|
|
11154
|
+
await fs17.cp(containerPath, path28.join(backupPath, "container"), {
|
|
10858
11155
|
recursive: true
|
|
10859
11156
|
});
|
|
10860
11157
|
}
|
|
@@ -10864,14 +11161,14 @@ async function runRemove(opts) {
|
|
|
10864
11161
|
await stopBridgeDaemon(containerPath);
|
|
10865
11162
|
}
|
|
10866
11163
|
if (hasYml) {
|
|
10867
|
-
await
|
|
11164
|
+
await fs17.rm(ymlPath, { force: true });
|
|
10868
11165
|
}
|
|
10869
11166
|
if (hasEnv) {
|
|
10870
|
-
await
|
|
11167
|
+
await fs17.rm(envPath, { force: true });
|
|
10871
11168
|
}
|
|
10872
11169
|
if (hasContainer) {
|
|
10873
11170
|
try {
|
|
10874
|
-
await
|
|
11171
|
+
await fs17.rm(containerPath, { recursive: true, force: true });
|
|
10875
11172
|
} catch (err) {
|
|
10876
11173
|
const code = err.code;
|
|
10877
11174
|
if (code !== "EACCES" && code !== "EPERM") {
|
|
@@ -10893,7 +11190,7 @@ async function runRemove(opts) {
|
|
|
10893
11190
|
"-delete"
|
|
10894
11191
|
]);
|
|
10895
11192
|
try {
|
|
10896
|
-
await
|
|
11193
|
+
await fs17.rm(containerPath, { recursive: true, force: true });
|
|
10897
11194
|
} catch (err2) {
|
|
10898
11195
|
const code2 = err2.code;
|
|
10899
11196
|
throw new Error(
|
|
@@ -10957,15 +11254,15 @@ var init_remove = __esm({
|
|
|
10957
11254
|
});
|
|
10958
11255
|
|
|
10959
11256
|
// src/commands/remove.ts
|
|
10960
|
-
import { defineCommand as
|
|
10961
|
-
import { consola as
|
|
11257
|
+
import { defineCommand as defineCommand21 } from "citty";
|
|
11258
|
+
import { consola as consola25 } from "consola";
|
|
10962
11259
|
import { createInterface } from "readline/promises";
|
|
10963
11260
|
var removeCommand;
|
|
10964
11261
|
var init_remove2 = __esm({
|
|
10965
11262
|
"src/commands/remove.ts"() {
|
|
10966
11263
|
"use strict";
|
|
10967
11264
|
init_remove();
|
|
10968
|
-
removeCommand =
|
|
11265
|
+
removeCommand = defineCommand21({
|
|
10969
11266
|
meta: {
|
|
10970
11267
|
name: "remove",
|
|
10971
11268
|
group: "lifecycle",
|
|
@@ -11002,7 +11299,7 @@ var init_remove2 = __esm({
|
|
|
11002
11299
|
const skipPrompt = args.yes === true;
|
|
11003
11300
|
if (!skipPrompt) {
|
|
11004
11301
|
const warning = noBackup ? `About to remove '${args.name}' WITHOUT a backup. Docker objects, container-configs entry, and container directory will all be deleted.` : `About to remove '${args.name}'. A backup will be written to container-backups/ first, then docker objects, container-configs entry, and container directory will all be deleted.`;
|
|
11005
|
-
|
|
11302
|
+
consola25.warn(warning);
|
|
11006
11303
|
const rl = createInterface({
|
|
11007
11304
|
input: process.stdin,
|
|
11008
11305
|
output: process.stdout
|
|
@@ -11010,7 +11307,7 @@ var init_remove2 = __esm({
|
|
|
11010
11307
|
const answer = await rl.question("Continue? [y/N] ");
|
|
11011
11308
|
rl.close();
|
|
11012
11309
|
if (!/^y(es)?$/i.test(answer.trim())) {
|
|
11013
|
-
|
|
11310
|
+
consola25.info("Aborted. Nothing changed.");
|
|
11014
11311
|
process.exit(0);
|
|
11015
11312
|
}
|
|
11016
11313
|
}
|
|
@@ -11019,7 +11316,7 @@ var init_remove2 = __esm({
|
|
|
11019
11316
|
...noBackup ? { noBackup: true } : {}
|
|
11020
11317
|
});
|
|
11021
11318
|
} catch (err) {
|
|
11022
|
-
|
|
11319
|
+
consola25.error(err instanceof Error ? err.message : String(err));
|
|
11023
11320
|
process.exit(1);
|
|
11024
11321
|
}
|
|
11025
11322
|
}
|
|
@@ -11028,24 +11325,24 @@ var init_remove2 = __esm({
|
|
|
11028
11325
|
});
|
|
11029
11326
|
|
|
11030
11327
|
// src/restore/index.ts
|
|
11031
|
-
import { existsSync as
|
|
11032
|
-
import
|
|
11033
|
-
import { consola as
|
|
11328
|
+
import { existsSync as existsSync18, promises as fs18 } from "fs";
|
|
11329
|
+
import path29 from "path";
|
|
11330
|
+
import { consola as consola26 } from "consola";
|
|
11034
11331
|
async function runRestore(opts) {
|
|
11035
11332
|
const home = opts.monocerosHome ?? monocerosHome();
|
|
11036
11333
|
const logger = opts.logger ?? {
|
|
11037
|
-
info: (msg) =>
|
|
11038
|
-
success: (msg) =>
|
|
11334
|
+
info: (msg) => consola26.info(msg),
|
|
11335
|
+
success: (msg) => consola26.success(msg)
|
|
11039
11336
|
};
|
|
11040
|
-
const backup =
|
|
11041
|
-
if (!
|
|
11337
|
+
const backup = path29.resolve(opts.backupPath);
|
|
11338
|
+
if (!existsSync18(backup)) {
|
|
11042
11339
|
throw new Error(`Backup not found: ${backup}.`);
|
|
11043
11340
|
}
|
|
11044
|
-
const stat = await
|
|
11341
|
+
const stat = await fs18.stat(backup);
|
|
11045
11342
|
if (!stat.isDirectory()) {
|
|
11046
11343
|
throw new Error(`Backup path is not a directory: ${backup}.`);
|
|
11047
11344
|
}
|
|
11048
|
-
const entries = await
|
|
11345
|
+
const entries = await fs18.readdir(backup);
|
|
11049
11346
|
const ymlFiles = entries.filter((f) => f.endsWith(".yml"));
|
|
11050
11347
|
if (ymlFiles.length === 0) {
|
|
11051
11348
|
throw new Error(
|
|
@@ -11059,29 +11356,29 @@ async function runRestore(opts) {
|
|
|
11059
11356
|
}
|
|
11060
11357
|
const ymlFile = ymlFiles[0];
|
|
11061
11358
|
const name = ymlFile.replace(/\.yml$/, "");
|
|
11062
|
-
const containerInBackup =
|
|
11063
|
-
const hasContainer =
|
|
11064
|
-
const envInBackup =
|
|
11065
|
-
const hasEnv =
|
|
11359
|
+
const containerInBackup = path29.join(backup, "container");
|
|
11360
|
+
const hasContainer = existsSync18(containerInBackup);
|
|
11361
|
+
const envInBackup = path29.join(backup, `${name}.env`);
|
|
11362
|
+
const hasEnv = existsSync18(envInBackup);
|
|
11066
11363
|
const destYml = containerConfigPath(name, home);
|
|
11067
11364
|
const destContainer = containerDir(name, home);
|
|
11068
|
-
if (
|
|
11365
|
+
if (existsSync18(destYml)) {
|
|
11069
11366
|
throw new Error(
|
|
11070
11367
|
`Refusing to restore: ${destYml} already exists. Remove the current container first (\`monoceros remove ${name}\`) or rename the existing config.`
|
|
11071
11368
|
);
|
|
11072
11369
|
}
|
|
11073
|
-
if (hasContainer &&
|
|
11370
|
+
if (hasContainer && existsSync18(destContainer)) {
|
|
11074
11371
|
throw new Error(
|
|
11075
11372
|
`Refusing to restore: ${destContainer} already exists. Remove the current container first (\`monoceros remove ${name}\`).`
|
|
11076
11373
|
);
|
|
11077
11374
|
}
|
|
11078
|
-
await
|
|
11079
|
-
await
|
|
11375
|
+
await fs18.mkdir(containerConfigsDir(home), { recursive: true });
|
|
11376
|
+
await fs18.copyFile(path29.join(backup, ymlFile), destYml);
|
|
11080
11377
|
if (hasEnv) {
|
|
11081
|
-
await
|
|
11378
|
+
await fs18.copyFile(envInBackup, containerEnvPath(name, home));
|
|
11082
11379
|
}
|
|
11083
11380
|
if (hasContainer) {
|
|
11084
|
-
await
|
|
11381
|
+
await fs18.cp(containerInBackup, destContainer, { recursive: true });
|
|
11085
11382
|
}
|
|
11086
11383
|
logger.success(`Restored '${name}' from ${prettyPath(backup)}.`);
|
|
11087
11384
|
logger.info(
|
|
@@ -11101,14 +11398,14 @@ var init_restore = __esm({
|
|
|
11101
11398
|
});
|
|
11102
11399
|
|
|
11103
11400
|
// src/commands/restore.ts
|
|
11104
|
-
import { defineCommand as
|
|
11105
|
-
import { consola as
|
|
11401
|
+
import { defineCommand as defineCommand22 } from "citty";
|
|
11402
|
+
import { consola as consola27 } from "consola";
|
|
11106
11403
|
var restoreCommand;
|
|
11107
11404
|
var init_restore2 = __esm({
|
|
11108
11405
|
"src/commands/restore.ts"() {
|
|
11109
11406
|
"use strict";
|
|
11110
11407
|
init_restore();
|
|
11111
|
-
restoreCommand =
|
|
11408
|
+
restoreCommand = defineCommand22({
|
|
11112
11409
|
meta: {
|
|
11113
11410
|
name: "restore",
|
|
11114
11411
|
group: "lifecycle",
|
|
@@ -11125,7 +11422,7 @@ var init_restore2 = __esm({
|
|
|
11125
11422
|
try {
|
|
11126
11423
|
await runRestore({ backupPath: args["backup-path"] });
|
|
11127
11424
|
} catch (err) {
|
|
11128
|
-
|
|
11425
|
+
consola27.error(err instanceof Error ? err.message : String(err));
|
|
11129
11426
|
process.exit(1);
|
|
11130
11427
|
}
|
|
11131
11428
|
}
|
|
@@ -11134,14 +11431,14 @@ var init_restore2 = __esm({
|
|
|
11134
11431
|
});
|
|
11135
11432
|
|
|
11136
11433
|
// src/commands/remove-from-url.ts
|
|
11137
|
-
import { defineCommand as
|
|
11138
|
-
import { consola as
|
|
11434
|
+
import { defineCommand as defineCommand23 } from "citty";
|
|
11435
|
+
import { consola as consola28 } from "consola";
|
|
11139
11436
|
var removeFromUrlCommand;
|
|
11140
11437
|
var init_remove_from_url = __esm({
|
|
11141
11438
|
"src/commands/remove-from-url.ts"() {
|
|
11142
11439
|
"use strict";
|
|
11143
11440
|
init_modify();
|
|
11144
|
-
removeFromUrlCommand =
|
|
11441
|
+
removeFromUrlCommand = defineCommand23({
|
|
11145
11442
|
meta: {
|
|
11146
11443
|
name: "remove-from-url",
|
|
11147
11444
|
group: "edit",
|
|
@@ -11174,7 +11471,7 @@ var init_remove_from_url = __esm({
|
|
|
11174
11471
|
});
|
|
11175
11472
|
process.exit(result.status === "aborted" ? 1 : 0);
|
|
11176
11473
|
} catch (err) {
|
|
11177
|
-
|
|
11474
|
+
consola28.error(err instanceof Error ? err.message : String(err));
|
|
11178
11475
|
process.exit(1);
|
|
11179
11476
|
}
|
|
11180
11477
|
}
|
|
@@ -11183,14 +11480,14 @@ var init_remove_from_url = __esm({
|
|
|
11183
11480
|
});
|
|
11184
11481
|
|
|
11185
11482
|
// src/commands/remove-language.ts
|
|
11186
|
-
import { defineCommand as
|
|
11187
|
-
import { consola as
|
|
11483
|
+
import { defineCommand as defineCommand24 } from "citty";
|
|
11484
|
+
import { consola as consola29 } from "consola";
|
|
11188
11485
|
var removeLanguageCommand;
|
|
11189
11486
|
var init_remove_language = __esm({
|
|
11190
11487
|
"src/commands/remove-language.ts"() {
|
|
11191
11488
|
"use strict";
|
|
11192
11489
|
init_modify();
|
|
11193
|
-
removeLanguageCommand =
|
|
11490
|
+
removeLanguageCommand = defineCommand24({
|
|
11194
11491
|
meta: {
|
|
11195
11492
|
name: "remove-language",
|
|
11196
11493
|
group: "edit",
|
|
@@ -11223,7 +11520,7 @@ var init_remove_language = __esm({
|
|
|
11223
11520
|
});
|
|
11224
11521
|
process.exit(result.status === "aborted" ? 1 : 0);
|
|
11225
11522
|
} catch (err) {
|
|
11226
|
-
|
|
11523
|
+
consola29.error(err instanceof Error ? err.message : String(err));
|
|
11227
11524
|
process.exit(1);
|
|
11228
11525
|
}
|
|
11229
11526
|
}
|
|
@@ -11232,8 +11529,8 @@ var init_remove_language = __esm({
|
|
|
11232
11529
|
});
|
|
11233
11530
|
|
|
11234
11531
|
// src/commands/remove-port.ts
|
|
11235
|
-
import { defineCommand as
|
|
11236
|
-
import { consola as
|
|
11532
|
+
import { defineCommand as defineCommand25 } from "citty";
|
|
11533
|
+
import { consola as consola30 } from "consola";
|
|
11237
11534
|
function coerceToken2(raw) {
|
|
11238
11535
|
const n = Number(raw);
|
|
11239
11536
|
return Number.isFinite(n) ? n : raw;
|
|
@@ -11244,7 +11541,7 @@ var init_remove_port = __esm({
|
|
|
11244
11541
|
"use strict";
|
|
11245
11542
|
init_inner_args();
|
|
11246
11543
|
init_modify();
|
|
11247
|
-
removePortCommand =
|
|
11544
|
+
removePortCommand = defineCommand25({
|
|
11248
11545
|
meta: {
|
|
11249
11546
|
name: "remove-port",
|
|
11250
11547
|
group: "edit",
|
|
@@ -11266,7 +11563,7 @@ var init_remove_port = __esm({
|
|
|
11266
11563
|
async run({ args }) {
|
|
11267
11564
|
const tokens = [...getInnerArgs()];
|
|
11268
11565
|
if (tokens.length === 0) {
|
|
11269
|
-
|
|
11566
|
+
consola30.error(
|
|
11270
11567
|
"No ports given. Usage: `monoceros remove-port <containername> [--yes] -- <port> [<port> \u2026]`."
|
|
11271
11568
|
);
|
|
11272
11569
|
process.exit(1);
|
|
@@ -11279,7 +11576,7 @@ var init_remove_port = __esm({
|
|
|
11279
11576
|
});
|
|
11280
11577
|
process.exit(result.status === "aborted" ? 1 : 0);
|
|
11281
11578
|
} catch (err) {
|
|
11282
|
-
|
|
11579
|
+
consola30.error(err instanceof Error ? err.message : String(err));
|
|
11283
11580
|
process.exit(1);
|
|
11284
11581
|
}
|
|
11285
11582
|
}
|
|
@@ -11288,14 +11585,14 @@ var init_remove_port = __esm({
|
|
|
11288
11585
|
});
|
|
11289
11586
|
|
|
11290
11587
|
// src/commands/remove-repo.ts
|
|
11291
|
-
import { defineCommand as
|
|
11292
|
-
import { consola as
|
|
11588
|
+
import { defineCommand as defineCommand26 } from "citty";
|
|
11589
|
+
import { consola as consola31 } from "consola";
|
|
11293
11590
|
var removeRepoCommand;
|
|
11294
11591
|
var init_remove_repo = __esm({
|
|
11295
11592
|
"src/commands/remove-repo.ts"() {
|
|
11296
11593
|
"use strict";
|
|
11297
11594
|
init_modify();
|
|
11298
|
-
removeRepoCommand =
|
|
11595
|
+
removeRepoCommand = defineCommand26({
|
|
11299
11596
|
meta: {
|
|
11300
11597
|
name: "remove-repo",
|
|
11301
11598
|
group: "edit",
|
|
@@ -11328,7 +11625,7 @@ var init_remove_repo = __esm({
|
|
|
11328
11625
|
});
|
|
11329
11626
|
process.exit(result.status === "aborted" ? 1 : 0);
|
|
11330
11627
|
} catch (err) {
|
|
11331
|
-
|
|
11628
|
+
consola31.error(err instanceof Error ? err.message : String(err));
|
|
11332
11629
|
process.exit(1);
|
|
11333
11630
|
}
|
|
11334
11631
|
}
|
|
@@ -11337,14 +11634,14 @@ var init_remove_repo = __esm({
|
|
|
11337
11634
|
});
|
|
11338
11635
|
|
|
11339
11636
|
// src/commands/remove-service.ts
|
|
11340
|
-
import { defineCommand as
|
|
11341
|
-
import { consola as
|
|
11637
|
+
import { defineCommand as defineCommand27 } from "citty";
|
|
11638
|
+
import { consola as consola32 } from "consola";
|
|
11342
11639
|
var removeServiceCommand;
|
|
11343
11640
|
var init_remove_service = __esm({
|
|
11344
11641
|
"src/commands/remove-service.ts"() {
|
|
11345
11642
|
"use strict";
|
|
11346
11643
|
init_modify();
|
|
11347
|
-
removeServiceCommand =
|
|
11644
|
+
removeServiceCommand = defineCommand27({
|
|
11348
11645
|
meta: {
|
|
11349
11646
|
name: "remove-service",
|
|
11350
11647
|
group: "edit",
|
|
@@ -11377,7 +11674,7 @@ var init_remove_service = __esm({
|
|
|
11377
11674
|
});
|
|
11378
11675
|
process.exit(result.status === "aborted" ? 1 : 0);
|
|
11379
11676
|
} catch (err) {
|
|
11380
|
-
|
|
11677
|
+
consola32.error(err instanceof Error ? err.message : String(err));
|
|
11381
11678
|
process.exit(1);
|
|
11382
11679
|
}
|
|
11383
11680
|
}
|
|
@@ -11386,16 +11683,16 @@ var init_remove_service = __esm({
|
|
|
11386
11683
|
});
|
|
11387
11684
|
|
|
11388
11685
|
// src/devcontainer/claude-trust.ts
|
|
11389
|
-
import { existsSync as
|
|
11390
|
-
import
|
|
11686
|
+
import { existsSync as existsSync19, promises as fsp7 } from "fs";
|
|
11687
|
+
import path30 from "path";
|
|
11391
11688
|
function resolveContainerCwd(name, cwd) {
|
|
11392
11689
|
const workspace = `/workspaces/${name}`;
|
|
11393
11690
|
if (!cwd) return workspace;
|
|
11394
|
-
return
|
|
11691
|
+
return path30.posix.isAbsolute(cwd) ? cwd : path30.posix.join(workspace, cwd);
|
|
11395
11692
|
}
|
|
11396
11693
|
async function preApproveClaudeProject(opts) {
|
|
11397
|
-
const file =
|
|
11398
|
-
if (!
|
|
11694
|
+
const file = path30.join(opts.root, "home", ".claude.json");
|
|
11695
|
+
if (!existsSync19(file)) return;
|
|
11399
11696
|
try {
|
|
11400
11697
|
const raw = await fsp7.readFile(file, "utf8");
|
|
11401
11698
|
const config = raw.trim() ? JSON.parse(raw) : {};
|
|
@@ -11486,8 +11783,8 @@ var init_run = __esm({
|
|
|
11486
11783
|
});
|
|
11487
11784
|
|
|
11488
11785
|
// src/commands/run.ts
|
|
11489
|
-
import { defineCommand as
|
|
11490
|
-
import { consola as
|
|
11786
|
+
import { defineCommand as defineCommand28 } from "citty";
|
|
11787
|
+
import { consola as consola33 } from "consola";
|
|
11491
11788
|
var runCommand;
|
|
11492
11789
|
var init_run2 = __esm({
|
|
11493
11790
|
"src/commands/run.ts"() {
|
|
@@ -11495,7 +11792,7 @@ var init_run2 = __esm({
|
|
|
11495
11792
|
init_paths();
|
|
11496
11793
|
init_run();
|
|
11497
11794
|
init_inner_args();
|
|
11498
|
-
runCommand =
|
|
11795
|
+
runCommand = defineCommand28({
|
|
11499
11796
|
meta: {
|
|
11500
11797
|
name: "run",
|
|
11501
11798
|
group: "run",
|
|
@@ -11515,7 +11812,7 @@ var init_run2 = __esm({
|
|
|
11515
11812
|
async run({ args }) {
|
|
11516
11813
|
const command = [...getInnerArgs()];
|
|
11517
11814
|
if (command.length === 0) {
|
|
11518
|
-
|
|
11815
|
+
consola33.error(
|
|
11519
11816
|
"No command provided. Usage: `monoceros run <containername> -- <cmd> [args\u2026]`."
|
|
11520
11817
|
);
|
|
11521
11818
|
process.exit(1);
|
|
@@ -11529,7 +11826,7 @@ var init_run2 = __esm({
|
|
|
11529
11826
|
});
|
|
11530
11827
|
process.exit(exitCode);
|
|
11531
11828
|
} catch (err) {
|
|
11532
|
-
|
|
11829
|
+
consola33.error(err instanceof Error ? err.message : String(err));
|
|
11533
11830
|
process.exit(1);
|
|
11534
11831
|
}
|
|
11535
11832
|
}
|
|
@@ -11538,15 +11835,15 @@ var init_run2 = __esm({
|
|
|
11538
11835
|
});
|
|
11539
11836
|
|
|
11540
11837
|
// src/commands/shell.ts
|
|
11541
|
-
import { defineCommand as
|
|
11542
|
-
import { consola as
|
|
11838
|
+
import { defineCommand as defineCommand29 } from "citty";
|
|
11839
|
+
import { consola as consola34 } from "consola";
|
|
11543
11840
|
var shellCommand;
|
|
11544
11841
|
var init_shell2 = __esm({
|
|
11545
11842
|
"src/commands/shell.ts"() {
|
|
11546
11843
|
"use strict";
|
|
11547
11844
|
init_paths();
|
|
11548
11845
|
init_shell();
|
|
11549
|
-
shellCommand =
|
|
11846
|
+
shellCommand = defineCommand29({
|
|
11550
11847
|
meta: {
|
|
11551
11848
|
name: "shell",
|
|
11552
11849
|
group: "run",
|
|
@@ -11567,7 +11864,7 @@ var init_shell2 = __esm({
|
|
|
11567
11864
|
});
|
|
11568
11865
|
process.exit(exitCode);
|
|
11569
11866
|
} catch (err) {
|
|
11570
|
-
|
|
11867
|
+
consola34.error(err instanceof Error ? err.message : String(err));
|
|
11571
11868
|
process.exit(1);
|
|
11572
11869
|
}
|
|
11573
11870
|
}
|
|
@@ -11575,9 +11872,94 @@ var init_shell2 = __esm({
|
|
|
11575
11872
|
}
|
|
11576
11873
|
});
|
|
11577
11874
|
|
|
11875
|
+
// src/devcontainer/app-control.ts
|
|
11876
|
+
function findRunningContainer(name, opts = {}) {
|
|
11877
|
+
return findRunningContainerByLocalFolder(containerDir(name), {
|
|
11878
|
+
...opts.docker ? { docker: opts.docker } : {}
|
|
11879
|
+
});
|
|
11880
|
+
}
|
|
11881
|
+
async function runAppCtl(name, ctlArgs2, opts = {}) {
|
|
11882
|
+
const id = await findRunningContainer(name, opts);
|
|
11883
|
+
if (!id) {
|
|
11884
|
+
throw new Error(
|
|
11885
|
+
`Container "${name}" is not running. Run \`monoceros start ${name}\` first.`
|
|
11886
|
+
);
|
|
11887
|
+
}
|
|
11888
|
+
const exec = opts.exec ?? realContainerExec;
|
|
11889
|
+
const result = await exec(id, ["monoceros-ctl", ...ctlArgs2]);
|
|
11890
|
+
return result.exitCode;
|
|
11891
|
+
}
|
|
11892
|
+
function ctlArgs(sub, app, target, extra = []) {
|
|
11893
|
+
return [sub, app, ...target ? ["--target", target] : [], ...extra];
|
|
11894
|
+
}
|
|
11895
|
+
var init_app_control = __esm({
|
|
11896
|
+
"src/devcontainer/app-control.ts"() {
|
|
11897
|
+
"use strict";
|
|
11898
|
+
init_paths();
|
|
11899
|
+
init_locate_running();
|
|
11900
|
+
}
|
|
11901
|
+
});
|
|
11902
|
+
|
|
11578
11903
|
// src/commands/start.ts
|
|
11579
|
-
import { defineCommand as
|
|
11580
|
-
import { consola as
|
|
11904
|
+
import { defineCommand as defineCommand30 } from "citty";
|
|
11905
|
+
import { consola as consola35 } from "consola";
|
|
11906
|
+
async function bringContainerUp(name, openTool) {
|
|
11907
|
+
{
|
|
11908
|
+
const args = { name, open: openTool };
|
|
11909
|
+
let needsProxy = false;
|
|
11910
|
+
let hostPort = 80;
|
|
11911
|
+
let deferred = [];
|
|
11912
|
+
let runtimeVersion;
|
|
11913
|
+
try {
|
|
11914
|
+
const parsed = await readConfig(containerConfigPath(args.name));
|
|
11915
|
+
runtimeVersion = parsed.config.runtimeVersion;
|
|
11916
|
+
if ((parsed.config.routing?.ports ?? []).length > 0) {
|
|
11917
|
+
needsProxy = true;
|
|
11918
|
+
const global = await readMonocerosConfig();
|
|
11919
|
+
hostPort = proxyHostPort(global);
|
|
11920
|
+
}
|
|
11921
|
+
deferred = (parsed.config.services ?? []).filter((s) => serviceDefersStart(s.name)).map((s) => s.name);
|
|
11922
|
+
} catch (err) {
|
|
11923
|
+
consola35.warn(
|
|
11924
|
+
`Could not read container yml ahead of start: ${err instanceof Error ? err.message : String(err)}. Skipping Traefik pre-flight.`
|
|
11925
|
+
);
|
|
11926
|
+
}
|
|
11927
|
+
if (needsProxy) {
|
|
11928
|
+
await preflightHostPort(hostPort);
|
|
11929
|
+
await ensureProxy({ hostPort });
|
|
11930
|
+
}
|
|
11931
|
+
const exitCode = await runStart({ root: containerDir(args.name) });
|
|
11932
|
+
if (exitCode === 0 && runtimeSupportsBrowserBridge(runtimeVersion)) {
|
|
11933
|
+
spawnBridgeDaemon(containerDir(args.name));
|
|
11934
|
+
}
|
|
11935
|
+
if (exitCode === 0 && deferred.length > 0) {
|
|
11936
|
+
try {
|
|
11937
|
+
const deferExit = await startDeferredServices({
|
|
11938
|
+
root: containerDir(args.name),
|
|
11939
|
+
services: deferred,
|
|
11940
|
+
logger: consola35
|
|
11941
|
+
});
|
|
11942
|
+
if (deferExit !== 0) {
|
|
11943
|
+
consola35.warn(
|
|
11944
|
+
`Deferred service(s) ${deferred.join(", ")} did not start cleanly (exit ${deferExit}).`
|
|
11945
|
+
);
|
|
11946
|
+
}
|
|
11947
|
+
} catch (err) {
|
|
11948
|
+
consola35.warn(
|
|
11949
|
+
`Could not start deferred service(s) ${deferred.join(", ")}: ${err instanceof Error ? err.message : String(err)}`
|
|
11950
|
+
);
|
|
11951
|
+
}
|
|
11952
|
+
}
|
|
11953
|
+
if (args.open && exitCode === 0) {
|
|
11954
|
+
try {
|
|
11955
|
+
await runOpen({ name: args.name, tool: args.open });
|
|
11956
|
+
} catch (err) {
|
|
11957
|
+
consola35.warn(err instanceof Error ? err.message : String(err));
|
|
11958
|
+
}
|
|
11959
|
+
}
|
|
11960
|
+
return exitCode;
|
|
11961
|
+
}
|
|
11962
|
+
}
|
|
11581
11963
|
var startCommand;
|
|
11582
11964
|
var init_start = __esm({
|
|
11583
11965
|
"src/commands/start.ts"() {
|
|
@@ -11591,12 +11973,13 @@ var init_start = __esm({
|
|
|
11591
11973
|
init_open();
|
|
11592
11974
|
init_proxy();
|
|
11593
11975
|
init_port_check();
|
|
11976
|
+
init_app_control();
|
|
11594
11977
|
init_dispatch();
|
|
11595
|
-
startCommand =
|
|
11978
|
+
startCommand = defineCommand30({
|
|
11596
11979
|
meta: {
|
|
11597
11980
|
name: "start",
|
|
11598
11981
|
group: "run",
|
|
11599
|
-
description: "Bring the named dev-container up
|
|
11982
|
+
description: "Bring the named dev-container up. With an <app>, start that app inside it (per its projects/<app>/.monoceros/launch.json); the container is brought up first if needed."
|
|
11600
11983
|
},
|
|
11601
11984
|
args: {
|
|
11602
11985
|
name: {
|
|
@@ -11604,73 +11987,45 @@ var init_start = __esm({
|
|
|
11604
11987
|
description: "Container name (yml in $MONOCEROS_HOME/container-configs/).",
|
|
11605
11988
|
required: true
|
|
11606
11989
|
},
|
|
11990
|
+
app: {
|
|
11991
|
+
type: "positional",
|
|
11992
|
+
description: "App to start (a path under projects/ with .monoceros/launch.json). Omit to just bring the container up.",
|
|
11993
|
+
required: false
|
|
11994
|
+
},
|
|
11995
|
+
target: {
|
|
11996
|
+
type: "string",
|
|
11997
|
+
description: `Which launch target to start (defaults to the app's "default" target, or its only one).`
|
|
11998
|
+
},
|
|
11607
11999
|
open: {
|
|
11608
12000
|
type: "string",
|
|
11609
12001
|
description: `After a successful start, open the container in this tool (${OPEN_TOOLS.join("|")}).`
|
|
11610
12002
|
}
|
|
11611
12003
|
},
|
|
11612
12004
|
run({ args }) {
|
|
11613
|
-
|
|
11614
|
-
|
|
11615
|
-
|
|
11616
|
-
|
|
11617
|
-
|
|
11618
|
-
|
|
11619
|
-
|
|
11620
|
-
runtimeVersion = parsed.config.runtimeVersion;
|
|
11621
|
-
if ((parsed.config.routing?.ports ?? []).length > 0) {
|
|
11622
|
-
needsProxy = true;
|
|
11623
|
-
const global = await readMonocerosConfig();
|
|
11624
|
-
hostPort = proxyHostPort(global);
|
|
11625
|
-
}
|
|
11626
|
-
deferred = (parsed.config.services ?? []).filter((s) => serviceDefersStart(s.name)).map((s) => s.name);
|
|
11627
|
-
} catch (err) {
|
|
11628
|
-
consola33.warn(
|
|
11629
|
-
`Could not read container yml ahead of start: ${err instanceof Error ? err.message : String(err)}. Skipping Traefik pre-flight.`
|
|
11630
|
-
);
|
|
11631
|
-
}
|
|
11632
|
-
if (needsProxy) {
|
|
11633
|
-
await preflightHostPort(hostPort);
|
|
11634
|
-
await ensureProxy({ hostPort });
|
|
11635
|
-
}
|
|
11636
|
-
const exitCode = await runStart({ root: containerDir(args.name) });
|
|
11637
|
-
if (exitCode === 0 && runtimeSupportsBrowserBridge(runtimeVersion)) {
|
|
11638
|
-
spawnBridgeDaemon(containerDir(args.name));
|
|
11639
|
-
}
|
|
11640
|
-
if (exitCode === 0 && deferred.length > 0) {
|
|
11641
|
-
try {
|
|
11642
|
-
const deferExit = await startDeferredServices({
|
|
11643
|
-
root: containerDir(args.name),
|
|
11644
|
-
services: deferred,
|
|
11645
|
-
logger: consola33
|
|
11646
|
-
});
|
|
11647
|
-
if (deferExit !== 0) {
|
|
11648
|
-
consola33.warn(
|
|
11649
|
-
`Deferred service(s) ${deferred.join(", ")} did not start cleanly (exit ${deferExit}).`
|
|
11650
|
-
);
|
|
11651
|
-
}
|
|
11652
|
-
} catch (err) {
|
|
11653
|
-
consola33.warn(
|
|
11654
|
-
`Could not start deferred service(s) ${deferred.join(", ")}: ${err instanceof Error ? err.message : String(err)}`
|
|
11655
|
-
);
|
|
11656
|
-
}
|
|
11657
|
-
}
|
|
11658
|
-
if (args.open && exitCode === 0) {
|
|
11659
|
-
try {
|
|
11660
|
-
await runOpen({ name: args.name, tool: args.open });
|
|
11661
|
-
} catch (err) {
|
|
11662
|
-
consola33.warn(err instanceof Error ? err.message : String(err));
|
|
12005
|
+
if (typeof args.app === "string" && args.app.length > 0) {
|
|
12006
|
+
const app = args.app;
|
|
12007
|
+
const target = typeof args.target === "string" ? args.target : void 0;
|
|
12008
|
+
return dispatch(async () => {
|
|
12009
|
+
if (!await findRunningContainer(args.name)) {
|
|
12010
|
+
const up = await bringContainerUp(args.name, void 0);
|
|
12011
|
+
if (up !== 0) return up;
|
|
11663
12012
|
}
|
|
11664
|
-
|
|
11665
|
-
|
|
11666
|
-
}
|
|
12013
|
+
return runAppCtl(args.name, ctlArgs("start", app, target));
|
|
12014
|
+
});
|
|
12015
|
+
}
|
|
12016
|
+
return dispatch(
|
|
12017
|
+
() => bringContainerUp(
|
|
12018
|
+
args.name,
|
|
12019
|
+
typeof args.open === "string" ? args.open : void 0
|
|
12020
|
+
)
|
|
12021
|
+
);
|
|
11667
12022
|
}
|
|
11668
12023
|
});
|
|
11669
12024
|
}
|
|
11670
12025
|
});
|
|
11671
12026
|
|
|
11672
12027
|
// src/commands/status.ts
|
|
11673
|
-
import { defineCommand as
|
|
12028
|
+
import { defineCommand as defineCommand31 } from "citty";
|
|
11674
12029
|
var statusCommand;
|
|
11675
12030
|
var init_status = __esm({
|
|
11676
12031
|
"src/commands/status.ts"() {
|
|
@@ -11678,7 +12033,7 @@ var init_status = __esm({
|
|
|
11678
12033
|
init_paths();
|
|
11679
12034
|
init_compose();
|
|
11680
12035
|
init_dispatch();
|
|
11681
|
-
statusCommand =
|
|
12036
|
+
statusCommand = defineCommand31({
|
|
11682
12037
|
meta: {
|
|
11683
12038
|
name: "status",
|
|
11684
12039
|
group: "run",
|
|
@@ -11708,8 +12063,8 @@ var init_status = __esm({
|
|
|
11708
12063
|
});
|
|
11709
12064
|
|
|
11710
12065
|
// src/commands/stop.ts
|
|
11711
|
-
import { defineCommand as
|
|
11712
|
-
import { consola as
|
|
12066
|
+
import { defineCommand as defineCommand32 } from "citty";
|
|
12067
|
+
import { consola as consola36 } from "consola";
|
|
11713
12068
|
var stopCommand;
|
|
11714
12069
|
var init_stop = __esm({
|
|
11715
12070
|
"src/commands/stop.ts"() {
|
|
@@ -11717,12 +12072,13 @@ var init_stop = __esm({
|
|
|
11717
12072
|
init_paths();
|
|
11718
12073
|
init_compose();
|
|
11719
12074
|
init_proxy();
|
|
12075
|
+
init_app_control();
|
|
11720
12076
|
init_dispatch();
|
|
11721
|
-
stopCommand =
|
|
12077
|
+
stopCommand = defineCommand32({
|
|
11722
12078
|
meta: {
|
|
11723
12079
|
name: "stop",
|
|
11724
12080
|
group: "run",
|
|
11725
|
-
description: "Stop the compose services for the named dev-container.
|
|
12081
|
+
description: "Stop the compose services for the named dev-container. With an <app>, stop that long-running app inside it instead (kills its process group)."
|
|
11726
12082
|
},
|
|
11727
12083
|
args: {
|
|
11728
12084
|
name: {
|
|
@@ -11730,12 +12086,26 @@ var init_stop = __esm({
|
|
|
11730
12086
|
description: "Container name (yml in $MONOCEROS_HOME/container-configs/).",
|
|
11731
12087
|
required: true
|
|
11732
12088
|
},
|
|
12089
|
+
app: {
|
|
12090
|
+
type: "positional",
|
|
12091
|
+
description: "App to stop (a path under projects/ with .monoceros/launch.json). Omit to stop the container.",
|
|
12092
|
+
required: false
|
|
12093
|
+
},
|
|
12094
|
+
target: {
|
|
12095
|
+
type: "string",
|
|
12096
|
+
description: `Which launch target to stop (defaults to the app's "default" target, or its only one).`
|
|
12097
|
+
},
|
|
11733
12098
|
service: {
|
|
11734
12099
|
type: "string",
|
|
11735
12100
|
description: "Restrict to a single compose service (e.g. postgres). Defaults to all."
|
|
11736
12101
|
}
|
|
11737
12102
|
},
|
|
11738
12103
|
run({ args }) {
|
|
12104
|
+
if (typeof args.app === "string" && args.app.length > 0) {
|
|
12105
|
+
const app = args.app;
|
|
12106
|
+
const target = typeof args.target === "string" ? args.target : void 0;
|
|
12107
|
+
return dispatch(() => runAppCtl(args.name, ctlArgs("stop", app, target)));
|
|
12108
|
+
}
|
|
11739
12109
|
return dispatch(async () => {
|
|
11740
12110
|
const exit = await runStop({
|
|
11741
12111
|
root: containerDir(args.name),
|
|
@@ -11743,10 +12113,10 @@ var init_stop = __esm({
|
|
|
11743
12113
|
});
|
|
11744
12114
|
try {
|
|
11745
12115
|
await maybeStopProxy({
|
|
11746
|
-
logger: { info: (msg) =>
|
|
12116
|
+
logger: { info: (msg) => consola36.info(msg) }
|
|
11747
12117
|
});
|
|
11748
12118
|
} catch (err) {
|
|
11749
|
-
|
|
12119
|
+
consola36.warn(
|
|
11750
12120
|
`Could not tear down the Traefik proxy: ${err instanceof Error ? err.message : String(err)}. Ignored.`
|
|
11751
12121
|
);
|
|
11752
12122
|
}
|
|
@@ -11758,11 +12128,11 @@ var init_stop = __esm({
|
|
|
11758
12128
|
});
|
|
11759
12129
|
|
|
11760
12130
|
// src/tunnel/resolve.ts
|
|
11761
|
-
import { existsSync as
|
|
11762
|
-
import
|
|
12131
|
+
import { existsSync as existsSync20 } from "fs";
|
|
12132
|
+
import path31 from "path";
|
|
11763
12133
|
async function resolveTunnelTarget(opts) {
|
|
11764
12134
|
const ymlPath = containerConfigPath(opts.name, opts.monocerosHome);
|
|
11765
|
-
if (!
|
|
12135
|
+
if (!existsSync20(ymlPath)) {
|
|
11766
12136
|
throw new Error(
|
|
11767
12137
|
`No yml profile for '${opts.name}' at ${ymlPath}. Run \`monoceros init ${opts.name}\` first.`
|
|
11768
12138
|
);
|
|
@@ -11770,13 +12140,13 @@ async function resolveTunnelTarget(opts) {
|
|
|
11770
12140
|
const parsed = await readConfig(ymlPath);
|
|
11771
12141
|
const config = parsed.config;
|
|
11772
12142
|
const containerRoot = containerDir(opts.name, opts.monocerosHome);
|
|
11773
|
-
if (!
|
|
12143
|
+
if (!existsSync20(containerRoot)) {
|
|
11774
12144
|
throw new Error(
|
|
11775
12145
|
`Container '${opts.name}' is not materialised at ${containerRoot}. Run \`monoceros apply ${opts.name}\` first.`
|
|
11776
12146
|
);
|
|
11777
12147
|
}
|
|
11778
|
-
const composePath =
|
|
11779
|
-
const isCompose =
|
|
12148
|
+
const composePath = path31.join(containerRoot, ".devcontainer", "compose.yaml");
|
|
12149
|
+
const isCompose = existsSync20(composePath);
|
|
11780
12150
|
const parsedTarget = parseTargetArg(opts.target, config);
|
|
11781
12151
|
const docker = opts.docker ?? defaultDockerExec;
|
|
11782
12152
|
if (isCompose) {
|
|
@@ -12012,7 +12382,7 @@ var init_port_check2 = __esm({
|
|
|
12012
12382
|
|
|
12013
12383
|
// src/tunnel/run.ts
|
|
12014
12384
|
import { spawn as spawn14 } from "child_process";
|
|
12015
|
-
import { consola as
|
|
12385
|
+
import { consola as consola37 } from "consola";
|
|
12016
12386
|
function signalNumber(signal) {
|
|
12017
12387
|
switch (signal) {
|
|
12018
12388
|
case "SIGINT":
|
|
@@ -12025,8 +12395,8 @@ function signalNumber(signal) {
|
|
|
12025
12395
|
}
|
|
12026
12396
|
async function runTunnel(opts) {
|
|
12027
12397
|
const log = opts.logger ?? {
|
|
12028
|
-
info: (m) =>
|
|
12029
|
-
warn: (m) =>
|
|
12398
|
+
info: (m) => consola37.info(m),
|
|
12399
|
+
warn: (m) => consola37.warn(m)
|
|
12030
12400
|
};
|
|
12031
12401
|
const resolve = opts.resolve ?? resolveTunnelTarget;
|
|
12032
12402
|
const resolveArgs3 = {
|
|
@@ -12132,8 +12502,8 @@ var init_run3 = __esm({
|
|
|
12132
12502
|
});
|
|
12133
12503
|
|
|
12134
12504
|
// src/commands/tunnel.ts
|
|
12135
|
-
import { defineCommand as
|
|
12136
|
-
import { consola as
|
|
12505
|
+
import { defineCommand as defineCommand33 } from "citty";
|
|
12506
|
+
import { consola as consola38 } from "consola";
|
|
12137
12507
|
function parseLocalPort(raw) {
|
|
12138
12508
|
if (raw === void 0) return void 0;
|
|
12139
12509
|
const n = Number(raw);
|
|
@@ -12149,7 +12519,7 @@ var init_tunnel = __esm({
|
|
|
12149
12519
|
"src/commands/tunnel.ts"() {
|
|
12150
12520
|
"use strict";
|
|
12151
12521
|
init_run3();
|
|
12152
|
-
tunnelCommand =
|
|
12522
|
+
tunnelCommand = defineCommand33({
|
|
12153
12523
|
meta: {
|
|
12154
12524
|
name: "tunnel",
|
|
12155
12525
|
group: "discovery",
|
|
@@ -12186,7 +12556,7 @@ var init_tunnel = __esm({
|
|
|
12186
12556
|
});
|
|
12187
12557
|
process.exit(exitCode);
|
|
12188
12558
|
} catch (err) {
|
|
12189
|
-
|
|
12559
|
+
consola38.error(err instanceof Error ? err.message : String(err));
|
|
12190
12560
|
process.exit(1);
|
|
12191
12561
|
}
|
|
12192
12562
|
}
|
|
@@ -12256,8 +12626,8 @@ var init_prune = __esm({
|
|
|
12256
12626
|
});
|
|
12257
12627
|
|
|
12258
12628
|
// src/upgrade/index.ts
|
|
12259
|
-
import { existsSync as
|
|
12260
|
-
import { consola as
|
|
12629
|
+
import { existsSync as existsSync21, promises as fs19 } from "fs";
|
|
12630
|
+
import { consola as consola39 } from "consola";
|
|
12261
12631
|
async function fetchRuntimeVersions() {
|
|
12262
12632
|
const tokenUrl = `https://ghcr.io/token?service=ghcr.io&scope=repository:${RUNTIME_REPO}:pull`;
|
|
12263
12633
|
const tokenRes = await fetch(tokenUrl);
|
|
@@ -12295,7 +12665,7 @@ ${yml}`;
|
|
|
12295
12665
|
}
|
|
12296
12666
|
async function runUpgrade(opts) {
|
|
12297
12667
|
const home = opts.monocerosHome ?? monocerosHome();
|
|
12298
|
-
const logger = opts.logger ??
|
|
12668
|
+
const logger = opts.logger ?? consola39;
|
|
12299
12669
|
const fetchVersions = opts.fetchVersions ?? fetchRuntimeVersions;
|
|
12300
12670
|
if (opts.list) {
|
|
12301
12671
|
const versions = await fetchVersions();
|
|
@@ -12321,7 +12691,7 @@ async function runUpgrade(opts) {
|
|
|
12321
12691
|
);
|
|
12322
12692
|
}
|
|
12323
12693
|
}
|
|
12324
|
-
if (opts.name && !
|
|
12694
|
+
if (opts.name && !existsSync21(containerConfigPath(opts.name, home))) {
|
|
12325
12695
|
throw new Error(
|
|
12326
12696
|
`No such config: ${containerConfigPath(opts.name, home)}. Run \`monoceros init <template> ${opts.name}\` first.`
|
|
12327
12697
|
);
|
|
@@ -12372,11 +12742,11 @@ async function runUpgrade(opts) {
|
|
|
12372
12742
|
let bumped = 0;
|
|
12373
12743
|
for (const name of targets) {
|
|
12374
12744
|
const ymlPath = containerConfigPath(name, home);
|
|
12375
|
-
if (!
|
|
12376
|
-
const raw = await
|
|
12745
|
+
if (!existsSync21(ymlPath)) continue;
|
|
12746
|
+
const raw = await fs19.readFile(ymlPath, "utf8");
|
|
12377
12747
|
const updated = setRuntimeVersion(raw, pinVersion);
|
|
12378
12748
|
if (updated !== raw) {
|
|
12379
|
-
await
|
|
12749
|
+
await fs19.writeFile(ymlPath, updated);
|
|
12380
12750
|
bumped += 1;
|
|
12381
12751
|
logger.info(`Pinned '${name}' to runtime ${pinVersion}.`);
|
|
12382
12752
|
}
|
|
@@ -12418,7 +12788,7 @@ function formatPruneLine(prune) {
|
|
|
12418
12788
|
}
|
|
12419
12789
|
async function listContainerNames2(home) {
|
|
12420
12790
|
try {
|
|
12421
|
-
const entries = await
|
|
12791
|
+
const entries = await fs19.readdir(containerConfigsDir(home));
|
|
12422
12792
|
return entries.filter((e) => e.endsWith(".yml")).map((e) => e.slice(0, -".yml".length));
|
|
12423
12793
|
} catch {
|
|
12424
12794
|
return [];
|
|
@@ -12441,7 +12811,7 @@ var init_upgrade = __esm({
|
|
|
12441
12811
|
});
|
|
12442
12812
|
|
|
12443
12813
|
// src/commands/upgrade.ts
|
|
12444
|
-
import { defineCommand as
|
|
12814
|
+
import { defineCommand as defineCommand34 } from "citty";
|
|
12445
12815
|
var upgradeCommand;
|
|
12446
12816
|
var init_upgrade2 = __esm({
|
|
12447
12817
|
"src/commands/upgrade.ts"() {
|
|
@@ -12449,7 +12819,7 @@ var init_upgrade2 = __esm({
|
|
|
12449
12819
|
init_upgrade();
|
|
12450
12820
|
init_version();
|
|
12451
12821
|
init_dispatch();
|
|
12452
|
-
upgradeCommand =
|
|
12822
|
+
upgradeCommand = defineCommand34({
|
|
12453
12823
|
meta: {
|
|
12454
12824
|
name: "upgrade",
|
|
12455
12825
|
group: "lifecycle",
|
|
@@ -12491,7 +12861,7 @@ var main_exports = {};
|
|
|
12491
12861
|
__export(main_exports, {
|
|
12492
12862
|
main: () => main
|
|
12493
12863
|
});
|
|
12494
|
-
import { defineCommand as
|
|
12864
|
+
import { defineCommand as defineCommand35 } from "citty";
|
|
12495
12865
|
var main;
|
|
12496
12866
|
var init_main = __esm({
|
|
12497
12867
|
"src/main.ts"() {
|
|
@@ -12509,6 +12879,7 @@ var init_main = __esm({
|
|
|
12509
12879
|
init_complete();
|
|
12510
12880
|
init_update_check();
|
|
12511
12881
|
init_init2();
|
|
12882
|
+
init_list_apps();
|
|
12512
12883
|
init_list_components();
|
|
12513
12884
|
init_logs();
|
|
12514
12885
|
init_open2();
|
|
@@ -12530,7 +12901,7 @@ var init_main = __esm({
|
|
|
12530
12901
|
init_tunnel();
|
|
12531
12902
|
init_upgrade2();
|
|
12532
12903
|
init_version();
|
|
12533
|
-
main =
|
|
12904
|
+
main = defineCommand35({
|
|
12534
12905
|
meta: {
|
|
12535
12906
|
name: "monoceros",
|
|
12536
12907
|
version: CLI_VERSION,
|
|
@@ -12538,6 +12909,7 @@ var init_main = __esm({
|
|
|
12538
12909
|
},
|
|
12539
12910
|
subCommands: {
|
|
12540
12911
|
init: initCommand,
|
|
12912
|
+
"list-apps": listAppsCommand,
|
|
12541
12913
|
"list-components": listComponentsCommand,
|
|
12542
12914
|
shell: shellCommand,
|
|
12543
12915
|
open: openCommand,
|
|
@@ -12829,25 +13201,25 @@ function detectHelpRequest(argv, main2) {
|
|
|
12829
13201
|
const separatorIdx = argv.indexOf("--");
|
|
12830
13202
|
if (helpIdx === -1) return null;
|
|
12831
13203
|
if (separatorIdx !== -1 && separatorIdx < helpIdx) return null;
|
|
12832
|
-
const
|
|
13204
|
+
const path32 = [];
|
|
12833
13205
|
const tokens = argv.slice(
|
|
12834
13206
|
0,
|
|
12835
13207
|
separatorIdx === -1 ? argv.length : separatorIdx
|
|
12836
13208
|
);
|
|
12837
13209
|
let cursor = main2;
|
|
12838
13210
|
const mainName = (main2.meta ?? {}).name ?? "monoceros";
|
|
12839
|
-
|
|
13211
|
+
path32.push(mainName);
|
|
12840
13212
|
for (const tok of tokens) {
|
|
12841
13213
|
if (tok.startsWith("-")) continue;
|
|
12842
13214
|
const subs = cursor.subCommands ?? {};
|
|
12843
13215
|
if (tok in subs) {
|
|
12844
13216
|
cursor = subs[tok];
|
|
12845
|
-
|
|
13217
|
+
path32.push(tok);
|
|
12846
13218
|
continue;
|
|
12847
13219
|
}
|
|
12848
13220
|
break;
|
|
12849
13221
|
}
|
|
12850
|
-
return { path:
|
|
13222
|
+
return { path: path32, cmd: cursor };
|
|
12851
13223
|
}
|
|
12852
13224
|
async function maybeRenderHelp(argv, main2) {
|
|
12853
13225
|
const hit = detectHelpRequest(argv, main2);
|