@flisk-sh/flisk 1.3.200 → 1.3.204
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/cli/dist/cli.js +9 -0
- package/cli/dist/commands/doctor.js +22 -0
- package/cli/dist/commands/open.js +24 -3
- package/cli/dist/utils/cold-preflight.js +14 -0
- package/cli/dist/utils/colima.js +144 -0
- package/cli/dist/utils/doctor-fix.js +78 -1
- package/cli/dist/utils/stack-progress.js +8 -5
- package/cli/dist/utils/up-readiness.js +9 -2
- package/cli/dist-bundle/{chunk-RMZQU74X.js → chunk-BS6G2SLM.js} +1 -1
- package/cli/dist-bundle/{chunk-LMHKXU2Q.js → chunk-CBFVK3TF.js} +1 -1
- package/cli/dist-bundle/{chunk-GEXOZCEQ.js → chunk-EPBYRJE3.js} +1 -1
- package/cli/dist-bundle/chunk-GD5676UE.js +52 -0
- package/cli/dist-bundle/chunk-MKJNQTIN.js +2 -0
- package/cli/dist-bundle/{chunk-IYZENTVI.js → chunk-QSPFSZCS.js} +2 -2
- package/cli/dist-bundle/{chunk-WUO7C6WO.js → chunk-RFHMXJTK.js} +1 -1
- package/cli/dist-bundle/{chunk-DS47LHYF.js → chunk-WMF4AFAE.js} +1 -1
- package/cli/dist-bundle/chunk-Z6UD7UZH.js +24 -0
- package/cli/dist-bundle/chunk-ZVGY7COV.js +4 -0
- package/cli/dist-bundle/cli.js +80 -80
- package/cli/dist-bundle/cold-preflight-FXOZ5SR5.js +2 -0
- package/cli/dist-bundle/colima-4ID4BGHC.js +2 -0
- package/cli/dist-bundle/{open-PF6BGKCR.js → open-UQ6DF3XN.js} +1 -1
- package/cli/dist-bundle/{project-2TVWT57J.js → project-GTYHCCFG.js} +1 -1
- package/cli/dist-bundle/stack-progress-6GO2TCRH.js +2 -0
- package/cli/dist-bundle/{tilt-port-owner-7O5FOW5C.js → tilt-port-owner-KLNX2ZI2.js} +1 -1
- package/cli/package.json +1 -1
- package/package.json +1 -1
- package/cli/dist-bundle/chunk-EICMGZXL.js +0 -5
- package/cli/dist-bundle/chunk-H446NBVS.js +0 -71
- package/cli/dist-bundle/chunk-RWNIFXXG.js +0 -4
- package/cli/dist-bundle/cold-preflight-LPH7WF3B.js +0 -2
- package/cli/dist-bundle/stack-progress-UVREHNNB.js +0 -2
package/cli/dist/cli.js
CHANGED
|
@@ -53,6 +53,15 @@ if (templateArg) {
|
|
|
53
53
|
const { initializeProject, installServiceDependencies, runStackQuiet } = await import("./utils/one-command.js");
|
|
54
54
|
const { openFirstFrontend } = await import("./commands/open.js");
|
|
55
55
|
const { startSpinner } = await import("./utils/spinner.js");
|
|
56
|
+
// Docker on Colima is only usable while the VM is up, and a stopped VM looks like a
|
|
57
|
+
// broken Docker daemon. Say so before the long wait instead of after it.
|
|
58
|
+
const { checkColima } = await import("./utils/colima.js");
|
|
59
|
+
const colima = checkColima();
|
|
60
|
+
if (colima.isColima && !colima.running) {
|
|
61
|
+
console.log(chalk.yellow(colima.problem ?? "The Colima VM is not running."));
|
|
62
|
+
console.log(chalk.gray(` Fix: ${colima.fix ?? "colima start"}`));
|
|
63
|
+
process.exit(1);
|
|
64
|
+
}
|
|
56
65
|
// A stack for this project may already be running (the same example in another folder
|
|
57
66
|
// shares its compose project). Then there is nothing to start: open what is up.
|
|
58
67
|
const { findReadyFrontend } = await import("./commands/open.js");
|
|
@@ -9,6 +9,7 @@ import { hasVerdaccioLicense } from "../generator/extension-fetch.js";
|
|
|
9
9
|
import { readProjectConfig } from "../generator/template-engine.js";
|
|
10
10
|
import { DEVCONTAINER_DOCKER_FIX, detectHost, isContainerHost, WEBCONTAINER_DOCS, WEBCONTAINER_UP_MESSAGE, } from "../utils/agent-host.js";
|
|
11
11
|
import { projectNeedsBun } from "../utils/bun-requirement.js";
|
|
12
|
+
import { checkColima as checkColimaState } from "../utils/colima.js";
|
|
12
13
|
import { AUTOGENERATED_DIR, CONTAINER_RUNTIME_CHECK, MASTER_CONFIG_FILES, PACKAGE_JSON, REQUIRED_PACKAGE_SCRIPTS, } from "../utils/constants.js";
|
|
13
14
|
import { isPathDiscovered, readDiscoveryPaths } from "../utils/discovery-paths.js";
|
|
14
15
|
import { checkCrashLoopingContainers } from "../utils/doctor-crashloop.js";
|
|
@@ -272,6 +273,26 @@ async function succeeds(command) {
|
|
|
272
273
|
return false;
|
|
273
274
|
}
|
|
274
275
|
}
|
|
276
|
+
/** The Colima VM behind Docker: a stopped VM or a colima CLI that cannot see it. */
|
|
277
|
+
export async function checkColima() {
|
|
278
|
+
const status = checkColimaState();
|
|
279
|
+
if (!status.isColima) {
|
|
280
|
+
return { name: "Colima", didPass: true, message: "Docker does not run on Colima" };
|
|
281
|
+
}
|
|
282
|
+
if (status.running && !status.problem) {
|
|
283
|
+
return {
|
|
284
|
+
name: "Colima",
|
|
285
|
+
didPass: true,
|
|
286
|
+
message: `Colima VM is running${status.arch ? ` (${status.arch})` : ""}`,
|
|
287
|
+
};
|
|
288
|
+
}
|
|
289
|
+
return {
|
|
290
|
+
name: "Colima",
|
|
291
|
+
didPass: false,
|
|
292
|
+
message: status.problem ?? "The Colima VM is not running",
|
|
293
|
+
fix: status.fix,
|
|
294
|
+
};
|
|
295
|
+
}
|
|
275
296
|
export async function checkDockerRuntime() {
|
|
276
297
|
if (process.platform === "win32") {
|
|
277
298
|
try {
|
|
@@ -1323,6 +1344,7 @@ export const doctorCommand = new Command("doctor")
|
|
|
1323
1344
|
didPass: false,
|
|
1324
1345
|
message: "Ingress port plan is unavailable",
|
|
1325
1346
|
},
|
|
1347
|
+
checkColima,
|
|
1326
1348
|
checkDockerRuntime,
|
|
1327
1349
|
() => checkDiskSpace(),
|
|
1328
1350
|
requiresContainerRuntime("Docker OS", checkDockerOperatingSystem),
|
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
// SPDX-License-Identifier: MIT
|
|
3
3
|
import chalk from "chalk";
|
|
4
4
|
import { Command } from "commander";
|
|
5
|
+
import { probeHostPort } from "../utils/doctor-runtime.js";
|
|
5
6
|
import { showDetail, showStep } from "../utils/formatting.js";
|
|
6
7
|
import { getHostPortPlan } from "../utils/host-port-config.js";
|
|
7
8
|
import { findProjectRoot } from "../utils/paths.js";
|
|
@@ -89,9 +90,29 @@ export async function openFirstFrontend(projectRootOverride) {
|
|
|
89
90
|
});
|
|
90
91
|
if (!first) {
|
|
91
92
|
spinner.fail("No frontend answered yet.");
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
93
|
+
const plan = await getHostPortPlan(projectRoot, { inspectDocker: false });
|
|
94
|
+
const ingress = plan?.ingressHttp;
|
|
95
|
+
const reachable = ingress ? (await probeHostPort(ingress)) === "in-use" : false;
|
|
96
|
+
if (ingress && !reachable) {
|
|
97
|
+
// The stack is up but this machine cannot reach the published port: Docker is not
|
|
98
|
+
// publishing it to the host. Saying that is more useful than "not serving yet".
|
|
99
|
+
console.log(chalk.yellow(`The stack is running, but this machine cannot reach port ${ingress}.`));
|
|
100
|
+
console.log(chalk.gray(" Docker is not publishing the port to the host."));
|
|
101
|
+
const { checkColima } = await import("../utils/colima.js");
|
|
102
|
+
const colima = checkColima();
|
|
103
|
+
if (colima.isColima && !colima.running) {
|
|
104
|
+
console.log(chalk.gray(` ${colima.problem ?? "The Colima VM is not running"}`));
|
|
105
|
+
console.log(chalk.gray(` Fix: ${colima.fix ?? "colima start"}`));
|
|
106
|
+
}
|
|
107
|
+
else {
|
|
108
|
+
console.log(chalk.gray(" Restart the Docker runtime (Docker Desktop or Colima), then run `flisk open` again."));
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
else {
|
|
112
|
+
console.log(chalk.yellow("The stack is not serving the frontend yet."));
|
|
113
|
+
console.log(chalk.gray(" - Start the stack in another terminal: flisk up"));
|
|
114
|
+
console.log(chalk.gray(" - Then run this again: flisk open"));
|
|
115
|
+
}
|
|
95
116
|
for (const target of targets) {
|
|
96
117
|
console.log(chalk.gray(` - ${target.name}: ${target.url}`));
|
|
97
118
|
}
|
|
@@ -7,6 +7,7 @@ import { checkDockerCompose, checkDockerRuntime, checkDockerVersions, checkTilt,
|
|
|
7
7
|
import { BUN_FLOOR_LABEL, bunMeetsFloor } from "./bun-floor.js";
|
|
8
8
|
import { projectNeedsBun } from "./bun-requirement.js";
|
|
9
9
|
import { readyNextStep } from "./cli-command.js";
|
|
10
|
+
import { checkColima } from "./colima.js";
|
|
10
11
|
import { PROJECT_JSON } from "./constants.js";
|
|
11
12
|
import { checkNatsBroker } from "./doctor-wiring.js";
|
|
12
13
|
import { getHostPortPlan } from "./host-port-config.js";
|
|
@@ -88,6 +89,19 @@ export async function runColdPreflight(opts = {}) {
|
|
|
88
89
|
// The runtime executables are only probed when the command actually starts a
|
|
89
90
|
// stack. Scaffolding a project must not depend on a running Docker daemon.
|
|
90
91
|
if (scope === "runtime") {
|
|
92
|
+
// Docker on Colima is only useful when the VM is up: a stopped VM looks like a broken
|
|
93
|
+
// Docker daemon, and the port publishing silently stops working.
|
|
94
|
+
const colima = checkColima();
|
|
95
|
+
if (colima.isColima) {
|
|
96
|
+
items.push({
|
|
97
|
+
id: "colima",
|
|
98
|
+
ok: colima.running,
|
|
99
|
+
message: colima.running
|
|
100
|
+
? `Colima VM is running${colima.arch ? ` (${colima.arch})` : ""}`
|
|
101
|
+
: (colima.problem ?? "The Colima VM is not running"),
|
|
102
|
+
fix: colima.running ? undefined : colima.fix,
|
|
103
|
+
});
|
|
104
|
+
}
|
|
91
105
|
items.push(await safeCheck("docker", checkDockerRuntime, "Docker daemon is not running"));
|
|
92
106
|
items.push(await safeCheck("compose", async () => {
|
|
93
107
|
const [compose, versions] = await Promise.all([
|
|
@@ -0,0 +1,144 @@
|
|
|
1
|
+
// Copyright (c) 2026 Flisk Landscape contributors
|
|
2
|
+
// SPDX-License-Identifier: MIT
|
|
3
|
+
import { execFileSync, spawnSync } from "node:child_process";
|
|
4
|
+
import { existsSync } from "node:fs";
|
|
5
|
+
import { join } from "node:path";
|
|
6
|
+
const defaultDeps = () => ({
|
|
7
|
+
env: process.env,
|
|
8
|
+
dockerAnswers: () => {
|
|
9
|
+
try {
|
|
10
|
+
execFileSync("docker", ["info", "--format", "{{.ServerVersion}}"], {
|
|
11
|
+
encoding: "utf-8",
|
|
12
|
+
timeout: 10_000,
|
|
13
|
+
stdio: ["ignore", "pipe", "ignore"],
|
|
14
|
+
});
|
|
15
|
+
return true;
|
|
16
|
+
}
|
|
17
|
+
catch {
|
|
18
|
+
return false;
|
|
19
|
+
}
|
|
20
|
+
},
|
|
21
|
+
run: (command, args) => {
|
|
22
|
+
// colima logs to stderr, so both streams matter.
|
|
23
|
+
const result = spawnSync(command, args, {
|
|
24
|
+
encoding: "utf-8",
|
|
25
|
+
timeout: 20_000,
|
|
26
|
+
stdio: ["ignore", "pipe", "pipe"],
|
|
27
|
+
});
|
|
28
|
+
return `${result.stdout ?? ""}${result.stderr ?? ""}`;
|
|
29
|
+
},
|
|
30
|
+
exists: existsSync,
|
|
31
|
+
home: process.env.HOME ?? "",
|
|
32
|
+
});
|
|
33
|
+
/** True when the Docker endpoint belongs to a Colima VM. */
|
|
34
|
+
export function isColimaDocker(deps = defaultDeps()) {
|
|
35
|
+
const host = deps.env.DOCKER_HOST ?? "";
|
|
36
|
+
if (host.includes(".colima"))
|
|
37
|
+
return true;
|
|
38
|
+
const socket = join(deps.home, ".colima", "default", "docker.sock");
|
|
39
|
+
return deps.exists(socket) && host.includes("docker.sock") === false && host !== "";
|
|
40
|
+
}
|
|
41
|
+
/**
|
|
42
|
+
* The state of the Colima VM behind Docker.
|
|
43
|
+
*
|
|
44
|
+
* Two failures matter and both look like "Docker is not working": the VM is not running, and
|
|
45
|
+
* Lima itself is an x86_64 build on an Apple Silicon machine, which cannot start the VM.
|
|
46
|
+
*/
|
|
47
|
+
export function checkColima(deps = defaultDeps()) {
|
|
48
|
+
if (!isColimaDocker(deps)) {
|
|
49
|
+
return { isColima: false, running: true };
|
|
50
|
+
}
|
|
51
|
+
let status = "";
|
|
52
|
+
try {
|
|
53
|
+
status = deps.run("colima", ["status"]);
|
|
54
|
+
}
|
|
55
|
+
catch (error) {
|
|
56
|
+
const message = String(error?.stderr ?? error);
|
|
57
|
+
if (/rosetta|native arch/i.test(message)) {
|
|
58
|
+
return {
|
|
59
|
+
isColima: true,
|
|
60
|
+
running: false,
|
|
61
|
+
problem: "Lima is installed as an x86_64 build, so it cannot start the Colima VM on this Mac",
|
|
62
|
+
fix: "Install a native Lima (brew reinstall lima, or use a native limactl on PATH) and run `colima start`",
|
|
63
|
+
};
|
|
64
|
+
}
|
|
65
|
+
if (deps.dockerAnswers()) {
|
|
66
|
+
// The VM is up: the colima CLI on this PATH simply cannot see it, which is what a
|
|
67
|
+
// Rosetta (x86_64) limactl does on Apple Silicon.
|
|
68
|
+
return {
|
|
69
|
+
isColima: true,
|
|
70
|
+
running: true,
|
|
71
|
+
problem: "The Colima VM is running, but the colima CLI on this PATH cannot see it",
|
|
72
|
+
fix: "Use a native limactl (a Rosetta x86_64 limactl cannot talk to the VM): brew reinstall lima, or put a native limactl first on PATH",
|
|
73
|
+
};
|
|
74
|
+
}
|
|
75
|
+
if (/not running/i.test(message)) {
|
|
76
|
+
return {
|
|
77
|
+
isColima: true,
|
|
78
|
+
running: false,
|
|
79
|
+
problem: "The Colima VM is not running",
|
|
80
|
+
fix: "Run `colima start`",
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
return {
|
|
84
|
+
isColima: true,
|
|
85
|
+
running: false,
|
|
86
|
+
problem: "The state of the Colima VM could not be read",
|
|
87
|
+
fix: "Run `colima status` to see what it says",
|
|
88
|
+
};
|
|
89
|
+
}
|
|
90
|
+
if (/is running/i.test(status)) {
|
|
91
|
+
const arch = /arch:\s*(\S+)/.exec(status)?.[1];
|
|
92
|
+
return { isColima: true, running: true, arch };
|
|
93
|
+
}
|
|
94
|
+
if (deps.dockerAnswers()) {
|
|
95
|
+
return {
|
|
96
|
+
isColima: true,
|
|
97
|
+
running: true,
|
|
98
|
+
problem: "The Colima VM is running, but the colima CLI on this PATH cannot see it",
|
|
99
|
+
fix: "Use a native limactl (a Rosetta x86_64 limactl cannot talk to the VM): brew reinstall lima, or put a native limactl first on PATH",
|
|
100
|
+
};
|
|
101
|
+
}
|
|
102
|
+
return {
|
|
103
|
+
isColima: true,
|
|
104
|
+
running: false,
|
|
105
|
+
problem: "The Colima VM is not running",
|
|
106
|
+
fix: "Run `colima start`",
|
|
107
|
+
};
|
|
108
|
+
}
|
|
109
|
+
/**
|
|
110
|
+
* What can be repaired about the Colima runtime: a VM that is not running is started, a VM
|
|
111
|
+
* whose Docker daemon does not answer is restarted, and a colima CLI that cannot see the VM
|
|
112
|
+
* (a Rosetta limactl) needs a native lima.
|
|
113
|
+
*/
|
|
114
|
+
export function planColimaRepair(status, dockerAnswers) {
|
|
115
|
+
if (!status.isColima)
|
|
116
|
+
return undefined;
|
|
117
|
+
if (!status.running)
|
|
118
|
+
return "start";
|
|
119
|
+
if (status.problem?.includes("cannot see it"))
|
|
120
|
+
return "native-lima";
|
|
121
|
+
if (!dockerAnswers)
|
|
122
|
+
return "restart";
|
|
123
|
+
return undefined;
|
|
124
|
+
}
|
|
125
|
+
/** Runs a colima command with a native limactl first on PATH, when one is installed. */
|
|
126
|
+
export function nativeLimaPath(env = process.env) {
|
|
127
|
+
const home = env.HOME ?? "";
|
|
128
|
+
const candidates = [
|
|
129
|
+
home ? `${home}/.local/bin` : "",
|
|
130
|
+
home ? `${home}/bin` : "",
|
|
131
|
+
"/opt/homebrew/bin",
|
|
132
|
+
].filter(Boolean);
|
|
133
|
+
for (const dir of candidates) {
|
|
134
|
+
const candidate = join(dir, "limactl");
|
|
135
|
+
try {
|
|
136
|
+
if (existsSync(candidate))
|
|
137
|
+
return dir;
|
|
138
|
+
}
|
|
139
|
+
catch {
|
|
140
|
+
// Not readable; try the next one.
|
|
141
|
+
}
|
|
142
|
+
}
|
|
143
|
+
return undefined;
|
|
144
|
+
}
|
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
// Copyright (c) 2026 Flisk Landscape contributors
|
|
2
2
|
// SPDX-License-Identifier: MIT
|
|
3
|
-
import { execFile } from "node:child_process";
|
|
3
|
+
import { execFile, execFileSync } from "node:child_process";
|
|
4
4
|
import { realpathSync, statfsSync } from "node:fs";
|
|
5
5
|
import { homedir } from "node:os";
|
|
6
6
|
import { join } from "node:path";
|
|
7
7
|
import { promisify } from "node:util";
|
|
8
|
+
import { checkColima, nativeLimaPath, planColimaRepair } from "./colima.js";
|
|
8
9
|
import { DISK_WARN_GIB } from "./doctor-host.js";
|
|
9
10
|
import { findProjectTiltUpPids, projectNetworkNames, tdkNetworkOwner, tdkNetworkPrefixes, } from "./down-cleanup.js";
|
|
10
11
|
import { tiltGetUiResources } from "./up-readiness.js";
|
|
@@ -21,6 +22,20 @@ const runDocker = async (args) => {
|
|
|
21
22
|
});
|
|
22
23
|
return stdout;
|
|
23
24
|
};
|
|
25
|
+
/** Whether the Docker daemon answers right now. */
|
|
26
|
+
function dockerAnswers() {
|
|
27
|
+
try {
|
|
28
|
+
execFileSync("docker", ["info", "--format", "{{.ServerVersion}}"], {
|
|
29
|
+
encoding: "utf-8",
|
|
30
|
+
timeout: 15_000,
|
|
31
|
+
stdio: ["ignore", "pipe", "ignore"],
|
|
32
|
+
});
|
|
33
|
+
return true;
|
|
34
|
+
}
|
|
35
|
+
catch {
|
|
36
|
+
return false;
|
|
37
|
+
}
|
|
38
|
+
}
|
|
24
39
|
function firstLine(error) {
|
|
25
40
|
const stderr = String(error.stderr ?? error).trim();
|
|
26
41
|
return stderr.split(/\r?\n/)[0] ?? "";
|
|
@@ -72,6 +87,9 @@ async function tiltProcessStatus(pid) {
|
|
|
72
87
|
}
|
|
73
88
|
export function createDockerFixDeps(run = runDocker) {
|
|
74
89
|
return {
|
|
90
|
+
colima: runColima,
|
|
91
|
+
colimaStatus: () => checkColima(),
|
|
92
|
+
dockerAnswers,
|
|
75
93
|
async listNetworks() {
|
|
76
94
|
const names = (await run(["network", "ls", "--format", "{{.Name}}"]))
|
|
77
95
|
.split(/\r?\n/)
|
|
@@ -167,6 +185,14 @@ export function createDockerFixDeps(run = runDocker) {
|
|
|
167
185
|
};
|
|
168
186
|
}
|
|
169
187
|
export const dockerFixDeps = createDockerFixDeps();
|
|
188
|
+
/** Starts or restarts Colima, with a native limactl first on PATH when one is installed. */
|
|
189
|
+
async function runColima(action) {
|
|
190
|
+
const nativeDir = nativeLimaPath();
|
|
191
|
+
const env = nativeDir
|
|
192
|
+
? { ...process.env, PATH: `${nativeDir}:${process.env.PATH ?? ""}` }
|
|
193
|
+
: process.env;
|
|
194
|
+
await execFilePromise("colima", [action], { encoding: "utf-8", timeout: 300_000, env });
|
|
195
|
+
}
|
|
170
196
|
/**
|
|
171
197
|
* What `--fix` would do: stop this project's stale Tilt; remove unused networks that are a leftover doctor probe or
|
|
172
198
|
* this project's own (the exact names the engine creates, skipped while its Tilt runs). Other Flisk projects' unused
|
|
@@ -195,6 +221,43 @@ export async function planDoctorFixes(projectName, deps = dockerFixDeps, context
|
|
|
195
221
|
const projectBusy = liveTilt.length > 0
|
|
196
222
|
? `Tilt is running for this project (pid ${liveTilt.join(", ")}); run flisk down first`
|
|
197
223
|
: undefined;
|
|
224
|
+
// The Docker runtime itself: a Colima VM that is not running, one whose daemon does not
|
|
225
|
+
// answer, or a colima CLI that cannot see the VM. All three look like "Docker is broken".
|
|
226
|
+
const colima = deps.colimaStatus();
|
|
227
|
+
const repair = planColimaRepair(colima, deps.dockerAnswers());
|
|
228
|
+
if (repair === "start") {
|
|
229
|
+
actions.push({
|
|
230
|
+
id: "colima:start",
|
|
231
|
+
check: "Colima",
|
|
232
|
+
scope: "host",
|
|
233
|
+
command: "colima start",
|
|
234
|
+
status: "planned",
|
|
235
|
+
reason: colima.problem ?? "the Colima VM is not running",
|
|
236
|
+
});
|
|
237
|
+
}
|
|
238
|
+
else if (repair === "restart") {
|
|
239
|
+
actions.push({
|
|
240
|
+
id: "colima:restart",
|
|
241
|
+
check: "Colima",
|
|
242
|
+
scope: "host",
|
|
243
|
+
command: "colima restart",
|
|
244
|
+
status: "planned",
|
|
245
|
+
reason: "the Colima VM is running but its Docker daemon does not answer",
|
|
246
|
+
});
|
|
247
|
+
}
|
|
248
|
+
else if (repair === "native-lima") {
|
|
249
|
+
const nativeDir = nativeLimaPath();
|
|
250
|
+
actions.push({
|
|
251
|
+
id: "colima:native-lima",
|
|
252
|
+
check: "Colima",
|
|
253
|
+
scope: "host",
|
|
254
|
+
command: nativeDir ? `PATH="${nativeDir}:$PATH" colima status` : "brew reinstall lima",
|
|
255
|
+
status: nativeDir ? "skipped" : "planned",
|
|
256
|
+
reason: nativeDir
|
|
257
|
+
? `the colima CLI on this PATH cannot see the VM; a native limactl is installed in ${nativeDir} (add it to PATH)`
|
|
258
|
+
: "the colima CLI on this PATH cannot see the VM; lima is installed as an x86_64 build (brew reinstall lima)",
|
|
259
|
+
});
|
|
260
|
+
}
|
|
198
261
|
const networks = await deps.listNetworks();
|
|
199
262
|
const freeGib = deps.freeDiskGib();
|
|
200
263
|
if (freeGib !== null && freeGib < DISK_WARN_GIB) {
|
|
@@ -303,6 +366,20 @@ export async function applyDoctorFixes(actions, options, deps = dockerFixDeps) {
|
|
|
303
366
|
results.push({ ...action, status: "applied", reason: "pruned" });
|
|
304
367
|
continue;
|
|
305
368
|
}
|
|
369
|
+
if (action.id.startsWith("colima:")) {
|
|
370
|
+
const what = action.id.slice("colima:".length);
|
|
371
|
+
if (what === "start" || what === "restart") {
|
|
372
|
+
await deps.colima(what);
|
|
373
|
+
results.push({ ...action, status: "applied", reason: `colima ${what} ran` });
|
|
374
|
+
continue;
|
|
375
|
+
}
|
|
376
|
+
results.push({
|
|
377
|
+
...action,
|
|
378
|
+
status: "skipped",
|
|
379
|
+
reason: "needs a native lima: see the command",
|
|
380
|
+
});
|
|
381
|
+
continue;
|
|
382
|
+
}
|
|
306
383
|
if (action.id.startsWith("stop-tilt:")) {
|
|
307
384
|
deps.stopProcess(Number(action.id.slice("stop-tilt:".length)));
|
|
308
385
|
results.push({ ...action, status: "applied", reason: "stopped" });
|
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
// Copyright (c) 2026 Flisk Landscape contributors
|
|
2
2
|
// SPDX-License-Identifier: MIT
|
|
3
3
|
import { execFile } from "node:child_process";
|
|
4
|
+
const defaultTiltResourceReader = (port) => new Promise((resolve) => {
|
|
5
|
+
execFile("tilt", ["get", "uiresources", "-o", "json", "--port", String(port)], { timeout: 15_000, maxBuffer: 16 * 1024 * 1024 }, (error, stdout) => resolve(error ? null : stdout));
|
|
6
|
+
});
|
|
4
7
|
/** Reads the resource states from the Tilt UI API. */
|
|
5
|
-
export async function readStackProgress(port,
|
|
6
|
-
const json = await
|
|
7
|
-
execFile(tiltBin, ["get", "uiresources", "-o", "json", "--port", String(port)], { timeout: 15_000, maxBuffer: 16 * 1024 * 1024 }, (error, stdout) => resolve(error ? null : stdout));
|
|
8
|
-
});
|
|
8
|
+
export async function readStackProgress(port, read = defaultTiltResourceReader) {
|
|
9
|
+
const json = await read(port);
|
|
9
10
|
if (!json)
|
|
10
11
|
return undefined;
|
|
11
12
|
let items = [];
|
|
@@ -30,7 +31,9 @@ export async function readStackProgress(port, tiltBin = "tilt") {
|
|
|
30
31
|
failed += 1;
|
|
31
32
|
broken.push({
|
|
32
33
|
name,
|
|
33
|
-
message: (item.status?.buildHistory?.[0]?.error ?? "the resource failed")
|
|
34
|
+
message: (item.status?.buildHistory?.[0]?.error ?? "the resource failed")
|
|
35
|
+
.replace(/\s+/g, " ")
|
|
36
|
+
.slice(0, 160),
|
|
34
37
|
});
|
|
35
38
|
continue;
|
|
36
39
|
}
|
|
@@ -39,15 +39,22 @@ export function checkExpectedResources(jsonText, expected) {
|
|
|
39
39
|
disabled: expected.filter((name) => byName.get(name)?.status?.disableStatus?.state === "Disabled"),
|
|
40
40
|
};
|
|
41
41
|
}
|
|
42
|
+
/** Resources that report on the stack without gating it. */
|
|
43
|
+
export function isAdvisoryResource(name) {
|
|
44
|
+
return name.endsWith("-typecheck");
|
|
45
|
+
}
|
|
42
46
|
/**
|
|
43
47
|
* One look at `tilt get uiresources -o json`. `settled` means polling can stop: everything is ready, or the rest has
|
|
44
48
|
* finished with a failure (an errored resource, or an expected service Tilt has disabled).
|
|
45
49
|
*/
|
|
46
50
|
export function evaluateTiltReadiness(jsonText, deferred, expected) {
|
|
47
51
|
const parsed = parseTiltResourceFailures(onlyEnabledResources(jsonText), deferred);
|
|
52
|
+
// A `<service>-typecheck` resource runs on the host and is advisory: it reports type errors
|
|
53
|
+
// in Tilt, it does not decide whether the stack is up. It must not fail the stack.
|
|
54
|
+
const blocking = parsed.failures.filter((failure) => !isAdvisoryResource(failure.name));
|
|
48
55
|
let result = {
|
|
49
|
-
ready:
|
|
50
|
-
failures:
|
|
56
|
+
ready: blocking.length === 0 && parsed.pendingCount === 0 && parsed.okCount > 0,
|
|
57
|
+
failures: blocking.map((failure) => ({
|
|
51
58
|
name: failure.name,
|
|
52
59
|
message: failure.error || `${failure.updateStatus}/${failure.runtimeStatus}`,
|
|
53
60
|
})),
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import{createRequire as __tdkRequire}from'node:module';const require=__tdkRequire(import.meta.url);
|
|
2
|
-
import{b as N}from"./chunk-
|
|
2
|
+
import{b as N}from"./chunk-EPBYRJE3.js";import{G as O,O as m,Ta as f,c as $,d as C,fa as T,g as U,h as E,k as F,l as P,s as l,x as M}from"./chunk-CBFVK3TF.js";import{execFileSync as de,execSync as ue}from"node:child_process";import{existsSync as R,readdirSync as V,readFileSync as y}from"node:fs";import{basename as le,dirname as me,join as u,relative as k}from"node:path";function Oe(t){return I(t,!1)}function Ne(t){return I(t,!0)}function I(t,e){return`import { Hono } from 'hono';
|
|
3
3
|
${e?`import { sql } from 'drizzle-orm';
|
|
4
4
|
import { db } from './db.js';
|
|
5
5
|
`:""}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import{createRequire as __tdkRequire}from'node:module';const require=__tdkRequire(import.meta.url);
|
|
2
|
-
import{b as f}from"./chunk-CF46CD6R.js";var ar="Container Runtime",_="bring-your-own";var De="database-management",cr=".tiltignore",Ie="service.json",Q="docker-compose.yml",ur=".autogenerated",Ct="TILT_TECH_STACK.star",Dt="TILT_RESOURCE_DEFAULTS.star",B="project.json",je="package.json",fr=[Ct,Dt,"spec.master"],pr=["backend","frontend","library","sdk","worker","migrator","mcp","agent",_],lr={backend:["dev","build","start"],worker:["dev","build","start"],migrator:["dev","build","start"],mcp:["dev","build","start"],agent:["dev","build","start"],frontend:["dev","build"],library:["dev","build"],sdk:["dev","build"],[_]:[]};var Z=["monitoring","elk","debezium","golden_image","verdaccio"],dr={frontend:{base:3e3,min:3e3,max:3999,range:"3000-3999"},backend:{base:4e3,min:4e3,max:4999,range:"4000-4999"},mcp:{base:4e3,min:4e3,max:5999,range:"4000-5999"},agent:{base:4e3,min:4e3,max:5999,range:"4000-5999"},[_]:{base:4e3,min:4e3,max:5999,range:"4000-5999"},worker:{base:6e3,min:6e3,max:6999,range:"6000-6999"},health:{base:5e3,min:5e3,max:5999,range:"5000-5999"},migrator:{base:7e3,min:7e3,max:7999,range:"7000-7999"}},mr={tiltUi:10350,traefik:8080},ee="https://flisk.sh/docs/quickstart/";var Ne=["node_modules",".git",".tilt",".tilt-engine","dist","build",".prisma",".turbo","coverage","tmp","temp","__tests__","test","tests",".github",".vscode","docs"],Pe=["Dockerfile",Q,"docker-compose.yaml","Tiltfile","vite.config.ts","tsconfig.json","tsconfig.build.json"],It={infra:"\u{1F3D7}\uFE0F",core:"\u{1F527}",api:"\u26A1",app:"\u{1F3A8}",orchestrator:"\u2699\uFE0F"};function hr(e){let t=e.toLowerCase();for(let[n,r]of Object.entries(It))if(t.includes(n))return r;return"\u{1F4E6}"}import{existsSync as Nt}from"node:fs";import{dirname as Pt,join as Ft,resolve as Ue}from"node:path";import{cwd as Ut}from"node:process";var Fe={name:"tdk-cli-internal",private:!0,version:"1.3.200",description:"Flisk CLI \u2014 start services on your machine.",keywords:["flisk","tilt","cli","local-dev","microservices"],homepage:"https://github.com/flisk-sh/flisk#readme",bugs:{url:"https://github.com/flisk-sh/flisk/issues"},repository:{type:"git",url:"git+https://github.com/flisk-sh/flisk.git",directory:"cli"},license:"MIT",author:"Flisk Team",type:"module",main:"./dist/index.js",types:"./dist/index.d.ts",bin:{flisk:"bin/tdk.js"},files:["dist","dist-bundle","bin","templates","README.md","Tiltfile","engine","discovery","specs","ext","!ext/ide-components/code_executor","shared-platform-engineering/docker-templates"],scripts:{build:"tsc && node scripts/bundle.mjs","build:watch":"tsc --watch","check:dist":"npm run build && ../scripts/check-cli-dist.sh",lint:"biome check .","lint:fix":"biome check . --write",typecheck:"tsc --project tsconfig.typecheck.json",clean:"rm -rf dist",dev:"bun run build:watch",test:"vitest run","test:watch":"vitest","test:coverage":"vitest run --coverage --coverage.reportOnFailure --coverage.reporter=text --coverage.reporter=html --coverage.reporter=json-summary --coverage.reporter=json --coverage.reportsDirectory=coverage --reporter=default --reporter=json --outputFile.json=test-results/vitest.json",prepack:"../scripts/stage-npm-engine.sh && npm run build"},dependencies:{commander:"^15.0.0",handlebars:"^4.7.8"},devDependencies:{"@biomejs/biome":"^2.5.13","@types/node":"^22.0.0","@types/react":"^19.3.0","@vitest/coverage-v8":"^5.0.2",ajv:"^8.17.1",chalk:"^6.0.1",esbuild:"^0.28.2",ink:"^8.0.0",knip:"^6.38.0",react:"^19.3.0","react-devtools-core":"^8.0.0",typescript:"^7.0.2",vite:"^8.3.3",vitest:"^5.0.0"},engines:{node:">=22.12.0"}};function E(e=Ut()){let t=Ue(e),n=Ue("/");for(;t!==n;){if(Nt(Ft(t,".tdk",B)))return t;let r=Pt(t);if(r===t)break;t=r}return null}var V=null;function Mt(){if(V)return V;let e=Fe;if(!e||typeof e!="object"||Array.isArray(e))throw new Error("Invalid package.json: expected object");let t=e;return V={name:String(t.name??"@flisk-sh/flisk"),version:String(t.version??"0.0.0"),fullPackage:t},V}function wr(){return Mt().version}import{existsSync as Me}from"node:fs";import{delimiter as Le,extname as Be,join as Ve}from"node:path";import{delimiter as br,extname as Lt}from"node:path";function U(){return process.platform==="win32"}function Bt(e){return e==="linux"?"linux":e==="darwin"?"darwin":e==="win32"?"windows":null}function Vt(e){return e==="x64"?"amd64":e==="arm64"?"arm64":null}function Gt(e,t){let n=Bt(e),r=Vt(t);if(!n||!r||n==="windows"&&r!=="amd64")return null;let o=`tdk-${n}-${r}`;return n==="windows"?`${o}.exe`:o}function Ar(){return Gt(process.platform,process.arch)}function Rr(){return U()?"tdk.exe":"flisk"}function te(e,t=U()){return t?Lt(e)?[e]:[e,`${e}.exe`,`${e}.cmd`,`${e}.bat`]:[e]}function G(e){let t=process.env.PATH??process.env.Path??"",n=U(),r=te(e,n);if(n&&!Be(e))for(let o of(process.env.PATHEXT??".EXE;.CMD;.BAT;.COM").split(";")){let s=o.toLowerCase();s&&!r.includes(`${e}${s}`)&&r.push(`${e}${s}`)}for(let o of t.split(Le))if(o)for(let s of r){let i=Ve(o,s);if(Me(i))return i}return null}function Ir(e){let t=process.env.PATH??process.env.Path??"",n=U(),r=te(e,n);if(n&&!Be(e))for(let i of(process.env.PATHEXT??".EXE;.CMD;.BAT;.COM").split(";")){let a=i.toLowerCase();a&&!r.includes(`${e}${a}`)&&r.push(`${e}${a}`)}let o=[],s=new Set;for(let i of t.split(Le))if(i)for(let a of r){let c=Ve(i,a);if(!Me(c))continue;let p=n?c.toLowerCase():c;s.has(p)||(s.add(p),o.push(c))}return o}import{execFileSync as Wt,execSync as Kt}from"node:child_process";var Ge=1e4;function We(){let e=!1;if(process.platform==="win32")try{return Wt(G("docker")??"docker",["ps"],{stdio:"ignore",timeout:Ge,windowsHide:!0}),"running"}catch(t){return t.code==="ETIMEDOUT"?"unresponsive":"missing"}for(let t of["docker ps","colima status","podman ps"])try{return Kt(t,{stdio:"ignore",timeout:Ge}),"running"}catch(n){n.code==="ETIMEDOUT"&&(e=!0)}return e?"unresponsive":"missing"}function W(e,t){return e[t]??0}function Ht(e,t){let n=Array.from({length:t.length+1},(r,o)=>o);for(let r=1;r<=e.length;r++){let o=[r];for(let s=1;s<=t.length;s++){let i=e[r-1]===t[s-1]?0:1;o[s]=Math.min(W(o,s-1)+1,W(n,s)+1,W(n,s-1)+i)}n=o}return W(n,t.length)}function zt(e,t){if(e.length!==t.length)return!1;for(let n=0;n<e.length-1;n++)if(e[n]!==t[n]&&e[n]===t[n+1]&&e[n+1]===t[n]&&e.slice(0,n)===t.slice(0,n)&&e.slice(n+2)===t.slice(n+2))return!0;return!1}function Ke(e,t){if(e.length<2||t.length===0||t.includes(e))return;let n=e.toLowerCase(),r,o=Number.POSITIVE_INFINITY;for(let s of t){if(s.length===0)continue;let i=s.toLowerCase(),a=zt(n,i)?1:Ht(n,i),c=Math.max(1,Math.min(2,Math.floor(Math.max(n.length,i.length)/3)));a>c||(a<o||a===o&&(r===void 0||s<r))&&(r=s,o=a)}return r}import{spawn as Jt}from"node:child_process";import{join as qt}from"node:path";function Yt(e,t=[],n={}){return new Promise((r,o)=>{let s=[e,...t];n.verbose&&console.log(`Executing: tilt ${s.join(" ")}`);let i=Jt(G("tilt")??"tilt",s,{stdio:n.inheritStdio?"inherit":"pipe",shell:!1,windowsHide:process.platform==="win32",timeout:n.timeoutMs}),a="",c="";n.inheritStdio||(i.stdout?.on("data",p=>{a+=p.toString()}),i.stderr?.on("data",p=>{c+=p.toString()})),i.on("close",p=>{r({exitCode:p??1,stdout:a,stderr:c})}),i.on("error",p=>{o(new Error(`Failed to spawn tilt: ${p.message}`))})})}async function He(){try{return(await Yt("version",[],{inheritStdio:!1,timeoutMs:1e4})).exitCode===0}catch{return!1}}function Xt(){let e=E();if(!e)throw $.notInProject();return qt(e,".tdk",".tdk-out","Tiltfile")}function ze(e){let t=Xt();e.push("-f",t)}function Wr(e,t={}){let n=[];return ze(n),t.focusTargets&&t.focusTargets.length>0&&n.push("--",`--focus=${t.focusTargets.join(",")}`),n.push(...e),t.verbose&&!t.quiet&&n.push("--verbose"),t.watch&&n.push("--watch"),n}function Kr(e={}){let t=[];return ze(t),e.focusTargets&&e.focusTargets.length>0&&t.push("--",`--focus=${e.focusTargets.join(",")}`),t}function Je(e){return e instanceof Error?e.message:String(e)}function Zr(e,t){if(process.env.TDK_VERBOSE){let n=t!==void 0?`: ${Je(t)}`:"";console.warn(f.gray(`${e}${n}`))}}var S=class extends Error{suggestions;exitCode;constructor(t,n=[],r=1){super(t),this.name="TdkError",this.suggestions=n,this.exitCode=r}display(){oe(this.message,void 0,this.suggestions)}exit(){this.display(),process.exit(this.exitCode)}},re=class extends Error{code;constructor(t=1){super(`process.exit(${t})`),this.name="ProcessExitError",this.code=t}};function ne(e,t,n=!1){let r=new Set;for(let o of e){let s=Ke(o,t);s&&r.add(n?`Did you mean "${s}" for "${o}"?`:`Did you mean "${s}"?`)}return[...r]}var $={tiltNotInstalled:()=>new S("Tilt CLI is not installed",["Install Tilt: `brew install tilt` (macOS)","Or download from: https://docs.tilt.dev/install.html","Verify with: `tilt version`",`Setup guide: ${ee}`]),dockerNotAvailable:()=>new S("Docker (or a compatible container runtime) is not running",["Start Docker Desktop, then verify with: `docker ps`","Or start Colima: `colima start`","Or start the Docker service on Linux: `sudo systemctl start docker`",`Setup guide: ${ee}`]),dockerNotResponding:()=>new S("Docker is running but not responding (`docker ps` hung for 10s)",["Quit and reopen Docker Desktop, or run `colima restart`","Then verify with: `docker ps`"]),stackNotFound:(e,t=[])=>new S(`Stack "${e}" not found`,[...ne([e],t),"Run `flisk stacks` to see available stacks","Run `flisk stack` to assign resources to a stack"]),resourceNotFound:(e,t=[])=>new S(`Resource "${e}" not found`,[...ne([e],t),"Run `flisk resources` to list all resources","Check the resource name spelling"]),unknownServices:(e,t)=>{let n=ne(e,t,e.length>1);return new S(`Unknown service ${e.join(", ")}. Valid names: ${t.join(", ")}`,n,2)},directoryExists:e=>new S(`Directory already exists: ${e}`,["Use `--path` to specify a different location","Remove the existing directory if no longer needed"]),invalidPath:e=>new S(`Invalid path: ${e}`,["Path must be within the project directory",'Path cannot contain special characters like <>:"|?*']),notInProject:()=>new S("Could not find project root (no .tdk/project.json found)",["Run this from within a Flisk project","Run `flisk project --yes` to initialize a new project"])};function eo(){let e=E();return e||$.notInProject().exit()}function Qt(e){e instanceof S&&e.exit(),oe(Je(e)),process.exit(1)}async function Zt(e,t){try{return await e()}catch(n){if(n instanceof re)throw n;return t?.verbose&&n instanceof Error&&n.stack&&console.error(f.gray(n.stack)),Qt(n)}}async function to(e,t){let n=[],r=We();return r==="unresponsive"?n.push($.dockerNotResponding()):r==="missing"&&n.push($.dockerNotAvailable()),await He()||n.push($.tiltNotInstalled()),n.length>0&&(console.error(f.red(`
|
|
2
|
+
import{b as f}from"./chunk-CF46CD6R.js";var ar="Container Runtime",_="bring-your-own";var De="database-management",cr=".tiltignore",Ie="service.json",Q="docker-compose.yml",ur=".autogenerated",Ct="TILT_TECH_STACK.star",Dt="TILT_RESOURCE_DEFAULTS.star",B="project.json",je="package.json",fr=[Ct,Dt,"spec.master"],pr=["backend","frontend","library","sdk","worker","migrator","mcp","agent",_],lr={backend:["dev","build","start"],worker:["dev","build","start"],migrator:["dev","build","start"],mcp:["dev","build","start"],agent:["dev","build","start"],frontend:["dev","build"],library:["dev","build"],sdk:["dev","build"],[_]:[]};var Z=["monitoring","elk","debezium","golden_image","verdaccio"],dr={frontend:{base:3e3,min:3e3,max:3999,range:"3000-3999"},backend:{base:4e3,min:4e3,max:4999,range:"4000-4999"},mcp:{base:4e3,min:4e3,max:5999,range:"4000-5999"},agent:{base:4e3,min:4e3,max:5999,range:"4000-5999"},[_]:{base:4e3,min:4e3,max:5999,range:"4000-5999"},worker:{base:6e3,min:6e3,max:6999,range:"6000-6999"},health:{base:5e3,min:5e3,max:5999,range:"5000-5999"},migrator:{base:7e3,min:7e3,max:7999,range:"7000-7999"}},mr={tiltUi:10350,traefik:8080},ee="https://flisk.sh/docs/quickstart/";var Ne=["node_modules",".git",".tilt",".tilt-engine","dist","build",".prisma",".turbo","coverage","tmp","temp","__tests__","test","tests",".github",".vscode","docs"],Pe=["Dockerfile",Q,"docker-compose.yaml","Tiltfile","vite.config.ts","tsconfig.json","tsconfig.build.json"],It={infra:"\u{1F3D7}\uFE0F",core:"\u{1F527}",api:"\u26A1",app:"\u{1F3A8}",orchestrator:"\u2699\uFE0F"};function hr(e){let t=e.toLowerCase();for(let[n,r]of Object.entries(It))if(t.includes(n))return r;return"\u{1F4E6}"}import{existsSync as Nt}from"node:fs";import{dirname as Pt,join as Ft,resolve as Ue}from"node:path";import{cwd as Ut}from"node:process";var Fe={name:"tdk-cli-internal",private:!0,version:"1.3.204",description:"Flisk CLI \u2014 start services on your machine.",keywords:["flisk","tilt","cli","local-dev","microservices"],homepage:"https://github.com/flisk-sh/flisk#readme",bugs:{url:"https://github.com/flisk-sh/flisk/issues"},repository:{type:"git",url:"git+https://github.com/flisk-sh/flisk.git",directory:"cli"},license:"MIT",author:"Flisk Team",type:"module",main:"./dist/index.js",types:"./dist/index.d.ts",bin:{flisk:"bin/tdk.js"},files:["dist","dist-bundle","bin","templates","README.md","Tiltfile","engine","discovery","specs","ext","!ext/ide-components/code_executor","shared-platform-engineering/docker-templates"],scripts:{build:"tsc && node scripts/bundle.mjs","build:watch":"tsc --watch","check:dist":"npm run build && ../scripts/check-cli-dist.sh",lint:"biome check .","lint:fix":"biome check . --write",typecheck:"tsc --project tsconfig.typecheck.json",clean:"rm -rf dist",dev:"bun run build:watch",test:"vitest run","test:watch":"vitest","test:coverage":"vitest run --coverage --coverage.reportOnFailure --coverage.reporter=text --coverage.reporter=html --coverage.reporter=json-summary --coverage.reporter=json --coverage.reportsDirectory=coverage --reporter=default --reporter=json --outputFile.json=test-results/vitest.json",prepack:"../scripts/stage-npm-engine.sh && npm run build"},dependencies:{commander:"^15.0.0",handlebars:"^4.7.8"},devDependencies:{"@biomejs/biome":"^2.5.13","@types/node":"^22.0.0","@types/react":"^19.3.0","@vitest/coverage-v8":"^5.0.2",ajv:"^8.17.1",chalk:"^6.0.1",esbuild:"^0.28.2",ink:"^8.0.0",knip:"^6.38.0",react:"^19.3.0","react-devtools-core":"^8.0.0",typescript:"^7.0.2",vite:"^8.3.3",vitest:"^5.0.0"},engines:{node:">=22.12.0"}};function E(e=Ut()){let t=Ue(e),n=Ue("/");for(;t!==n;){if(Nt(Ft(t,".tdk",B)))return t;let r=Pt(t);if(r===t)break;t=r}return null}var V=null;function Mt(){if(V)return V;let e=Fe;if(!e||typeof e!="object"||Array.isArray(e))throw new Error("Invalid package.json: expected object");let t=e;return V={name:String(t.name??"@flisk-sh/flisk"),version:String(t.version??"0.0.0"),fullPackage:t},V}function wr(){return Mt().version}import{existsSync as Me}from"node:fs";import{delimiter as Le,extname as Be,join as Ve}from"node:path";import{delimiter as br,extname as Lt}from"node:path";function U(){return process.platform==="win32"}function Bt(e){return e==="linux"?"linux":e==="darwin"?"darwin":e==="win32"?"windows":null}function Vt(e){return e==="x64"?"amd64":e==="arm64"?"arm64":null}function Gt(e,t){let n=Bt(e),r=Vt(t);if(!n||!r||n==="windows"&&r!=="amd64")return null;let o=`tdk-${n}-${r}`;return n==="windows"?`${o}.exe`:o}function Ar(){return Gt(process.platform,process.arch)}function Rr(){return U()?"tdk.exe":"flisk"}function te(e,t=U()){return t?Lt(e)?[e]:[e,`${e}.exe`,`${e}.cmd`,`${e}.bat`]:[e]}function G(e){let t=process.env.PATH??process.env.Path??"",n=U(),r=te(e,n);if(n&&!Be(e))for(let o of(process.env.PATHEXT??".EXE;.CMD;.BAT;.COM").split(";")){let s=o.toLowerCase();s&&!r.includes(`${e}${s}`)&&r.push(`${e}${s}`)}for(let o of t.split(Le))if(o)for(let s of r){let i=Ve(o,s);if(Me(i))return i}return null}function Ir(e){let t=process.env.PATH??process.env.Path??"",n=U(),r=te(e,n);if(n&&!Be(e))for(let i of(process.env.PATHEXT??".EXE;.CMD;.BAT;.COM").split(";")){let a=i.toLowerCase();a&&!r.includes(`${e}${a}`)&&r.push(`${e}${a}`)}let o=[],s=new Set;for(let i of t.split(Le))if(i)for(let a of r){let c=Ve(i,a);if(!Me(c))continue;let p=n?c.toLowerCase():c;s.has(p)||(s.add(p),o.push(c))}return o}import{execFileSync as Wt,execSync as Kt}from"node:child_process";var Ge=1e4;function We(){let e=!1;if(process.platform==="win32")try{return Wt(G("docker")??"docker",["ps"],{stdio:"ignore",timeout:Ge,windowsHide:!0}),"running"}catch(t){return t.code==="ETIMEDOUT"?"unresponsive":"missing"}for(let t of["docker ps","colima status","podman ps"])try{return Kt(t,{stdio:"ignore",timeout:Ge}),"running"}catch(n){n.code==="ETIMEDOUT"&&(e=!0)}return e?"unresponsive":"missing"}function W(e,t){return e[t]??0}function Ht(e,t){let n=Array.from({length:t.length+1},(r,o)=>o);for(let r=1;r<=e.length;r++){let o=[r];for(let s=1;s<=t.length;s++){let i=e[r-1]===t[s-1]?0:1;o[s]=Math.min(W(o,s-1)+1,W(n,s)+1,W(n,s-1)+i)}n=o}return W(n,t.length)}function zt(e,t){if(e.length!==t.length)return!1;for(let n=0;n<e.length-1;n++)if(e[n]!==t[n]&&e[n]===t[n+1]&&e[n+1]===t[n]&&e.slice(0,n)===t.slice(0,n)&&e.slice(n+2)===t.slice(n+2))return!0;return!1}function Ke(e,t){if(e.length<2||t.length===0||t.includes(e))return;let n=e.toLowerCase(),r,o=Number.POSITIVE_INFINITY;for(let s of t){if(s.length===0)continue;let i=s.toLowerCase(),a=zt(n,i)?1:Ht(n,i),c=Math.max(1,Math.min(2,Math.floor(Math.max(n.length,i.length)/3)));a>c||(a<o||a===o&&(r===void 0||s<r))&&(r=s,o=a)}return r}import{spawn as Jt}from"node:child_process";import{join as qt}from"node:path";function Yt(e,t=[],n={}){return new Promise((r,o)=>{let s=[e,...t];n.verbose&&console.log(`Executing: tilt ${s.join(" ")}`);let i=Jt(G("tilt")??"tilt",s,{stdio:n.inheritStdio?"inherit":"pipe",shell:!1,windowsHide:process.platform==="win32",timeout:n.timeoutMs}),a="",c="";n.inheritStdio||(i.stdout?.on("data",p=>{a+=p.toString()}),i.stderr?.on("data",p=>{c+=p.toString()})),i.on("close",p=>{r({exitCode:p??1,stdout:a,stderr:c})}),i.on("error",p=>{o(new Error(`Failed to spawn tilt: ${p.message}`))})})}async function He(){try{return(await Yt("version",[],{inheritStdio:!1,timeoutMs:1e4})).exitCode===0}catch{return!1}}function Xt(){let e=E();if(!e)throw $.notInProject();return qt(e,".tdk",".tdk-out","Tiltfile")}function ze(e){let t=Xt();e.push("-f",t)}function Wr(e,t={}){let n=[];return ze(n),t.focusTargets&&t.focusTargets.length>0&&n.push("--",`--focus=${t.focusTargets.join(",")}`),n.push(...e),t.verbose&&!t.quiet&&n.push("--verbose"),t.watch&&n.push("--watch"),n}function Kr(e={}){let t=[];return ze(t),e.focusTargets&&e.focusTargets.length>0&&t.push("--",`--focus=${e.focusTargets.join(",")}`),t}function Je(e){return e instanceof Error?e.message:String(e)}function Zr(e,t){if(process.env.TDK_VERBOSE){let n=t!==void 0?`: ${Je(t)}`:"";console.warn(f.gray(`${e}${n}`))}}var S=class extends Error{suggestions;exitCode;constructor(t,n=[],r=1){super(t),this.name="TdkError",this.suggestions=n,this.exitCode=r}display(){oe(this.message,void 0,this.suggestions)}exit(){this.display(),process.exit(this.exitCode)}},re=class extends Error{code;constructor(t=1){super(`process.exit(${t})`),this.name="ProcessExitError",this.code=t}};function ne(e,t,n=!1){let r=new Set;for(let o of e){let s=Ke(o,t);s&&r.add(n?`Did you mean "${s}" for "${o}"?`:`Did you mean "${s}"?`)}return[...r]}var $={tiltNotInstalled:()=>new S("Tilt CLI is not installed",["Install Tilt: `brew install tilt` (macOS)","Or download from: https://docs.tilt.dev/install.html","Verify with: `tilt version`",`Setup guide: ${ee}`]),dockerNotAvailable:()=>new S("Docker (or a compatible container runtime) is not running",["Start Docker Desktop, then verify with: `docker ps`","Or start Colima: `colima start`","Or start the Docker service on Linux: `sudo systemctl start docker`",`Setup guide: ${ee}`]),dockerNotResponding:()=>new S("Docker is running but not responding (`docker ps` hung for 10s)",["Quit and reopen Docker Desktop, or run `colima restart`","Then verify with: `docker ps`"]),stackNotFound:(e,t=[])=>new S(`Stack "${e}" not found`,[...ne([e],t),"Run `flisk stacks` to see available stacks","Run `flisk stack` to assign resources to a stack"]),resourceNotFound:(e,t=[])=>new S(`Resource "${e}" not found`,[...ne([e],t),"Run `flisk resources` to list all resources","Check the resource name spelling"]),unknownServices:(e,t)=>{let n=ne(e,t,e.length>1);return new S(`Unknown service ${e.join(", ")}. Valid names: ${t.join(", ")}`,n,2)},directoryExists:e=>new S(`Directory already exists: ${e}`,["Use `--path` to specify a different location","Remove the existing directory if no longer needed"]),invalidPath:e=>new S(`Invalid path: ${e}`,["Path must be within the project directory",'Path cannot contain special characters like <>:"|?*']),notInProject:()=>new S("Could not find project root (no .tdk/project.json found)",["Run this from within a Flisk project","Run `flisk project --yes` to initialize a new project"])};function eo(){let e=E();return e||$.notInProject().exit()}function Qt(e){e instanceof S&&e.exit(),oe(Je(e)),process.exit(1)}async function Zt(e,t){try{return await e()}catch(n){if(n instanceof re)throw n;return t?.verbose&&n instanceof Error&&n.stack&&console.error(f.gray(n.stack)),Qt(n)}}async function to(e,t){let n=[],r=We();return r==="unresponsive"?n.push($.dockerNotResponding()):r==="missing"&&n.push($.dockerNotAvailable()),await He()||n.push($.tiltNotInstalled()),n.length>0&&(console.error(f.red(`
|
|
3
3
|
Flisk can't start - missing prerequisites:
|
|
4
4
|
`)),n.forEach((o,s)=>{s>0&&console.error(""),o.display()}),console.error(f.gray("\nRun `flisk doctor` for a full environment check.")),process.exit(1)),Zt(e,t)}function no(e,t=1,n){oe(e,void 0,n),process.exit(t)}function oe(e,t,n){if(console.error(f.red(`\u274C ${e}`)),t&&console.error(f.gray(` ${t}`)),n&&n.length>0){console.error(f.yellow(`
|
|
5
5
|
\u{1F4A1} Suggestions:`));for(let r of n)console.error(f.cyan(` \u2192 ${r}`))}}function ro(e,t){console.error(f.red(`
|
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
import{createRequire as __tdkRequire}from'node:module';const require=__tdkRequire(import.meta.url);
|
|
2
|
-
import{Ta as _,cb as A,d as u,k as S}from"./chunk-
|
|
2
|
+
import{Ta as _,cb as A,d as u,k as S}from"./chunk-CBFVK3TF.js";import{existsSync as w,readFileSync as h}from"node:fs";import{join as i}from"node:path";var O=["postgres",u],y=["pre_alpha","alpha","beta","out_of_scope"];function D(e){return O.includes(e)}function b(e){try{return JSON.parse(h(i(e,".tdk",S),"utf-8"))}catch{return}}function d(e){try{return w(e)?h(e,"utf-8"):void 0}catch{return}}function k(e,s){let n=r=>{let t=r;for(;t<e.length&&/\s/.test(e[t]);)t+=1;return t},a=0;for(;;){let r=e.indexOf(s,a);if(r===-1)return;let t=n(r+s.length);if(e[t]==="="&&(t=n(t+1),e[t]==="[")){let o=e.indexOf("]",t+1);return o===-1?void 0:[...e.slice(t+1,o).matchAll(/"([^"]+)"|'([^']+)'/g)].map(f=>f[1]??f[2]??"")}a=r+s.length}}function N(e){let s=i(e,".tdk",".tdk-out","Tiltfile"),n=d(s);if(n)return k(n,"ALWAYS_ENABLED_INFRA")}function M(e){let s=i(e,".tdk",".tdk-out","spec.master"),n=d(s);if(n!==void 0)return/"database-management"\s*:\s*True/.test(n)}function x(e){let s=i(e,".tdk",".tdk-out"),n=d(i(s,"Tiltfile")),a=d(i(s,"spec.master")),r=d(i(s,"tdk-cli-ext","discovery","config.star")),t=d(i(s,"tdk-cli-ext","engine","topologies","tilt","config","profiles.star"));if(!n||!a||!r||!t)return!1;let o=a.match(/PRE_ALPHA_RESOURCES\s*=\s*\{([^}]*)\}/)?.[1],f=k(r,"CORE_INFRA");return/FOCUS_MODE\s*,\s*FOCUS_ENABLED_ALL\s*,\s*FOCUS_ENABLED_RESOURCES\s*=\s*Config\.apply_focus\(cfg\)/.test(n)&&/if FOCUS_MODE and FOCUS_ENABLED_ALL\s*:/.test(n)&&/"[^"]+"\s*:\s*True|'[^']+'\s*:\s*True/.test(o??"")&&(f?.includes("postgres")??!1)&&/["']postgres["']\s*:\s*["']database-management["']/.test(r)&&/for infra in CORE_INFRA_EXPORT\s*:/.test(t)&&/needed\[INFRA_STACK_MAP_EXPORT\[infra\]\]\s*=\s*True/.test(t)}function C(e){let s=b(e);if(!s)return!1;let n=s.phases??{};for(let r of y){let t=n[r]?.enabledStacks;if(Array.isArray(t)&&t.includes(u))return!0}let a=s.always_enabled_infra??A;return Array.isArray(a)&&a.includes(u)}function L(e,s){let n=new Set;for(let t of O)n.add(t);for(let t of s)n.add(t.name),t.stack&&n.add(t.stack);let a=b(e);if(a){let t=a.phases??{};for(let f of y){let l=t[f]?.enabledStacks;if(Array.isArray(l))for(let c of l)n.add(c)}let o=a.always_enabled_infra??A;if(Array.isArray(o))for(let f of o)n.add(f)}let r=N(e);if(Array.isArray(r))for(let t of r)n.add(t);return n}function $(e,s=_(e)){let n=C(e),a=N(e),r=Array.isArray(a)&&a.includes(u),t=M(e)===!0,o=n||r||t,f=!n&&x(e),l=L(e,s),c=[],E=[];for(let p of s){let P=p.config?.dependsOn??[],g=!1;for(let m of P){if(D(m)){g=!0;continue}l.has(m)||E.push({resource:p.name,name:m})}g&&c.push(p.name)}let T=o||c.length>0,F=o?"feature":c.length>0?"dependsOn":"none";return{featureOn:o,featureOnFromProjectJson:n,featureOnFromTiltfile:r,featureOnFromSpecMaster:t,focusWouldEnableDatabaseManagement:f,dependsOnUsers:c,willStart:T,reason:F,unknownDependsOnNames:E}}export{O as a,$ as b};
|