@tdk-landscape/tdk-cli-core 1.3.171 → 1.3.172

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.
@@ -4,6 +4,7 @@ import { spawn } from "node:child_process";
4
4
  import { closeSync, existsSync, openSync, readFileSync } from "node:fs";
5
5
  import { tmpdir } from "node:os";
6
6
  import { isAbsolute, join } from "node:path";
7
+ import { createMachineEnvelope } from "../utils/machine-output.js";
7
8
  /** A service or stack name. A leading "-" is rejected so a value can never be read as a flag. */
8
9
  const NAME = /^[A-Za-z0-9][A-Za-z0-9._-]*$/;
9
10
  const SINCE = /^(\d+(\.\d+)?(ns|us|µs|ms|s|m|h))+$/;
@@ -131,6 +132,8 @@ export function buildUpArgs(args) {
131
132
  out.push(...only.map((name) => `--only=${name}`));
132
133
  if (flag(args.force, "force"))
133
134
  out.push("--force");
135
+ if (flag(args.dryRun, "dryRun"))
136
+ out.push("--dry-run");
134
137
  out.push("--json");
135
138
  return out;
136
139
  }
@@ -168,17 +171,13 @@ export async function startUp(args, deps = defaultUpDeps) {
168
171
  }
169
172
  child.unref();
170
173
  return {
171
- data: {
172
- schemaVersion: 1,
173
- data: {
174
- ok: true,
175
- started: true,
176
- pid: child.pid ?? null,
177
- logFile,
178
- next: "Poll the status tool until data.tilt.readiness.ready is true. Call down to stop it.",
179
- },
180
- errors: [],
181
- },
174
+ data: createMachineEnvelope({
175
+ ok: true,
176
+ started: true,
177
+ pid: child.pid ?? null,
178
+ logFile,
179
+ next: "Poll the status tool until data.tilt.readiness.ready is true. Call down to stop it.",
180
+ }),
182
181
  isError: false,
183
182
  };
184
183
  }
@@ -245,6 +244,7 @@ export function createTdkTools(run = runTdkCli, up = defaultUpDeps) {
245
244
  description: "Start only these services plus what they depend on and shared infrastructure",
246
245
  },
247
246
  force: { type: "boolean", description: "Replace a Tilt that is already running" },
247
+ dryRun: { type: "boolean", description: "Show what would be started without starting" },
248
248
  waitSeconds: {
249
249
  type: "number",
250
250
  description: "How long to watch for an early failure before returning (default 15, max 60)",
@@ -255,8 +255,15 @@ export function createTdkTools(run = runTdkCli, up = defaultUpDeps) {
255
255
  {
256
256
  name: "down",
257
257
  description: "Stop the running stack, optionally selecting its project with projectPath.",
258
- inputSchema: OBJECT({ projectPath: PROJECT_PATH }),
259
- handler: viaCli(() => ["down", "--json"]),
258
+ inputSchema: OBJECT({
259
+ projectPath: PROJECT_PATH,
260
+ dryRun: { type: "boolean", description: "Show what would be stopped without stopping" },
261
+ }),
262
+ handler: viaCli((args) => [
263
+ "down",
264
+ "--json",
265
+ ...(flag(args.dryRun, "dryRun") ? ["--dry-run"] : []),
266
+ ]),
260
267
  },
261
268
  {
262
269
  name: "status",
@@ -290,5 +297,53 @@ export function createTdkTools(run = runTdkCli, up = defaultUpDeps) {
290
297
  return ["resources", "--json", ...(stack ? [`--stack=${stack}`] : [])];
291
298
  }),
292
299
  },
300
+ {
301
+ name: "restart_resource",
302
+ description: "Restart a running resource in the stack (or trigger its rebuild). Set projectPath when the MCP server is not running from the project root.",
303
+ inputSchema: OBJECT({
304
+ projectPath: PROJECT_PATH,
305
+ resource: { type: "string", description: "Name of the resource to restart" },
306
+ }),
307
+ handler: viaCli((args) => {
308
+ const resource = optionalName(args.resource, "resource");
309
+ if (!resource)
310
+ throw new Error("resource is required");
311
+ return ["restart", resource, "--json"];
312
+ }),
313
+ },
314
+ {
315
+ name: "list_agents",
316
+ description: "List AI agent resources (appType: 'agent') in the project with their stack, runtime, durability and port. Set projectPath when the MCP server is not running from the project root.",
317
+ inputSchema: OBJECT({
318
+ projectPath: PROJECT_PATH,
319
+ stack: { type: "string", description: "Only this stack" },
320
+ }),
321
+ handler: viaCli((args) => {
322
+ const stack = optionalName(args.stack, "stack");
323
+ return ["resources", "--type=agent", "--json", ...(stack ? [`--stack=${stack}`] : [])];
324
+ }),
325
+ },
326
+ {
327
+ name: "get_agent_sessions",
328
+ description: "Inspect session checkpoints from a running AI agent resource. Set projectPath when the MCP server is not running from the project root.",
329
+ inputSchema: OBJECT({
330
+ projectPath: PROJECT_PATH,
331
+ resource: { type: "string", description: "Name of the agent resource" },
332
+ sessionId: { type: "string", description: "Optional session ID to fetch" },
333
+ }),
334
+ handler: viaCli((args) => {
335
+ const resource = optionalName(args.resource, "resource");
336
+ if (!resource)
337
+ throw new Error("resource is required");
338
+ const sessionId = optionalName(args.sessionId, "sessionId");
339
+ return [
340
+ "agent",
341
+ "sessions",
342
+ resource,
343
+ ...(sessionId ? [`--session-id=${sessionId}`] : []),
344
+ "--json",
345
+ ];
346
+ }),
347
+ },
293
348
  ];
