@a5c-ai/babysitter-sdk 0.0.168 → 0.0.170-staging.00aac85c

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.
Files changed (76) hide show
  1. package/dist/cli/commands/configure.d.ts +124 -0
  2. package/dist/cli/commands/configure.d.ts.map +1 -0
  3. package/dist/cli/commands/configure.js +514 -0
  4. package/dist/cli/commands/health.d.ts +89 -0
  5. package/dist/cli/commands/health.d.ts.map +1 -0
  6. package/dist/cli/commands/health.js +579 -0
  7. package/dist/cli/commands/hookLog.d.ts +15 -0
  8. package/dist/cli/commands/hookLog.d.ts.map +1 -0
  9. package/dist/cli/commands/hookLog.js +286 -0
  10. package/dist/cli/commands/hookRun.d.ts +20 -0
  11. package/dist/cli/commands/hookRun.d.ts.map +1 -0
  12. package/dist/cli/commands/hookRun.js +544 -0
  13. package/dist/cli/commands/runExecuteTasks.d.ts +42 -0
  14. package/dist/cli/commands/runExecuteTasks.d.ts.map +1 -0
  15. package/dist/cli/commands/runExecuteTasks.js +377 -0
  16. package/dist/cli/commands/runIterate.d.ts +5 -1
  17. package/dist/cli/commands/runIterate.d.ts.map +1 -1
  18. package/dist/cli/commands/runIterate.js +75 -6
  19. package/dist/cli/commands/session.d.ts +97 -0
  20. package/dist/cli/commands/session.d.ts.map +1 -0
  21. package/dist/cli/commands/session.js +922 -0
  22. package/dist/cli/commands/skill.d.ts +87 -0
  23. package/dist/cli/commands/skill.d.ts.map +1 -0
  24. package/dist/cli/commands/skill.js +869 -0
  25. package/dist/cli/completionProof.d.ts +4 -0
  26. package/dist/cli/completionProof.d.ts.map +1 -0
  27. package/dist/cli/{completionSecret.js → completionProof.js} +7 -7
  28. package/dist/cli/main.d.ts +14 -0
  29. package/dist/cli/main.d.ts.map +1 -1
  30. package/dist/cli/main.js +649 -16
  31. package/dist/config/defaults.d.ts +165 -0
  32. package/dist/config/defaults.d.ts.map +1 -0
  33. package/dist/config/defaults.js +281 -0
  34. package/dist/config/index.d.ts +25 -0
  35. package/dist/config/index.d.ts.map +1 -0
  36. package/dist/config/index.js +35 -0
  37. package/dist/hooks/dispatcher.d.ts.map +1 -1
  38. package/dist/hooks/dispatcher.js +2 -1
  39. package/dist/index.d.ts +1 -0
  40. package/dist/index.d.ts.map +1 -1
  41. package/dist/index.js +1 -0
  42. package/dist/runtime/constants.d.ts +1 -1
  43. package/dist/runtime/constants.d.ts.map +1 -1
  44. package/dist/runtime/createRun.d.ts.map +1 -1
  45. package/dist/runtime/createRun.js +7 -3
  46. package/dist/runtime/exceptions.d.ts +186 -3
  47. package/dist/runtime/exceptions.d.ts.map +1 -1
  48. package/dist/runtime/exceptions.js +416 -15
  49. package/dist/runtime/types.d.ts +1 -0
  50. package/dist/runtime/types.d.ts.map +1 -1
  51. package/dist/session/index.d.ts +9 -0
  52. package/dist/session/index.d.ts.map +1 -0
  53. package/dist/session/index.js +30 -0
  54. package/dist/session/parse.d.ts +45 -0
  55. package/dist/session/parse.d.ts.map +1 -0
  56. package/dist/session/parse.js +159 -0
  57. package/dist/session/types.d.ts +194 -0
  58. package/dist/session/types.d.ts.map +1 -0
  59. package/dist/session/types.js +45 -0
  60. package/dist/session/write.d.ts +50 -0
  61. package/dist/session/write.d.ts.map +1 -0
  62. package/dist/session/write.js +196 -0
  63. package/dist/storage/createRunDir.d.ts.map +1 -1
  64. package/dist/storage/createRunDir.js +1 -0
  65. package/dist/storage/paths.d.ts +5 -1
  66. package/dist/storage/paths.d.ts.map +1 -1
  67. package/dist/storage/paths.js +6 -1
  68. package/dist/storage/types.d.ts +3 -1
  69. package/dist/storage/types.d.ts.map +1 -1
  70. package/dist/tasks/kinds/index.d.ts.map +1 -1
  71. package/dist/tasks/kinds/index.js +6 -1
  72. package/dist/testing/runHarness.d.ts.map +1 -1
  73. package/dist/testing/runHarness.js +5 -1
  74. package/package.json +1 -2
  75. package/dist/cli/completionSecret.d.ts +0 -4
  76. package/dist/cli/completionSecret.d.ts.map +0 -1
