feat(FN-1225): add headless fn serve command with health checks

- Add a new serve command implementation that runs the dashboard server in headless mode and exposes a health endpoint
- Register the serve command in CLI routing and extend bin command coverage for dispatch behavior
- Add comprehensive serve command tests for startup flow, options handling, and health-check responses
- Fix mission event ordering in MissionStore to keep health snapshots deterministic under concurrent updates
- Include a changeset for @gsxdsm/fusion documenting the new fn serve capability
This commit is contained in:
gsxdsm
2026-04-08 09:26:56 -07:00
parent f0878ce7b6
commit cc4c4dc7e1
8 changed files with 1235 additions and 7 deletions

View File

@@ -3,6 +3,7 @@ import { describe, it, expect, vi, beforeEach, afterEach } from "vitest";
const runTaskCreate = vi.fn();
const runTaskList = vi.fn();
const runDesktop = vi.fn();
const runServe = vi.fn();
const runTaskPlan = vi.fn();
const runTaskImportFromGitHub = vi.fn();
const runSettingsShow = vi.fn();
@@ -41,6 +42,10 @@ vi.mock("../commands/desktop.js", () => ({
runDesktop,
}));
vi.mock("../commands/serve.js", () => ({
runServe,
}));
vi.mock("../commands/task.js", () => ({
runTaskCreate,
runTaskList,
@@ -277,6 +282,16 @@ describe("bin", () => {
expect(errorSpy).toHaveBeenCalledWith("Unknown subcommand: node wat");
});
it("routes serve command with port, host, paused, and interactive flags", async () => {
await runBin(["serve", "--port", "5050", "--host", "127.0.0.1", "--paused", "--interactive"]);
expect(runServe).toHaveBeenCalledWith(5050, {
paused: true,
interactive: true,
host: "127.0.0.1",
});
});
it("routes desktop command flags", async () => {
await runBin(["desktop", "--dev", "--paused", "--interactive"]);
@@ -323,6 +338,7 @@ describe("bin", () => {
const help = logSpy.mock.calls.map((call) => String(call[0])).join("\n");
expect(help).toContain("fn project list | ls");
expect(help).toContain("fn node list | ls");
expect(help).toContain("fn serve [--port <port>] [--host <host>] [--paused]");
expect(help).toContain("fn task comments <id>");
expect(help).toContain("--project, -P <name>");
});