294
349
  }
@@ -1,4 +1,5 @@
1
1
  import { CONTAINER_RUNTIME_CHECK } from "./constants.js";
2
+ import { SCHEMA_VERSION } from "./machine-output.js";
2
3
  /** Wait for concurrent probes to finish even if one throws, so they can release resources. */
3
4
  export async function collectDoctorChecks(machineChecks, projectChecks) {
4
5
  const checks = [];
@@ -28,7 +29,7 @@ function containerRuntimeReachable(checks) {
28
29
  /** Produce the same readiness decision for human and machine consumers. */
29
30
  export function createDoctorReport(checks, inProject, errors = [], portPlan, host) {
30
31
  return {
31
- schemaVersion: 1,
32
+ schemaVersion: SCHEMA_VERSION,
32
33
  data: {
33
34
  ready: errors.length === 0 &&
34
35
  checks.every((check) => check.didPass || check.isSkipped || check.isWarning),
@@ -1,6 +1,7 @@
1
1
  // Copyright (c) 2026 TDK Landscape contributors
2
2
  // SPDX-License-Identifier: MIT
3
3
  import { writeSync } from "node:fs";
4
+ import { createMachineEnvelope, } from "./machine-output.js";
4
5
  /**
5
6
  * Returns an emitter that writes at most one `{schemaVersion, data, errors}` object to stdout. If the process
6
7
  * exits before anything was emitted (a preflight `process.exit`, Tilt ending early), a failure object is written
@@ -12,7 +13,7 @@ export function createJsonEmitter(failureCode, command) {
12
13
  if (emitted)
13
14
  return;
14
15
  emitted = true;
15
- writeSync(1, `${JSON.stringify({ schemaVersion: 1, data, errors })}\n`);
16
+ writeSync(1, `${JSON.stringify(createMachineEnvelope(data, errors))}\n`);
16
17
  };
17
18
  process.once("exit", (code) => {
18
19
  emit({ ok: false }, [
@@ -1,8 +1,9 @@
1
1
  // Copyright (c) 2026 TDK Landscape contributors
2
2
  // SPDX-License-Identifier: MIT
3
3
  import { TdkError } from "./errors.js";
4
+ export const SCHEMA_VERSION = 1;
4
5
  export function createMachineEnvelope(data, errors = []) {
5
- return { schemaVersion: 1, data, errors };
6
+ return { schemaVersion: SCHEMA_VERSION, data, errors };
6
7
  }
7
8
  export function toMachineError(error) {
8
9
  if (error instanceof TdkError) {
@@ -25,4 +25,8 @@ export const PROJECT_TEMPLATES = {
25
25
  bundledPath: "examples/tdk-example",
26
26
  description: "Hono + Postgres + NATS worker + Vite example with a routed write path",
27
27
  },
28
+ "agent-stack": {
29
+ repo: "https://github.com/tdk-landscape/tdk-agent-stack.git",
30
+ description: "AI agent stack: Bun agent + MCP tool server + Postgres + NATS",
31
+ },
28
32
  };