@@ -0,0 +1,89 @@
1
+ /**
2
+ * health command - Verify SDK installation and environment health
3
+ *
4
+ * This command performs diagnostic checks to verify:
5
+ * - SDK CLI is properly installed and version is accessible
6
+ * - .a5c directory exists and is writable
7
+ * - Node.js version is compatible (>=18)
8
+ * - Package.json has babysitter-sdk dependency if in project context
9
+ * - Environment variables are set correctly
10
+ */
11
+ /**
12
+ * Status of an individual health check
13
+ */
14
+ export type CheckStatus = "pass" | "fail" | "warn";
15
+ /**
16
+ * Result of a single health check
17
+ */
18
+ export interface HealthCheck {
19
+ /** Name of the check */
20
+ name: string;
21
+ /** Human-readable description of what was checked */
22
+ description: string;
23
+ /** Status of the check */
24
+ status: CheckStatus;
25
+ /** Detailed message about the result */
26
+ message: string;
27
+ /** Suggested next steps if the check failed or warned */
28
+ nextSteps?: string[];
29
+ /** Additional diagnostic details */
30
+ details?: Record<string, unknown>;
31
+ }
32
+ /**
33
+ * Options for running health checks
34
+ */
35
+ export interface HealthCheckOptions {
36
+ /** Output in JSON format for machine consumption */
37
+ json?: boolean;
38
+ /** Include verbose diagnostic information */
39
+ verbose?: boolean;
40
+ /** Working directory to check (defaults to cwd) */
41
+ cwd?: string;
42
+ }
43
+ /**
44
+ * Overall health check result
45
+ */
46
+ export interface HealthCheckResult {
47
+ /** Overall health status */
48
+ status: "healthy" | "degraded" | "unhealthy";
49
+ /** Timestamp of the health check */
50
+ timestamp: string;
51
+ /** Individual check results */
52
+ checks: HealthCheck[];
53
+ /** Summary counts */
54
+ summary: {
55
+ total: number;
56
+ passed: number;
57
+ failed: number;
58
+ warnings: number;
59
+ };
60
+ /** Aggregated next steps from all failing checks */
61
+ nextSteps: string[];
62
+ }
63
+ /**
64
+ * Runs all health checks and returns aggregated results
65
+ *
66
+ * @param options - Health check options
67
+ * @returns Complete health check result
68
+ *
69
+ * @example
70
+ * ```ts
71
+ * // Run health checks with default options
72
+ * const result = await runHealthCheck({});
73
+ *
74
+ * // Run with verbose output
75
+ * const result = await runHealthCheck({ verbose: true });
76
+ *
77
+ * // Get JSON output
78
+ * const result = await runHealthCheck({ json: true });
79
+ * ```
80
+ */
81
+ export declare function runHealthCheck(options: HealthCheckOptions): Promise<HealthCheckResult>;
82
+ /**
83
+ * CLI entry point for the health command
84
+ *
85
+ * @param options - Parsed CLI options
86
+ * @returns Exit code (0 for healthy, 1 for unhealthy)
87
+ */
88
+ export declare function handleHealthCommand(options: HealthCheckOptions): Promise<number>;
89
+ //# sourceMappingURL=health.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"health.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/health.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAUH;;GAEG;AACH,MAAM,MAAM,WAAW,GAAG,MAAM,GAAG,MAAM,GAAG,MAAM,CAAC;AAEnD;;GAEG;AACH,MAAM,WAAW,WAAW;IAC1B,wBAAwB;IACxB,IAAI,EAAE,MAAM,CAAC;IACb,qDAAqD;IACrD,WAAW,EAAE,MAAM,CAAC;IACpB,0BAA0B;IAC1B,MAAM,EAAE,WAAW,CAAC;IACpB,wCAAwC;IACxC,OAAO,EAAE,MAAM,CAAC;IAChB,yDAAyD;IACzD,SAAS,CAAC,EAAE,MAAM,EAAE,CAAC;IACrB,oCAAoC;IACpC,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACnC;AAED;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC,oDAAoD;IACpD,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,6CAA6C;IAC7C,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,mDAAmD;IACnD,GAAG,CAAC,EAAE,MAAM,CAAC;CACd;AAED;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAChC,4BAA4B;IAC5B,MAAM,EAAE,SAAS,GAAG,UAAU,GAAG,WAAW,CAAC;IAC7C,oCAAoC;IACpC,SAAS,EAAE,MAAM,CAAC;IAClB,+BAA+B;IAC/B,MAAM,EAAE,WAAW,EAAE,CAAC;IACtB,qBAAqB;IACrB,OAAO,EAAE;QACP,KAAK,EAAE,MAAM,CAAC;QACd,MAAM,EAAE,MAAM,CAAC;QACf,MAAM,EAAE,MAAM,CAAC;QACf,QAAQ,EAAE,MAAM,CAAC;KAClB,CAAC;IACF,oDAAoD;IACpD,SAAS,EAAE,MAAM,EAAE,CAAC;CACrB;AAyaD;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAsB,cAAc,CAAC,OAAO,EAAE,kBAAkB,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAkD5F;AA2ED;;;;;GAKG;AACH,wBAAsB,mBAAmB,CAAC,OAAO,EAAE,kBAAkB,GAAG,OAAO,CAAC,MAAM,CAAC,CAkBtF"}
@@ -0,0 +1,579 @@
1
+ "use strict";
2
+ /**
3
+ * health command - Verify SDK installation and environment health
4
+ *
5
+ * This command performs diagnostic checks to verify:
6
+ * - SDK CLI is properly installed and version is accessible
7
+ * - .a5c directory exists and is writable
8
+ * - Node.js version is compatible (>=18)
9
+ * - Package.json has babysitter-sdk dependency if in project context
10
+ * - Environment variables are set correctly
11
+ */
12
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
13
+ if (k2 === undefined) k2 = k;
14
+ var desc = Object.getOwnPropertyDescriptor(m, k);
15
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
16
+ desc = { enumerable: true, get: function() { return m[k]; } };
17
+ }
18
+ Object.defineProperty(o, k2, desc);
19
+ }) : (function(o, m, k, k2) {
20
+ if (k2 === undefined) k2 = k;
21
+ o[k2] = m[k];
22
+ }));
23
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
24
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
25
+ }) : function(o, v) {
26
+ o["default"] = v;
27
+ });
28
+ var __importStar = (this && this.__importStar) || (function () {
29
+ var ownKeys = function(o) {
30
+ ownKeys = Object.getOwnPropertyNames || function (o) {
31
+ var ar = [];
32
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
33
+ return ar;
34
+ };
35
+ return ownKeys(o);
36
+ };
37
+ return function (mod) {
38
+ if (mod && mod.__esModule) return mod;
39
+ var result = {};
40
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
41
+ __setModuleDefault(result, mod);
42
+ return result;
43
+ };
44
+ })();
45
+ Object.defineProperty(exports, "__esModule", { value: true });
46
+ exports.runHealthCheck = runHealthCheck;
47
+ exports.handleHealthCommand = handleHealthCommand;
48
+ const node_fs_1 = require("node:fs");
49
+ const path = __importStar(require("node:path"));
50
+ const defaults_1 = require("../../config/defaults");
51
+ // ============================================================================
52
+ // Color Utilities
53
+ // ============================================================================
54
+ /**
55
+ * ANSI color codes for terminal output
56
+ */
57
+ const COLORS = {
58
+ reset: "\x1b[0m",
59
+ green: "\x1b[32m",
60
+ red: "\x1b[31m",
61
+ yellow: "\x1b[33m",
62
+ cyan: "\x1b[36m",
63
+ dim: "\x1b[2m",
64
+ bold: "\x1b[1m",
65
+ };
66
+ /**
67
+ * Check symbols with colors
68
+ */
69
+ const SYMBOLS = {
70
+ pass: `${COLORS.green}\u2713${COLORS.reset}`,
71
+ fail: `${COLORS.red}\u2717${COLORS.reset}`,
72
+ warn: `${COLORS.yellow}\u26A0${COLORS.reset}`,
73
+ };
74
+ /**
75
+ * Plain symbols without colors (for non-TTY output)
76
+ */
77
+ const PLAIN_SYMBOLS = {
78
+ pass: "[PASS]",
79
+ fail: "[FAIL]",
80
+ warn: "[WARN]",
81
+ };
82
+ /**
83
+ * Checks if stdout supports colors
84
+ */
85
+ function supportsColors() {
86
+ if (process.env.NO_COLOR !== undefined) {
87
+ return false;
88
+ }
89
+ if (process.env.FORCE_COLOR !== undefined) {
90
+ return true;
91
+ }
92
+ if (process.stdout && typeof process.stdout.isTTY === "boolean") {
93
+ return process.stdout.isTTY;
94
+ }
95
+ return false;
96
+ }
97
+ /**
98
+ * Get the appropriate symbol for a check status
99
+ */
100
+ function getSymbol(status, useColors) {
101
+ return useColors ? SYMBOLS[status] : PLAIN_SYMBOLS[status];
102
+ }
103
+ // ============================================================================
104
+ // Version Utilities
105
+ // ============================================================================
106
+ /**
107
+ * Reads the CLI version from package.json
108
+ */
109
+ async function readCliVersion() {
110
+ try {
111
+ const packagePath = path.join(__dirname, "..", "..", "..", "package.json");
112
+ const raw = await node_fs_1.promises.readFile(packagePath, "utf8");
113
+ const parsed = JSON.parse(raw);
114
+ return parsed.version ?? "unknown";
115
+ }
116
+ catch {
117
+ return "unknown";
118
+ }
119
+ }
120
+ /**
121
+ * Parses a semver version string into components
122
+ */
123
+ function parseVersion(version) {
124
+ const match = version.match(/^v?(\d+)\.(\d+)\.(\d+)/);
125
+ if (!match)
126
+ return null;
127
+ return {
128
+ major: parseInt(match[1], 10),
129
+ minor: parseInt(match[2], 10),
130
+ patch: parseInt(match[3], 10),
131
+ };
132
+ }
133
+ // ============================================================================
134
+ // Individual Health Checks
135
+ // ============================================================================
136
+ /**
137
+ * Check: SDK CLI Version
138
+ * Verifies the SDK CLI is installed and version is accessible
139
+ */
140
+ async function checkSdkVersion() {
141
+ const version = await readCliVersion();
142
+ if (version === "unknown") {
143
+ return {
144
+ name: "sdk-version",
145
+ description: "SDK CLI version is accessible",
146
+ status: "fail",
147
+ message: "Unable to read SDK version from package.json",
148
+ nextSteps: [
149
+ "Ensure @a5c-ai/babysitter-sdk is properly installed",
150
+ "Run: npm install @a5c-ai/babysitter-sdk",
151
+ ],
152
+ };
153
+ }
154
+ return {
155
+ name: "sdk-version",
156
+ description: "SDK CLI version is accessible",
157
+ status: "pass",
158
+ message: `SDK version ${version}`,
159
+ details: { version },
160
+ };
161
+ }
162
+ /**
163
+ * Check: Node.js Version
164
+ * Verifies Node.js version is compatible (>=18)
165
+ */
166
+ function checkNodeVersion() {
167
+ const nodeVersion = process.version;
168
+ const parsed = parseVersion(nodeVersion);
169
+ if (!parsed) {
170
+ return {
171
+ name: "node-version",
172
+ description: "Node.js version is compatible (>=18)",
173
+ status: "warn",
174
+ message: `Unable to parse Node.js version: ${nodeVersion}`,
175
+ nextSteps: ["Verify Node.js is properly installed"],
176
+ details: { version: nodeVersion },
177
+ };
178
+ }
179
+ const minMajor = 18;
180
+ if (parsed.major < minMajor) {
181
+ return {
182
+ name: "node-version",
183
+ description: "Node.js version is compatible (>=18)",
184
+ status: "fail",
185
+ message: `Node.js ${nodeVersion} is below minimum required version (v${minMajor}.0.0)`,
186
+ nextSteps: [
187
+ `Upgrade Node.js to version ${minMajor} or higher`,
188
+ "Visit https://nodejs.org to download the latest LTS version",
189
+ "Consider using nvm or fnm for version management",
190
+ ],
191
+ details: { version: nodeVersion, required: `>=${minMajor}.0.0` },
192
+ };
193
+ }
194
+ return {
195
+ name: "node-version",
196
+ description: "Node.js version is compatible (>=18)",
197
+ status: "pass",
198
+ message: `Node.js ${nodeVersion}`,
199
+ details: { version: nodeVersion, major: parsed.major },
200
+ };
201
+ }
202
+ /**
203
+ * Check: .a5c Directory
204
+ * Verifies the .a5c directory exists and is writable
205
+ */
206
+ async function checkA5cDirectory(cwd) {
207
+ const a5cDir = path.join(cwd, ".a5c");
208
+ const runsDir = path.join(a5cDir, "runs");
209
+ try {
210
+ const stats = await node_fs_1.promises.stat(a5cDir);
211
+ if (!stats.isDirectory()) {
212
+ return {
213
+ name: "a5c-directory",
214
+ description: ".a5c directory exists and is writable",
215
+ status: "fail",
216
+ message: `.a5c exists but is not a directory at ${a5cDir}`,
217
+ nextSteps: [
218
+ "Remove the .a5c file and let the SDK create the directory",
219
+ "Or run: rm .a5c && mkdir -p .a5c/runs",
220
+ ],
221
+ details: { path: a5cDir, isDirectory: false },
222
+ };
223
+ }
224
+ // Check if writable by attempting to write a test file
225
+ const testFile = path.join(a5cDir, ".health-check-test");
226
+ try {
227
+ await node_fs_1.promises.writeFile(testFile, "test", "utf8");
228
+ await node_fs_1.promises.unlink(testFile);
229
+ }
230
+ catch (writeError) {
231
+ return {
232
+ name: "a5c-directory",
233
+ description: ".a5c directory exists and is writable",
234
+ status: "fail",
235
+ message: `.a5c directory exists but is not writable at ${a5cDir}`,
236
+ nextSteps: [
237
+ "Check file permissions on the .a5c directory",
238
+ "Run: chmod 755 .a5c",
239
+ ],
240
+ details: { path: a5cDir, writable: false },
241
+ };
242
+ }
243
+ // Check if runs subdirectory exists
244
+ let runsExists = false;
245
+ try {
246
+ const runsStats = await node_fs_1.promises.stat(runsDir);
247
+ runsExists = runsStats.isDirectory();
248
+ }
249
+ catch {
250
+ // runs dir doesn't exist yet, that's okay
251
+ }
252
+ return {
253
+ name: "a5c-directory",
254
+ description: ".a5c directory exists and is writable",
255
+ status: "pass",
256
+ message: `.a5c directory is ready at ${a5cDir}`,
257
+ details: { path: a5cDir, runsDir, runsExists, writable: true },
258
+ };
259
+ }
260
+ catch (error) {
261
+ const err = error;
262
+ if (err.code === "ENOENT") {
263
+ return {
264
+ name: "a5c-directory",
265
+ description: ".a5c directory exists and is writable",
266
+ status: "warn",
267
+ message: `.a5c directory does not exist at ${a5cDir}`,
268
+ nextSteps: [
269
+ "The directory will be created automatically when running babysitter commands",
270
+ "Or create it manually: mkdir -p .a5c/runs",
271
+ ],
272
+ details: { path: a5cDir, exists: false },
273
+ };
274
+ }
275
+ return {
276
+ name: "a5c-directory",
277
+ description: ".a5c directory exists and is writable",
278
+ status: "fail",
279
+ message: `Error accessing .a5c directory: ${err.message}`,
280
+ nextSteps: ["Check file system permissions and disk space"],
281
+ details: { path: a5cDir, error: err.message },
282
+ };
283
+ }
284
+ }
285
+ /**
286
+ * Check: Package.json Dependency
287
+ * Verifies babysitter-sdk is listed as a dependency in the project
288
+ */
289
+ async function checkPackageDependency(cwd) {
290
+ const packagePath = path.join(cwd, "package.json");
291
+ try {
292
+ const raw = await node_fs_1.promises.readFile(packagePath, "utf8");
293
+ const pkg = JSON.parse(raw);
294
+ const depVersion = pkg.dependencies?.["@a5c-ai/babysitter-sdk"];
295
+ const devDepVersion = pkg.devDependencies?.["@a5c-ai/babysitter-sdk"];
296
+ const version = depVersion || devDepVersion;
297
+ const location = depVersion ? "dependencies" : devDepVersion ? "devDependencies" : null;
298
+ if (version) {
299
+ return {
300
+ name: "package-dependency",
301
+ description: "Project has babysitter-sdk dependency",
302
+ status: "pass",
303
+ message: `@a5c-ai/babysitter-sdk@${version} found in ${location}`,
304
+ details: { version, location, packagePath },
305
+ };
306
+ }
307
+ return {
308
+ name: "package-dependency",
309
+ description: "Project has babysitter-sdk dependency",
310
+ status: "warn",
311
+ message: "@a5c-ai/babysitter-sdk not found in package.json",
312
+ nextSteps: [
313
+ "Add the dependency: npm install @a5c-ai/babysitter-sdk",
314
+ "Or if this is not a babysitter project, this warning can be ignored",
315
+ ],
316
+ details: { packagePath, found: false },
317
+ };
318
+ }
319
+ catch (error) {
320
+ const err = error;
321
+ if (err.code === "ENOENT") {
322
+ return {
323
+ name: "package-dependency",
324
+ description: "Project has babysitter-sdk dependency",
325
+ status: "warn",
326
+ message: "No package.json found in current directory",
327
+ nextSteps: [
328
+ "If this is a Node.js project, run: npm init -y",
329
+ "If not in a project directory, this warning can be ignored",
330
+ ],
331
+ details: { packagePath, exists: false },
332
+ };
333
+ }
334
+ return {
335
+ name: "package-dependency",
336
+ description: "Project has babysitter-sdk dependency",
337
+ status: "warn",
338
+ message: `Error reading package.json: ${err.message}`,
339
+ details: { packagePath, error: err.message },
340
+ };
341
+ }
342
+ }
343
+ /**
344
+ * Check: Environment Variables
345
+ * Verifies babysitter-related environment variables are set correctly
346
+ */
347
+ function checkEnvironmentVariables() {
348
+ const envChecks = [];
349
+ // Check BABYSITTER_RUNS_DIR
350
+ const runsDir = process.env[defaults_1.CONFIG_ENV_VARS.RUNS_DIR];
351
+ envChecks.push({
352
+ name: "BABYSITTER_RUNS_DIR",
353
+ key: defaults_1.CONFIG_ENV_VARS.RUNS_DIR,
354
+ value: runsDir,
355
+ required: false,
356
+ valid: true,
357
+ note: runsDir ? `Custom runs directory: ${runsDir}` : `Using default: ${defaults_1.DEFAULTS.runsDir}`,
358
+ });
359
+ // Check BABYSITTER_MAX_ITERATIONS
360
+ const maxIterations = process.env[defaults_1.CONFIG_ENV_VARS.MAX_ITERATIONS];
361
+ let maxIterValid = true;
362
+ if (maxIterations) {
363
+ const parsed = parseInt(maxIterations, 10);
364
+ maxIterValid = Number.isFinite(parsed) && parsed > 0;
365
+ }
366
+ envChecks.push({
367
+ name: "BABYSITTER_MAX_ITERATIONS",
368
+ key: defaults_1.CONFIG_ENV_VARS.MAX_ITERATIONS,
369
+ value: maxIterations,
370
+ required: false,
371
+ valid: maxIterValid,
372
+ note: maxIterations
373
+ ? maxIterValid
374
+ ? `Max iterations: ${maxIterations}`
375
+ : `Invalid value: ${maxIterations} (must be positive integer)`
376
+ : `Using default: ${defaults_1.DEFAULTS.maxIterations}`,
377
+ });
378
+ // Check BABYSITTER_LOG_LEVEL
379
+ const logLevel = process.env[defaults_1.CONFIG_ENV_VARS.LOG_LEVEL];
380
+ const validLogLevels = ["debug", "info", "warn", "error", "silent"];
381
+ const logLevelValid = !logLevel || validLogLevels.includes(logLevel.toLowerCase());
382
+ envChecks.push({
383
+ name: "BABYSITTER_LOG_LEVEL",
384
+ key: defaults_1.CONFIG_ENV_VARS.LOG_LEVEL,
385
+ value: logLevel,
386
+ required: false,
387
+ valid: logLevelValid,
388
+ note: logLevel
389
+ ? logLevelValid
390
+ ? `Log level: ${logLevel}`
391
+ : `Invalid value: ${logLevel} (must be one of: ${validLogLevels.join(", ")})`
392
+ : `Using default: ${defaults_1.DEFAULTS.logLevel}`,
393
+ });
394
+ // Check BABYSITTER_ALLOW_SECRET_LOGS
395
+ const allowSecrets = process.env[defaults_1.CONFIG_ENV_VARS.ALLOW_SECRET_LOGS];
396
+ envChecks.push({
397
+ name: "BABYSITTER_ALLOW_SECRET_LOGS",
398
+ key: defaults_1.CONFIG_ENV_VARS.ALLOW_SECRET_LOGS,
399
+ value: allowSecrets,
400
+ required: false,
401
+ valid: true,
402
+ note: allowSecrets
403
+ ? `Secret logging: ${allowSecrets === "1" || allowSecrets.toLowerCase() === "true" ? "enabled" : "disabled"}`
404
+ : "Secret logging: disabled (default)",
405
+ });
406
+ const invalidVars = envChecks.filter((c) => !c.valid);
407
+ const setVars = envChecks.filter((c) => c.value !== undefined);
408
+ if (invalidVars.length > 0) {
409
+ return {
410
+ name: "environment-variables",
411
+ description: "Environment variables are configured correctly",
412
+ status: "fail",
413
+ message: `${invalidVars.length} environment variable(s) have invalid values`,
414
+ nextSteps: invalidVars.map((v) => `Fix ${v.name}: ${v.note}`),
415
+ details: { checks: envChecks, invalid: invalidVars.map((v) => v.name) },
416
+ };
417
+ }
418
+ return {
419
+ name: "environment-variables",
420
+ description: "Environment variables are configured correctly",
421
+ status: "pass",
422
+ message: setVars.length > 0
423
+ ? `${setVars.length} environment variable(s) configured`
424
+ : "Using default configuration",
425
+ details: { checks: envChecks, customized: setVars.map((v) => v.name) },
426
+ };
427
+ }
428
+ // ============================================================================
429
+ // Main Health Check Runner
430
+ // ============================================================================
431
+ /**
432
+ * Runs all health checks and returns aggregated results
433
+ *
434
+ * @param options - Health check options
435
+ * @returns Complete health check result
436
+ *
437
+ * @example
438
+ * ```ts
439
+ * // Run health checks with default options
440
+ * const result = await runHealthCheck({});
441
+ *
442
+ * // Run with verbose output
443
+ * const result = await runHealthCheck({ verbose: true });
444
+ *
445
+ * // Get JSON output
446
+ * const result = await runHealthCheck({ json: true });
447
+ * ```
448
+ */
449
+ async function runHealthCheck(options) {
450
+ const cwd = options.cwd ?? process.cwd();
451
+ const timestamp = new Date().toISOString();
452
+ // Run all checks
453
+ const checks = await Promise.all([
454
+ checkSdkVersion(),
455
+ checkNodeVersion(),
456
+ checkA5cDirectory(cwd),
457
+ checkPackageDependency(cwd),
458
+ checkEnvironmentVariables(),
459
+ ]);
460
+ // Calculate summary
461
+ const summary = {
462
+ total: checks.length,
463
+ passed: checks.filter((c) => c.status === "pass").length,
464
+ failed: checks.filter((c) => c.status === "fail").length,
465
+ warnings: checks.filter((c) => c.status === "warn").length,
466
+ };
467
+ // Determine overall status
468
+ let status;
469
+ if (summary.failed > 0) {
470
+ status = "unhealthy";
471
+ }
472
+ else if (summary.warnings > 0) {
473
+ status = "degraded";
474
+ }
475
+ else {
476
+ status = "healthy";
477
+ }
478
+ // Aggregate next steps from failing and warning checks
479
+ const nextSteps = checks
480
+ .filter((c) => c.status === "fail" || c.status === "warn")
481
+ .flatMap((c) => c.nextSteps ?? []);
482
+ const result = {
483
+ status,
484
+ timestamp,
485
+ checks,
486
+ summary,
487
+ nextSteps,
488
+ };
489
+ // Output results
490
+ if (!options.json) {
491
+ outputTextResult(result, options);
492
+ }
493
+ return result;
494
+ }
495
+ /**
496
+ * Outputs health check results in human-readable format
497
+ */
498
+ function outputTextResult(result, options) {
499
+ const useColors = supportsColors();
500
+ const { verbose } = options;
501
+ // Header
502
+ console.log("");
503
+ const statusColor = result.status === "healthy"
504
+ ? COLORS.green
505
+ : result.status === "degraded"
506
+ ? COLORS.yellow
507
+ : COLORS.red;
508
+ const statusText = useColors
509
+ ? `${statusColor}${COLORS.bold}${result.status.toUpperCase()}${COLORS.reset}`
510
+ : result.status.toUpperCase();
511
+ console.log(`Babysitter SDK Health Check: ${statusText}`);
512
+ console.log("");
513
+ // Individual checks
514
+ for (const check of result.checks) {
515
+ const symbol = getSymbol(check.status, useColors);
516
+ console.log(` ${symbol} ${check.description}`);
517
+ if (verbose || check.status !== "pass") {
518
+ const msgColor = check.status === "pass"
519
+ ? COLORS.dim
520
+ : check.status === "warn"
521
+ ? COLORS.yellow
522
+ : COLORS.red;
523
+ const message = useColors ? `${msgColor}${check.message}${COLORS.reset}` : check.message;
524
+ console.log(` ${message}`);
525
+ }
526
+ if (verbose && check.details) {
527
+ const detailsStr = JSON.stringify(check.details, null, 2)
528
+ .split("\n")
529
+ .map((line) => ` ${useColors ? COLORS.dim : ""}${line}${useColors ? COLORS.reset : ""}`)
530
+ .join("\n");
531
+ console.log(detailsStr);
532
+ }
533
+ }
534
+ console.log("");
535
+ // Summary
536
+ const summaryLine = [
537
+ `${result.summary.passed} passed`,
538
+ result.summary.failed > 0 ? `${result.summary.failed} failed` : null,
539
+ result.summary.warnings > 0 ? `${result.summary.warnings} warnings` : null,
540
+ ]
541
+ .filter(Boolean)
542
+ .join(", ");
543
+ console.log(`Summary: ${summaryLine}`);
544
+ // Next steps
545
+ if (result.nextSteps.length > 0) {
546
+ console.log("");
547
+ const nextStepsHeader = useColors
548
+ ? `${COLORS.cyan}${COLORS.bold}Next Steps:${COLORS.reset}`
549
+ : "Next Steps:";
550
+ console.log(nextStepsHeader);
551
+ for (const step of result.nextSteps) {
552
+ console.log(` - ${step}`);
553
+ }
554
+ }
555
+ console.log("");
556
+ }
557
+ /**
558
+ * CLI entry point for the health command
559
+ *
560
+ * @param options - Parsed CLI options
561
+ * @returns Exit code (0 for healthy, 1 for unhealthy)
562
+ */
563
+ async function handleHealthCommand(options) {
564
+ const result = await runHealthCheck(options);
565
+ if (options.json) {
566
+ console.log(JSON.stringify(result, null, 2));
567
+ }
568
+ // Return exit code based on status
569
+ switch (result.status) {
570
+ case "healthy":
571
+ return 0;
572
+ case "degraded":
573
+ return 0; // Warnings don't cause failure
574
+ case "unhealthy":
575
+ return 1;
576
+ default:
577
+ return 1;
578
+ }
579
+ }
@@ -0,0 +1,15 @@
1
+ /**
2
+ * hook:log CLI command.
3
+ *
4
+ * Reads a hook payload from stdin, extracts the relevant fields for the
5
+ * given hook type, formats a structured log line, and appends it to the
6
+ * specified log file. This consolidates the field-extraction logic that
7
+ * was previously duplicated across 13 logger.sh shell scripts.
8
+ */
9
+ export interface HookLogCommandArgs {
10
+ hookType: string;
11
+ logFile: string;
12
+ json: boolean;
13
+ }
14
+ export declare function handleHookLog(args: HookLogCommandArgs): Promise<number>;
15
+ //# sourceMappingURL=hookLog.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"hookLog.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/hookLog.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAUH,MAAM,WAAW,kBAAkB;IACjC,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,EAAE,OAAO,CAAC;CACf;AAoLD,wBAAsB,aAAa,CAAC,IAAI,EAAE,kBAAkB,GAAG,OAAO,CAAC,MAAM,CAAC,CAuG7E"}