agentsmesh 0.5.0 → 0.6.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/CHANGELOG.md +65 -6
- package/README.md +167 -78
- package/dist/{canonical-types-gdrUi3bD.d.ts → canonical-types-CZwrJoBX.d.ts} +1 -1
- package/dist/canonical.d.ts +3 -2
- package/dist/canonical.js +59 -70
- package/dist/canonical.js.map +1 -1
- package/dist/cli.js +453 -17020
- package/dist/engine.d.ts +186 -5
- package/dist/engine.js +1673 -882
- package/dist/engine.js.map +1 -1
- package/dist/index.d.ts +6 -0
- package/dist/index.js +12312 -0
- package/dist/index.js.map +1 -0
- package/dist/{target-descriptor-D64xD0C2.d.ts → target-descriptor-DjHhww11.d.ts} +30 -9
- package/dist/targets.d.ts +4 -3
- package/dist/targets.js +572 -775
- package/dist/targets.js.map +1 -1
- package/package.json +17 -3
- package/schemas/agentsmesh.json +122 -8
- package/dist/cli.js.map +0 -1
package/dist/canonical.js
CHANGED
|
@@ -1,27 +1,31 @@
|
|
|
1
|
+
import { join, basename } from 'path';
|
|
2
|
+
import { access, readdir, realpath, stat, readFile } from 'fs/promises';
|
|
3
|
+
import { constants } from 'fs';
|
|
4
|
+
import { parse } from 'yaml';
|
|
5
|
+
|
|
1
6
|
// src/canonical/load/loader.ts
|
|
2
|
-
import { join as join3 } from "path";
|
|
3
7
|
|
|
4
|
-
// src/
|
|
5
|
-
|
|
8
|
+
// src/core/errors.ts
|
|
9
|
+
var AgentsMeshError = class extends Error {
|
|
10
|
+
code;
|
|
11
|
+
constructor(code, message, options) {
|
|
12
|
+
super(message, options);
|
|
13
|
+
this.name = "AgentsMeshError";
|
|
14
|
+
this.code = code;
|
|
15
|
+
}
|
|
16
|
+
};
|
|
17
|
+
var FileSystemError = class extends AgentsMeshError {
|
|
18
|
+
path;
|
|
19
|
+
errnoCode;
|
|
20
|
+
constructor(path, message, options) {
|
|
21
|
+
super("AM_FILESYSTEM", message, options);
|
|
22
|
+
this.name = "FileSystemError";
|
|
23
|
+
this.path = path;
|
|
24
|
+
this.errnoCode = options?.errnoCode;
|
|
25
|
+
}
|
|
26
|
+
};
|
|
6
27
|
|
|
7
28
|
// src/utils/filesystem/fs.ts
|
|
8
|
-
import {
|
|
9
|
-
readFile,
|
|
10
|
-
writeFile,
|
|
11
|
-
access,
|
|
12
|
-
mkdir,
|
|
13
|
-
rename,
|
|
14
|
-
readdir,
|
|
15
|
-
copyFile,
|
|
16
|
-
stat,
|
|
17
|
-
symlink,
|
|
18
|
-
unlink,
|
|
19
|
-
lstat,
|
|
20
|
-
readlink,
|
|
21
|
-
realpath
|
|
22
|
-
} from "fs/promises";
|
|
23
|
-
import { dirname, join, resolve } from "path";
|
|
24
|
-
import { constants } from "fs";
|
|
25
29
|
var UTF8_BOM = "\uFEFF";
|
|
26
30
|
async function readFileSafe(path) {
|
|
27
31
|
try {
|
|
@@ -30,9 +34,10 @@ async function readFileSafe(path) {
|
|
|
30
34
|
} catch (err) {
|
|
31
35
|
const e = err;
|
|
32
36
|
if (e.code === "ENOENT") return null;
|
|
33
|
-
throw new
|
|
37
|
+
throw new FileSystemError(
|
|
38
|
+
path,
|
|
34
39
|
`Failed to read ${path}: ${e.message}. Ensure the file exists and is readable.`,
|
|
35
|
-
{ cause: err }
|
|
40
|
+
{ cause: err, errnoCode: e.code }
|
|
36
41
|
);
|
|
37
42
|
}
|
|
38
43
|
}
|
|
@@ -51,9 +56,11 @@ async function readDirRecursive(dir, visited) {
|
|
|
51
56
|
} catch (err) {
|
|
52
57
|
const e = err;
|
|
53
58
|
if (e.code === "ENOENT" || e.code === "ENOTDIR" || e.code === "ELOOP") return [];
|
|
54
|
-
throw new
|
|
55
|
-
|
|
56
|
-
|
|
59
|
+
throw new FileSystemError(
|
|
60
|
+
dir,
|
|
61
|
+
`Failed to read directory ${dir}: ${e.message}. Check permissions.`,
|
|
62
|
+
{ cause: err, errnoCode: e.code }
|
|
63
|
+
);
|
|
57
64
|
}
|
|
58
65
|
const seen = visited ?? /* @__PURE__ */ new Set();
|
|
59
66
|
if (seen.has(canonicalDir)) return [];
|
|
@@ -77,14 +84,13 @@ async function readDirRecursive(dir, visited) {
|
|
|
77
84
|
} catch (err) {
|
|
78
85
|
const e = err;
|
|
79
86
|
if (e.code === "ENOENT" || e.code === "ENOTDIR" || e.code === "EACCES") return [];
|
|
80
|
-
throw new
|
|
81
|
-
|
|
82
|
-
|
|
87
|
+
throw new FileSystemError(
|
|
88
|
+
dir,
|
|
89
|
+
`Failed to read directory ${dir}: ${e.message}. Check permissions.`,
|
|
90
|
+
{ cause: err, errnoCode: e.code }
|
|
91
|
+
);
|
|
83
92
|
}
|
|
84
93
|
}
|
|
85
|
-
|
|
86
|
-
// src/utils/text/markdown.ts
|
|
87
|
-
import { parse as yamlParse, stringify as yamlStringify } from "yaml";
|
|
88
94
|
function parseFrontmatter(content) {
|
|
89
95
|
const open = content.indexOf("---");
|
|
90
96
|
if (open !== 0) {
|
|
@@ -96,7 +102,7 @@ function parseFrontmatter(content) {
|
|
|
96
102
|
}
|
|
97
103
|
const yamlStr = content.slice(3, close).trim();
|
|
98
104
|
const body = content.slice(close + 3).trim();
|
|
99
|
-
const frontmatter = yamlStr === "" ? {} :
|
|
105
|
+
const frontmatter = yamlStr === "" ? {} : parse(yamlStr) ?? {};
|
|
100
106
|
return { frontmatter, body };
|
|
101
107
|
}
|
|
102
108
|
|
|
@@ -142,9 +148,6 @@ async function parseRules(rulesDir) {
|
|
|
142
148
|
}
|
|
143
149
|
return rules;
|
|
144
150
|
}
|
|
145
|
-
|
|
146
|
-
// src/canonical/features/commands.ts
|
|
147
|
-
import { basename as basename2 } from "path";
|
|
148
151
|
function toBool(v) {
|
|
149
152
|
return v === true || v === "true" || v === 1 || v === "1";
|
|
150
153
|
}
|
|
@@ -159,13 +162,13 @@ function toToolsArray(v) {
|
|
|
159
162
|
}
|
|
160
163
|
async function parseCommands(commandsDir) {
|
|
161
164
|
const files = await readDirRecursive(commandsDir);
|
|
162
|
-
const mdFiles = files.filter((f) => f.endsWith(".md") && !
|
|
165
|
+
const mdFiles = files.filter((f) => f.endsWith(".md") && !basename(f).startsWith("_"));
|
|
163
166
|
const commands = [];
|
|
164
167
|
for (const path of mdFiles) {
|
|
165
168
|
const content = await readFileSafe(path);
|
|
166
169
|
if (!content) continue;
|
|
167
170
|
const { frontmatter, body } = parseFrontmatter(content);
|
|
168
|
-
const name =
|
|
171
|
+
const name = basename(path, ".md");
|
|
169
172
|
const fromCamel = toToolsArray(frontmatter.allowedTools);
|
|
170
173
|
const fromKebab = toToolsArray(frontmatter["allowed-tools"]);
|
|
171
174
|
const allowedTools = fromCamel.length > 0 ? fromCamel : fromKebab;
|
|
@@ -180,9 +183,6 @@ async function parseCommands(commandsDir) {
|
|
|
180
183
|
}
|
|
181
184
|
return commands;
|
|
182
185
|
}
|
|
183
|
-
|
|
184
|
-
// src/canonical/features/agents.ts
|
|
185
|
-
import { basename as basename3 } from "path";
|
|
186
186
|
function toStrArray2(v) {
|
|
187
187
|
if (Array.isArray(v)) {
|
|
188
188
|
return v.filter((x) => typeof x === "string").map((s) => s.trim()).filter(Boolean);
|
|
@@ -211,13 +211,13 @@ function toHooks(v) {
|
|
|
211
211
|
}
|
|
212
212
|
async function parseAgents(agentsDir) {
|
|
213
213
|
const files = await readDirRecursive(agentsDir);
|
|
214
|
-
const mdFiles = files.filter((f) => f.endsWith(".md") && !
|
|
214
|
+
const mdFiles = files.filter((f) => f.endsWith(".md") && !basename(f).startsWith("_"));
|
|
215
215
|
const agents = [];
|
|
216
216
|
for (const path of mdFiles) {
|
|
217
217
|
const content = await readFileSafe(path);
|
|
218
218
|
if (!content) continue;
|
|
219
219
|
const { frontmatter, body } = parseFrontmatter(content);
|
|
220
|
-
const name =
|
|
220
|
+
const name = basename(path, ".md");
|
|
221
221
|
const toolsCamel = toStrArray2(frontmatter.tools);
|
|
222
222
|
const toolsKebab = toStrArray2(frontmatter["tools"]);
|
|
223
223
|
const tools = toolsCamel.length > 0 ? toolsCamel : toolsKebab;
|
|
@@ -250,10 +250,6 @@ async function parseAgents(agentsDir) {
|
|
|
250
250
|
}
|
|
251
251
|
return agents;
|
|
252
252
|
}
|
|
253
|
-
|
|
254
|
-
// src/canonical/features/skills.ts
|
|
255
|
-
import { basename as basename4, join as join2 } from "path";
|
|
256
|
-
import { readdir as readdir2 } from "fs/promises";
|
|
257
253
|
async function readContent(path) {
|
|
258
254
|
const c = await readFileSafe(path);
|
|
259
255
|
return c ?? "";
|
|
@@ -278,7 +274,7 @@ async function listSupportingFiles(skillDir) {
|
|
|
278
274
|
async function parseSkills(skillsDir) {
|
|
279
275
|
let entries;
|
|
280
276
|
try {
|
|
281
|
-
entries = await
|
|
277
|
+
entries = await readdir(skillsDir, { withFileTypes: true });
|
|
282
278
|
} catch {
|
|
283
279
|
return [];
|
|
284
280
|
}
|
|
@@ -286,8 +282,8 @@ async function parseSkills(skillsDir) {
|
|
|
286
282
|
for (const ent of entries) {
|
|
287
283
|
if (!ent.isDirectory()) continue;
|
|
288
284
|
if (ent.name.startsWith("_")) continue;
|
|
289
|
-
const skillDir =
|
|
290
|
-
const skillPath =
|
|
285
|
+
const skillDir = join(skillsDir, ent.name);
|
|
286
|
+
const skillPath = join(skillDir, SKILL_FILE);
|
|
291
287
|
const content = await readFileSafe(skillPath);
|
|
292
288
|
if (!content) continue;
|
|
293
289
|
const { frontmatter, body } = parseFrontmatter(content);
|
|
@@ -357,9 +353,6 @@ async function parseMcp(mcpPath) {
|
|
|
357
353
|
}
|
|
358
354
|
return { mcpServers };
|
|
359
355
|
}
|
|
360
|
-
|
|
361
|
-
// src/canonical/features/permissions.ts
|
|
362
|
-
import { parse as parseYaml } from "yaml";
|
|
363
356
|
function ensureStringArray(val) {
|
|
364
357
|
if (!Array.isArray(val)) return [];
|
|
365
358
|
return val.filter((x) => typeof x === "string");
|
|
@@ -370,7 +363,7 @@ async function parsePermissions(permissionsPath) {
|
|
|
370
363
|
if (!content.trim()) return { allow: [], deny: [], ask: [] };
|
|
371
364
|
let parsed;
|
|
372
365
|
try {
|
|
373
|
-
parsed =
|
|
366
|
+
parsed = parse(content);
|
|
374
367
|
} catch {
|
|
375
368
|
return null;
|
|
376
369
|
}
|
|
@@ -382,9 +375,6 @@ async function parsePermissions(permissionsPath) {
|
|
|
382
375
|
return { allow, deny, ask };
|
|
383
376
|
}
|
|
384
377
|
|
|
385
|
-
// src/canonical/features/hooks.ts
|
|
386
|
-
import { parse as parseYaml2 } from "yaml";
|
|
387
|
-
|
|
388
378
|
// src/core/hook-command.ts
|
|
389
379
|
function trimString(value) {
|
|
390
380
|
return typeof value === "string" ? value.trim() : "";
|
|
@@ -427,7 +417,7 @@ async function parseHooks(hooksPath) {
|
|
|
427
417
|
if (!content.trim()) return {};
|
|
428
418
|
let parsed;
|
|
429
419
|
try {
|
|
430
|
-
parsed =
|
|
420
|
+
parsed = parse(content);
|
|
431
421
|
} catch {
|
|
432
422
|
return null;
|
|
433
423
|
}
|
|
@@ -462,17 +452,17 @@ async function parseIgnore(ignorePath) {
|
|
|
462
452
|
|
|
463
453
|
// src/canonical/load/loader.ts
|
|
464
454
|
async function loadCanonicalFiles(canonicalDirOrProjectRoot) {
|
|
465
|
-
const nestedCanonicalDir =
|
|
455
|
+
const nestedCanonicalDir = join(canonicalDirOrProjectRoot, ".agentsmesh");
|
|
466
456
|
const canonicalDir = await exists(nestedCanonicalDir) ? nestedCanonicalDir : canonicalDirOrProjectRoot;
|
|
467
457
|
const [rules, commands, agents, skills, mcp, permissions, hooks, ignore] = await Promise.all([
|
|
468
|
-
parseRules(
|
|
469
|
-
parseCommands(
|
|
470
|
-
parseAgents(
|
|
471
|
-
parseSkills(
|
|
472
|
-
parseMcp(
|
|
473
|
-
parsePermissions(
|
|
474
|
-
parseHooks(
|
|
475
|
-
parseIgnore(
|
|
458
|
+
parseRules(join(canonicalDir, "rules")),
|
|
459
|
+
parseCommands(join(canonicalDir, "commands")),
|
|
460
|
+
parseAgents(join(canonicalDir, "agents")),
|
|
461
|
+
parseSkills(join(canonicalDir, "skills")),
|
|
462
|
+
parseMcp(join(canonicalDir, "mcp.json")),
|
|
463
|
+
parsePermissions(join(canonicalDir, "permissions.yaml")),
|
|
464
|
+
parseHooks(join(canonicalDir, "hooks.yaml")),
|
|
465
|
+
parseIgnore(join(canonicalDir, "ignore"))
|
|
476
466
|
]);
|
|
477
467
|
return {
|
|
478
468
|
rules,
|
|
@@ -490,8 +480,7 @@ async function loadCanonicalFiles(canonicalDirOrProjectRoot) {
|
|
|
490
480
|
async function loadCanonical(projectRoot) {
|
|
491
481
|
return loadCanonicalFiles(projectRoot);
|
|
492
482
|
}
|
|
493
|
-
|
|
494
|
-
|
|
495
|
-
|
|
496
|
-
};
|
|
483
|
+
|
|
484
|
+
export { loadCanonical, loadCanonicalFiles };
|
|
485
|
+
//# sourceMappingURL=canonical.js.map
|
|
497
486
|
//# sourceMappingURL=canonical.js.map
|
package/dist/canonical.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/canonical/load/loader.ts","../src/canonical/features/rules.ts","../src/utils/filesystem/fs.ts","../src/utils/text/markdown.ts","../src/canonical/features/commands.ts","../src/canonical/features/agents.ts","../src/canonical/features/skills.ts","../src/canonical/features/mcp.ts","../src/canonical/features/permissions.ts","../src/canonical/features/hooks.ts","../src/core/hook-command.ts","../src/canonical/features/ignore.ts","../src/public/canonical.ts"],"sourcesContent":["/**\n * Load all canonical files from a canonical directory into CanonicalFiles.\n */\n\nimport { join } from 'node:path';\nimport type { CanonicalFiles } from '../../core/types.js';\nimport { parseRules } from '../features/rules.js';\nimport { parseCommands } from '../features/commands.js';\nimport { parseAgents } from '../features/agents.js';\nimport { parseSkills } from '../features/skills.js';\nimport { parseMcp } from '../features/mcp.js';\nimport { parsePermissions } from '../features/permissions.js';\nimport { parseHooks } from '../features/hooks.js';\nimport { parseIgnore } from '../features/ignore.js';\nimport { exists } from '../../utils/filesystem/fs.js';\n\n/**\n * Load all canonical files from a canonical directory or project root.\n * Missing directories/files yield empty arrays or null as per each parser.\n *\n * @param canonicalDirOrProjectRoot - Absolute path to canonical directory or project root\n * @returns CanonicalFiles with all parsed data\n */\nexport async function loadCanonicalFiles(\n canonicalDirOrProjectRoot: string,\n): Promise<CanonicalFiles> {\n const nestedCanonicalDir = join(canonicalDirOrProjectRoot, '.agentsmesh');\n const canonicalDir = (await exists(nestedCanonicalDir))\n ? nestedCanonicalDir\n : canonicalDirOrProjectRoot;\n\n const [rules, commands, agents, skills, mcp, permissions, hooks, ignore] = await Promise.all([\n parseRules(join(canonicalDir, 'rules')),\n parseCommands(join(canonicalDir, 'commands')),\n parseAgents(join(canonicalDir, 'agents')),\n parseSkills(join(canonicalDir, 'skills')),\n parseMcp(join(canonicalDir, 'mcp.json')),\n parsePermissions(join(canonicalDir, 'permissions.yaml')),\n parseHooks(join(canonicalDir, 'hooks.yaml')),\n parseIgnore(join(canonicalDir, 'ignore')),\n ]);\n\n return {\n rules,\n commands,\n agents,\n skills,\n mcp,\n permissions,\n hooks,\n ignore,\n };\n}\n","/**\n * Parse .agentsmesh/rules/*.md into CanonicalRule objects.\n */\n\nimport { basename } from 'node:path';\nimport type { CanonicalRule } from '../../core/types.js';\nimport { readFileSafe, readDirRecursive } from '../../utils/filesystem/fs.js';\nimport { parseFrontmatter } from '../../utils/text/markdown.js';\n\nconst VALID_TRIGGERS = ['always_on', 'model_decision', 'glob', 'manual'] as const;\ntype Trigger = (typeof VALID_TRIGGERS)[number];\n\n/**\n * Coerce value to string array. Handles string, string[], or invalid.\n * @param v - Raw value from YAML\n * @returns Normalized string array\n */\nfunction toStrArray(v: unknown): string[] {\n if (Array.isArray(v)) return v.filter((x): x is string => typeof x === 'string');\n if (typeof v === 'string') return v ? [v] : [];\n return [];\n}\n\n/**\n * Parse all rule files in a rules directory.\n * @param rulesDir - Absolute path to .agentsmesh/rules\n * @returns Array of parsed CanonicalRule, or [] if dir missing/empty\n */\nexport async function parseRules(rulesDir: string): Promise<CanonicalRule[]> {\n const files = await readDirRecursive(rulesDir);\n const mdFiles = files.filter((f) => {\n if (!f.endsWith('.md')) return false;\n const name = basename(f, '.md');\n return name === '_root' || !name.startsWith('_');\n });\n const rules: CanonicalRule[] = [];\n for (const path of mdFiles) {\n const content = await readFileSafe(path);\n if (!content) continue;\n const { frontmatter, body } = parseFrontmatter(content);\n const name = basename(path, '.md');\n const rootFromFilename = name === '_root';\n const rootFromFm = frontmatter.root === true;\n const triggerRaw = frontmatter.trigger;\n const trigger: Trigger | undefined =\n typeof triggerRaw === 'string' && VALID_TRIGGERS.includes(triggerRaw as Trigger)\n ? (triggerRaw as Trigger)\n : undefined;\n const codexEmitRaw = frontmatter.codex_emit;\n const codexEmit =\n codexEmitRaw === 'execution'\n ? ('execution' as const)\n : codexEmitRaw === 'advisory'\n ? ('advisory' as const)\n : undefined;\n const instrRaw = frontmatter.codex_instruction;\n const codexInstructionVariant = instrRaw === 'override' ? ('override' as const) : undefined;\n rules.push({\n source: path,\n root: rootFromFilename || rootFromFm,\n targets: toStrArray(frontmatter.targets),\n description: typeof frontmatter.description === 'string' ? frontmatter.description : '',\n globs: toStrArray(frontmatter.globs),\n body,\n ...(trigger !== undefined && { trigger }),\n ...(codexEmit !== undefined && { codexEmit }),\n ...(codexInstructionVariant !== undefined && { codexInstructionVariant }),\n });\n }\n return rules;\n}\n","/**\n * File system helpers for agentsmesh.\n */\n\nimport {\n readFile,\n writeFile,\n access,\n mkdir,\n rename,\n readdir,\n copyFile,\n stat,\n symlink,\n unlink,\n lstat,\n readlink,\n realpath,\n} from 'node:fs/promises';\nimport { dirname, join, resolve } from 'node:path';\nimport { constants } from 'node:fs';\n\nconst UTF8_BOM = '\\uFEFF';\n\ninterface ErrnoLike {\n code?: string;\n message: string;\n}\n\n/**\n * Read file as utf-8 string. Strips BOM. Returns null on ENOENT.\n * @param path - Absolute or relative file path\n * @returns File content or null if not found\n */\nexport async function readFileSafe(path: string): Promise<string | null> {\n try {\n const data = await readFile(path, 'utf-8');\n return data.startsWith(UTF8_BOM) ? data.slice(UTF8_BOM.length) : data;\n } catch (err) {\n const e = err as ErrnoLike;\n if (e.code === 'ENOENT') return null;\n throw new Error(\n `Failed to read ${path}: ${e.message}. Ensure the file exists and is readable.`,\n { cause: err },\n );\n }\n}\n\n/**\n * Write content atomically (write to .tmp, then rename).\n * Creates parent directories.\n * @param path - Target file path\n * @param content - Content to write\n */\nexport async function writeFileAtomic(path: string, content: string): Promise<void> {\n const dir = dirname(path);\n await mkdir(dir, { recursive: true });\n const tmpPath = `${path}.tmp`;\n try {\n await writeFile(tmpPath, content, 'utf-8');\n await rename(tmpPath, path);\n } catch (err) {\n const e = err as ErrnoLike;\n throw new Error(`Failed to write ${path}: ${e.message}. Check permissions and disk space.`, {\n cause: err,\n });\n }\n}\n\n/**\n * Check if path exists.\n * @param path - File or directory path\n * @returns true if exists, false otherwise\n */\nexport async function exists(path: string): Promise<boolean> {\n try {\n await access(path, constants.F_OK);\n return true;\n } catch {\n return false;\n }\n}\n\n/**\n * Create directory recursively. No-op if already exists.\n * @param path - Directory path\n */\nexport async function mkdirp(path: string): Promise<void> {\n await mkdir(path, { recursive: true });\n}\n\n/**\n * List all files recursively under dir. Returns absolute paths only.\n * Skips revisiting the same real directory (breaks symlink cycles).\n * @param dir - Directory to scan\n * @returns Array of absolute file paths\n */\nexport async function readDirRecursive(dir: string, visited?: Set<string>): Promise<string[]> {\n let canonicalDir: string;\n try {\n canonicalDir = await realpath(dir);\n } catch (err) {\n const e = err as ErrnoLike;\n if (e.code === 'ENOENT' || e.code === 'ENOTDIR' || e.code === 'ELOOP') return [];\n throw new Error(`Failed to read directory ${dir}: ${e.message}. Check permissions.`, {\n cause: err,\n });\n }\n const seen = visited ?? new Set<string>();\n if (seen.has(canonicalDir)) return [];\n seen.add(canonicalDir);\n try {\n const entries = await readdir(dir, { withFileTypes: true });\n const files: string[] = [];\n for (const ent of entries) {\n const full = join(dir, ent.name);\n const walkChild =\n ent.isDirectory() ||\n (ent.isSymbolicLink() &&\n (await stat(full).then(\n (s) => s.isDirectory(),\n () => false,\n )));\n if (walkChild) {\n files.push(...(await readDirRecursive(full, seen)));\n } else {\n files.push(full);\n }\n }\n return files;\n } catch (err) {\n const e = err as ErrnoLike;\n if (e.code === 'ENOENT' || e.code === 'ENOTDIR' || e.code === 'EACCES') return [];\n throw new Error(`Failed to read directory ${dir}: ${e.message}. Check permissions.`, {\n cause: err,\n });\n }\n}\n\n/**\n * Copy directory recursively preserving structure.\n * @param src - Source directory\n * @param dest - Destination directory\n */\nexport async function copyDir(src: string, dest: string): Promise<void> {\n await mkdirp(dest);\n const entries = await readdir(src, { withFileTypes: true });\n for (const ent of entries) {\n const srcPath = join(src, ent.name);\n const destPath = join(dest, ent.name);\n const info = await stat(srcPath);\n if (info.isDirectory()) {\n await copyDir(srcPath, destPath);\n } else {\n await mkdirp(dirname(destPath));\n await copyFile(srcPath, destPath);\n }\n }\n}\n\n/**\n * Ensure .agentsmeshcache symlink exists pointing to the agentsmesh cache dir.\n * Creates or updates the symlink so devs can inspect cached remote extends.\n * @param cacheDir - Absolute path to the cache (e.g. ~/.agentsmesh/cache)\n * @param linkPath - Absolute path where the symlink should live\n */\nexport async function ensureCacheSymlink(cacheDir: string, linkPath: string): Promise<void> {\n const targetPath = resolve(cacheDir);\n try {\n const info = await lstat(linkPath);\n if (!info.isSymbolicLink()) return; // leave existing non-symlink alone\n const currentTarget = resolve(dirname(linkPath), await readlink(linkPath));\n if (currentTarget === targetPath) return;\n await unlink(linkPath);\n } catch (err) {\n const e = err as ErrnoLike;\n if (e.code !== 'ENOENT') throw err;\n }\n await symlink(targetPath, linkPath, 'dir');\n}\n","// Frontmatter parsing\n\nimport { parse as yamlParse, stringify as yamlStringify } from 'yaml';\n\n/**\n * Parse YAML frontmatter and body from markdown/MDC content.\n * @param content - Raw content with optional --- delimited frontmatter\n * @returns Parsed frontmatter object and trimmed body\n */\nexport function parseFrontmatter(content: string): {\n frontmatter: Record<string, unknown>;\n body: string;\n} {\n const open = content.indexOf('---');\n if (open !== 0) {\n return { frontmatter: {}, body: content.trim() };\n }\n const close = content.indexOf('---', 3);\n if (close === -1) {\n return { frontmatter: {}, body: content.trim() };\n }\n const yamlStr = content.slice(3, close).trim();\n const body = content.slice(close + 3).trim();\n const frontmatter = yamlStr === '' ? {} : ((yamlParse(yamlStr) as Record<string, unknown>) ?? {});\n return { frontmatter, body };\n}\n\n/**\n * Serialize frontmatter and body back to string.\n * @param frontmatter - Key-value pairs for YAML\n * @param body - Markdown body content\n * @returns Full content with --- delimiters when frontmatter has keys\n */\nexport function serializeFrontmatter(frontmatter: Record<string, unknown>, body: string): string {\n const keys = Object.keys(frontmatter);\n if (keys.length === 0) return body;\n const yamlStr = yamlStringify(frontmatter, { lineWidth: 0 }).trimEnd();\n return `---\\n${yamlStr}\\n---\\n\\n${body}`;\n}\n","/**\n * Parse .agentsmesh/commands/*.md into CanonicalCommand objects.\n */\n\nimport { basename } from 'node:path';\nimport type { CanonicalCommand } from '../../core/types.js';\nimport { readFileSafe, readDirRecursive } from '../../utils/filesystem/fs.js';\nimport { parseFrontmatter } from '../../utils/text/markdown.js';\n\n/**\n * Coerce value to tools array. Handles comma-separated string, string[], or invalid.\n * @param v - Raw value from YAML (e.g. \"Read, Grep\" or [\"Read\", \"Grep\"])\n * @returns Normalized string array\n */\nfunction toBool(v: unknown): boolean {\n return v === true || v === 'true' || v === 1 || v === '1';\n}\n\nfunction toToolsArray(v: unknown): string[] {\n if (Array.isArray(v)) {\n return v\n .filter((x): x is string => typeof x === 'string')\n .map((s) => s.trim())\n .filter(Boolean);\n }\n if (typeof v === 'string') {\n return v\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean);\n }\n return [];\n}\n\n/**\n * Parse all command files in a commands directory.\n * @param commandsDir - Absolute path to .agentsmesh/commands\n * @returns Array of parsed CanonicalCommand, or [] if dir missing/empty\n */\nexport async function parseCommands(commandsDir: string): Promise<CanonicalCommand[]> {\n const files = await readDirRecursive(commandsDir);\n const mdFiles = files.filter((f) => f.endsWith('.md') && !basename(f).startsWith('_'));\n const commands: CanonicalCommand[] = [];\n for (const path of mdFiles) {\n const content = await readFileSafe(path);\n if (!content) continue;\n const { frontmatter, body } = parseFrontmatter(content);\n const name = basename(path, '.md');\n const fromCamel = toToolsArray(frontmatter.allowedTools);\n const fromKebab = toToolsArray(frontmatter['allowed-tools']);\n const allowedTools = fromCamel.length > 0 ? fromCamel : fromKebab;\n commands.push({\n source: path,\n name,\n description: typeof frontmatter.description === 'string' ? frontmatter.description : '',\n allowedTools,\n outputStyle: toBool(frontmatter.outputStyle) || toBool(frontmatter['output-style']),\n body,\n });\n }\n return commands;\n}\n","/**\n * Parse .agentsmesh/agents/*.md into CanonicalAgent objects.\n */\n\nimport { basename } from 'node:path';\nimport type { CanonicalAgent, Hooks } from '../../core/types.js';\nimport { readFileSafe, readDirRecursive } from '../../utils/filesystem/fs.js';\nimport { parseFrontmatter } from '../../utils/text/markdown.js';\n\n/**\n * Coerce value to string array. Handles comma-separated string, YAML array, or invalid.\n * @param v - Raw value from YAML\n * @returns Normalized string array\n */\nfunction toStrArray(v: unknown): string[] {\n if (Array.isArray(v)) {\n return v\n .filter((x): x is string => typeof x === 'string')\n .map((s) => s.trim())\n .filter(Boolean);\n }\n if (typeof v === 'string') {\n return v\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean);\n }\n return [];\n}\n\n/**\n * Coerce value to positive integer.\n * @param v - Raw value from YAML\n * @returns Number or 0 if invalid\n */\nfunction toBool(v: unknown): boolean {\n return v === true || v === 'true' || v === 1 || v === '1';\n}\n\nfunction toInt(v: unknown): number {\n if (typeof v === 'number' && Number.isInteger(v) && v >= 0) return v;\n if (typeof v === 'string') {\n const n = parseInt(v, 10);\n return Number.isInteger(n) && n >= 0 ? n : 0;\n }\n return 0;\n}\n\n/**\n * Extract hooks object from frontmatter. Must be a plain object.\n * @param v - Raw value\n * @returns Record or empty object\n */\nfunction toHooks(v: unknown): Hooks {\n if (v !== null && typeof v === 'object' && !Array.isArray(v)) {\n return v as Hooks;\n }\n return {};\n}\n\n/**\n * Parse all agent files in an agents directory.\n * @param agentsDir - Absolute path to .agentsmesh/agents\n * @returns Array of parsed CanonicalAgent, or [] if dir missing/empty\n */\nexport async function parseAgents(agentsDir: string): Promise<CanonicalAgent[]> {\n const files = await readDirRecursive(agentsDir);\n const mdFiles = files.filter((f) => f.endsWith('.md') && !basename(f).startsWith('_'));\n const agents: CanonicalAgent[] = [];\n for (const path of mdFiles) {\n const content = await readFileSafe(path);\n if (!content) continue;\n const { frontmatter, body } = parseFrontmatter(content);\n const name = basename(path, '.md');\n const toolsCamel = toStrArray(frontmatter.tools);\n const toolsKebab = toStrArray(frontmatter['tools']);\n const tools = toolsCamel.length > 0 ? toolsCamel : toolsKebab;\n const disallowedCamel = toStrArray(frontmatter.disallowedTools);\n const disallowedKebab = toStrArray(frontmatter['disallowed-tools']);\n const disallowedTools = disallowedCamel.length > 0 ? disallowedCamel : disallowedKebab;\n const mcpCamel = toStrArray(frontmatter.mcpServers);\n const mcpKebab = toStrArray(frontmatter['mcp-servers']);\n const mcpServers = mcpCamel.length > 0 ? mcpCamel : mcpKebab;\n const skills = toStrArray(frontmatter.skills);\n const maxTurnsCamel = toInt(frontmatter.maxTurns);\n const maxTurnsKebab = toInt(frontmatter['max-turns']);\n const maxTurns = maxTurnsCamel > 0 ? maxTurnsCamel : maxTurnsKebab > 0 ? maxTurnsKebab : 0;\n agents.push({\n source: path,\n name,\n description: typeof frontmatter.description === 'string' ? frontmatter.description : '',\n tools,\n disallowedTools,\n model: typeof frontmatter.model === 'string' ? frontmatter.model : '',\n permissionMode:\n typeof frontmatter.permissionMode === 'string'\n ? frontmatter.permissionMode\n : typeof frontmatter['permission-mode'] === 'string'\n ? frontmatter['permission-mode']\n : '',\n maxTurns,\n mcpServers,\n hooks: toHooks(frontmatter.hooks),\n skills,\n memory: typeof frontmatter.memory === 'string' ? frontmatter.memory : '',\n outputStyle: toBool(frontmatter.outputStyle) || toBool(frontmatter['output-style']),\n body,\n });\n }\n return agents;\n}\n","/**\n * Parse .agentsmesh/skills/{name}/SKILL.md into CanonicalSkill objects.\n */\n\nimport { basename, join } from 'node:path';\nimport { readdir } from 'node:fs/promises';\nimport type { CanonicalSkill, SkillSupportingFile } from '../../core/types.js';\nimport { readFileSafe, readDirRecursive } from '../../utils/filesystem/fs.js';\nimport { parseFrontmatter } from '../../utils/text/markdown.js';\n\n/** Read file content; returns empty string if unreadable */\nasync function readContent(path: string): Promise<string> {\n const c = await readFileSafe(path);\n return c ?? '';\n}\n\nconst SKILL_FILE = 'SKILL.md';\n\n/** Directories that are never valid skill supporting content. */\nconst EXCLUDED_DIR_PREFIXES = ['.git', 'node_modules'];\n\n/** Sanitize a frontmatter name into a valid directory/skill name. */\nfunction sanitizeSkillName(raw: string): string {\n return raw\n .toLowerCase()\n .replace(/[^a-z0-9-]+/g, '-')\n .replace(/-+/g, '-')\n .replace(/^-|-$/g, '');\n}\n\n/**\n * List supporting files in a skill directory (all files except SKILL.md).\n * @param skillDir - Absolute path to skill directory\n * @returns Supporting files with relative and absolute paths\n */\nasync function listSupportingFiles(skillDir: string): Promise<SkillSupportingFile[]> {\n const files = await readDirRecursive(skillDir);\n const result: SkillSupportingFile[] = [];\n for (const absPath of files) {\n const raw = absPath.slice(skillDir.length + 1);\n const name = raw.replace(/\\\\/g, '/');\n if (name === SKILL_FILE || name.endsWith(`/${SKILL_FILE}`)) continue;\n const firstSegment = name.split('/')[0]!;\n if (EXCLUDED_DIR_PREFIXES.some((p) => firstSegment === p)) continue;\n if (name === '.DS_Store' || name.endsWith('/.DS_Store')) continue;\n const content = await readContent(absPath);\n result.push({ relativePath: name, absolutePath: absPath, content });\n }\n return result.sort((a, b) => a.relativePath.localeCompare(b.relativePath));\n}\n\n/**\n * Parse all skill directories under skillsDir.\n * Each skill lives in skillsDir/{name}/SKILL.md.\n * @param skillsDir - Absolute path to .agentsmesh/skills\n * @returns Array of parsed CanonicalSkill, or [] if dir missing/empty\n */\n/**\n * Parse a single skill directory containing SKILL.md (Anthropic-style leaf folder).\n */\nexport async function parseSkillDirectory(skillDir: string): Promise<CanonicalSkill | null> {\n const skillPath = join(skillDir, SKILL_FILE);\n const content = await readFileSafe(skillPath);\n if (!content) return null;\n const { frontmatter, body } = parseFrontmatter(content);\n const supportingFiles = await listSupportingFiles(skillDir);\n const fmName = typeof frontmatter.name === 'string' ? sanitizeSkillName(frontmatter.name) : '';\n return {\n source: skillPath,\n name: fmName || basename(skillDir),\n description: typeof frontmatter.description === 'string' ? frontmatter.description : '',\n body,\n supportingFiles,\n };\n}\n\nexport async function parseSkills(skillsDir: string): Promise<CanonicalSkill[]> {\n let entries: { name: string; isDirectory: () => boolean }[];\n try {\n entries = await readdir(skillsDir, { withFileTypes: true });\n } catch {\n return [];\n }\n const skills: CanonicalSkill[] = [];\n for (const ent of entries) {\n if (!ent.isDirectory()) continue;\n if (ent.name.startsWith('_')) continue;\n const skillDir = join(skillsDir, ent.name);\n const skillPath = join(skillDir, SKILL_FILE);\n const content = await readFileSafe(skillPath);\n if (!content) continue;\n const { frontmatter, body } = parseFrontmatter(content);\n const supportingFiles = await listSupportingFiles(skillDir);\n skills.push({\n source: skillPath,\n name: ent.name,\n description: typeof frontmatter.description === 'string' ? frontmatter.description : '',\n body,\n supportingFiles,\n });\n }\n return skills.sort((a, b) => a.name.localeCompare(b.name));\n}\n","/**\n * Parse .agentsmesh/mcp.json into McpConfig.\n */\n\nimport { readFileSafe } from '../../utils/filesystem/fs.js';\nimport type { McpConfig, McpServer } from '../../core/types.js';\n\nfunction parseStringMap(raw: unknown): Record<string, string> {\n if (raw === null || typeof raw !== 'object' || Array.isArray(raw)) return {};\n return Object.fromEntries(\n Object.entries(raw).filter((entry): entry is [string, string] => typeof entry[1] === 'string'),\n );\n}\n\nfunction parseServer(raw: unknown): McpServer | null {\n if (!raw || typeof raw !== 'object') return null;\n const obj = raw as Record<string, unknown>;\n const type = typeof obj.type === 'string' ? obj.type : 'stdio';\n const env = parseStringMap(obj.env);\n const description = typeof obj.description === 'string' ? obj.description : undefined;\n\n const url = typeof obj.url === 'string' ? obj.url : '';\n if (url) {\n return {\n ...(description !== undefined && { description }),\n type,\n url,\n headers: parseStringMap(obj.headers),\n env,\n };\n }\n\n const command = typeof obj.command === 'string' ? obj.command : '';\n if (!command) return null;\n\n const args = Array.isArray(obj.args)\n ? obj.args.filter((x): x is string => typeof x === 'string')\n : [];\n return {\n ...(description !== undefined && { description }),\n type,\n command,\n args,\n env,\n };\n}\n\n/**\n * Parse mcp.json at the given path.\n * @param mcpPath - Absolute path to .agentsmesh/mcp.json\n * @returns McpConfig or null if file missing, malformed, or lacks mcpServers\n */\nexport async function parseMcp(mcpPath: string): Promise<McpConfig | null> {\n const content = await readFileSafe(mcpPath);\n if (!content) return null;\n let parsed: unknown;\n try {\n parsed = JSON.parse(content) as unknown;\n } catch {\n return null;\n }\n if (!parsed || typeof parsed !== 'object') return null;\n const mcpServersRaw = (parsed as Record<string, unknown>).mcpServers;\n if (mcpServersRaw === undefined) return null;\n if (typeof mcpServersRaw !== 'object' || mcpServersRaw === null) return null;\n const mcpServers: Record<string, McpServer> = {};\n for (const [name, val] of Object.entries(mcpServersRaw)) {\n const server = parseServer(val);\n if (server) mcpServers[name] = server;\n }\n return { mcpServers };\n}\n","/**\n * Parse .agentsmesh/permissions.yaml into Permissions.\n */\n\nimport { parse as parseYaml } from 'yaml';\nimport { readFileSafe } from '../../utils/filesystem/fs.js';\nimport type { Permissions } from '../../core/types.js';\n\nfunction ensureStringArray(val: unknown): string[] {\n if (!Array.isArray(val)) return [];\n return val.filter((x): x is string => typeof x === 'string');\n}\n\n/**\n * Parse permissions.yaml at the given path.\n * @param permissionsPath - Absolute path to .agentsmesh/permissions.yaml\n * @returns Permissions or null if file missing or malformed\n */\nexport async function parsePermissions(permissionsPath: string): Promise<Permissions | null> {\n const content = await readFileSafe(permissionsPath);\n if (content === null) return null;\n if (!content.trim()) return { allow: [], deny: [], ask: [] };\n let parsed: unknown;\n try {\n parsed = parseYaml(content) as unknown;\n } catch {\n return null;\n }\n if (!parsed || typeof parsed !== 'object') return null;\n const obj = parsed as Record<string, unknown>;\n const allow = ensureStringArray(obj.allow);\n const deny = ensureStringArray(obj.deny);\n const ask = ensureStringArray(obj.ask);\n return { allow, deny, ask };\n}\n","/**\n * Parse .agentsmesh/hooks.yaml into Hooks.\n */\n\nimport { parse as parseYaml } from 'yaml';\nimport { readFileSafe } from '../../utils/filesystem/fs.js';\nimport type { HookEntry, Hooks } from '../../core/types.js';\nimport { getHookText, getHookPrompt } from '../../core/hook-command.js';\n\nconst VALID_TYPES = ['command', 'prompt'] as const;\n\nfunction toHookEntry(raw: unknown): HookEntry | null {\n if (!raw || typeof raw !== 'object') return null;\n const obj = raw as Record<string, unknown>;\n const matcher = obj.matcher;\n if (typeof matcher !== 'string') return null;\n const command = getHookText(obj);\n if (!command) return null;\n const type =\n typeof obj.type === 'string' && VALID_TYPES.includes(obj.type as (typeof VALID_TYPES)[number])\n ? (obj.type as 'command' | 'prompt')\n : undefined;\n const timeout =\n typeof obj.timeout === 'number' && Number.isFinite(obj.timeout) ? obj.timeout : undefined;\n const prompt = getHookPrompt(obj) || undefined;\n return {\n matcher,\n command,\n ...(timeout !== undefined && { timeout }),\n ...(type && { type }),\n ...(prompt && { prompt }),\n };\n}\n\n/**\n * Parse hooks.yaml at the given path.\n * @param hooksPath - Absolute path to .agentsmesh/hooks.yaml\n * @returns Hooks or null if file missing or malformed\n */\nexport async function parseHooks(hooksPath: string): Promise<Hooks | null> {\n const content = await readFileSafe(hooksPath);\n if (content === null) return null;\n if (!content.trim()) return {};\n let parsed: unknown;\n try {\n parsed = parseYaml(content) as unknown;\n } catch {\n return null;\n }\n if (!parsed || typeof parsed !== 'object') return null;\n const result: Hooks = {};\n const obj = parsed as Record<string, unknown>;\n for (const [key, val] of Object.entries(obj)) {\n if (!Array.isArray(val)) continue;\n const entries: HookEntry[] = [];\n for (const item of val) {\n const entry = toHookEntry(item);\n if (entry) entries.push(entry);\n }\n if (entries.length > 0) result[key] = entries;\n }\n return result;\n}\n","type HookLike = {\n command?: unknown;\n prompt?: unknown;\n type?: unknown;\n};\n\nfunction trimString(value: unknown): string {\n return typeof value === 'string' ? value.trim() : '';\n}\n\nexport function getHookCommand(entry: HookLike): string {\n return trimString(entry.command);\n}\n\nexport function getHookPrompt(entry: HookLike): string {\n return trimString(entry.prompt);\n}\n\nexport function getHookText(entry: HookLike): string {\n const command = getHookCommand(entry);\n const prompt = getHookPrompt(entry);\n return entry.type === 'prompt' ? prompt || command : command || prompt;\n}\n\nexport function hasHookCommand(entry: HookLike): boolean {\n return getHookCommand(entry).length > 0;\n}\n\nexport function hasHookText(entry: HookLike): boolean {\n return getHookText(entry).length > 0;\n}\n","/**\n * Parse .agentsmesh/ignore into gitignore-style patterns.\n */\n\nimport { readFileSafe } from '../../utils/filesystem/fs.js';\nimport type { IgnorePatterns } from '../../core/types.js';\n\n/**\n * Parse ignore file at the given path.\n * @param ignorePath - Absolute path to .agentsmesh/ignore\n * @returns Array of ignore patterns (empty array if file missing or empty)\n */\nexport async function parseIgnore(ignorePath: string): Promise<IgnorePatterns> {\n const content = await readFileSafe(ignorePath);\n if (content === null || !content.trim()) return [];\n\n const lines = content.split(/\\r?\\n/);\n const patterns: string[] = [];\n\n for (const line of lines) {\n const trimmed = line.trim();\n if (trimmed === '' || trimmed.startsWith('#')) continue;\n patterns.push(trimmed);\n }\n\n return patterns;\n}\n","/**\n * Public API — canonical loading (package.json \"exports\".\"./canonical\").\n */\n\nimport type { CanonicalFiles } from '../core/types.js';\nimport { loadCanonicalFiles } from '../canonical/load/loader.js';\n\nexport { loadCanonicalFiles };\n\n/** Load `.agentsmesh/` from a project root (or an explicit canonical directory). */\nexport async function loadCanonical(projectRoot: string): Promise<CanonicalFiles> {\n return loadCanonicalFiles(projectRoot);\n}\n"],"mappings":"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","names":["join","basename","basename","basename","toStrArray","toBool","basename","basename","join","readdir","readdir","join","parseYaml","parseYaml","join"]}
|
|
1
|
+
{"version":3,"sources":["../src/core/errors.ts","../src/utils/filesystem/fs.ts","../src/utils/text/markdown.ts","../src/canonical/features/rules.ts","../src/canonical/features/commands.ts","../src/canonical/features/agents.ts","../src/canonical/features/skills.ts","../src/canonical/features/mcp.ts","../src/canonical/features/permissions.ts","../src/core/hook-command.ts","../src/canonical/features/hooks.ts","../src/canonical/features/ignore.ts","../src/canonical/load/loader.ts","../src/public/canonical.ts"],"names":["yamlParse","basename","toStrArray","toBool","readdir","join","parseYaml"],"mappings":"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","file":"canonical.js","sourcesContent":["/**\n * Typed error taxonomy for agentsmesh programmatic consumers.\n *\n * All public-API errors inherit from AgentsMeshError and carry a stable `code`\n * property. Consumers can branch on `err instanceof AgentsMeshError && err.code === 'AM_...'`\n * without relying on error message strings.\n */\n\nexport type AgentsMeshErrorCode =\n | 'AM_CONFIG_NOT_FOUND'\n | 'AM_CONFIG_INVALID'\n | 'AM_TARGET_NOT_FOUND'\n | 'AM_TARGET_UNSUPPORTED'\n | 'AM_IMPORT_FAILED'\n | 'AM_GENERATION_FAILED'\n | 'AM_REMOTE_FETCH_FAILED'\n | 'AM_LOCK_ACQUISITION_FAILED'\n | 'AM_LOCK_CONFLICT'\n | 'AM_FILESYSTEM';\n\nexport class AgentsMeshError extends Error {\n readonly code: AgentsMeshErrorCode;\n\n constructor(code: AgentsMeshErrorCode, message: string, options?: { cause?: unknown }) {\n super(message, options);\n this.name = 'AgentsMeshError';\n this.code = code;\n }\n}\n\nexport class ConfigNotFoundError extends AgentsMeshError {\n readonly path: string;\n\n constructor(path: string, options?: { cause?: unknown; message?: string }) {\n super(\n 'AM_CONFIG_NOT_FOUND',\n options?.message ??\n `agentsmesh.yaml not found at ${path}. Run 'agentsmesh init' to create one.`,\n options,\n );\n this.name = 'ConfigNotFoundError';\n this.path = path;\n }\n}\n\nexport class ConfigValidationError extends AgentsMeshError {\n readonly issues: readonly string[];\n\n constructor(path: string, issues: readonly string[], options?: { cause?: unknown }) {\n super(\n 'AM_CONFIG_INVALID',\n `Invalid config at ${path}: ${issues.join('; ')}. Fix the YAML and try again.`,\n options,\n );\n this.name = 'ConfigValidationError';\n this.issues = issues;\n }\n}\n\nexport class TargetNotFoundError extends AgentsMeshError {\n readonly target: string;\n\n constructor(target: string, options?: { cause?: unknown; supported?: readonly string[] }) {\n const suffix = options?.supported ? ` Supported: ${options.supported.join(', ')}.` : '';\n super('AM_TARGET_NOT_FOUND', `Unknown target \"${target}\".${suffix}`, options);\n this.name = 'TargetNotFoundError';\n this.target = target;\n }\n}\n\nexport class ImportError extends AgentsMeshError {\n readonly target: string;\n\n constructor(target: string, message: string, options?: { cause?: unknown }) {\n super('AM_IMPORT_FAILED', `Import from ${target} failed: ${message}`, options);\n this.name = 'ImportError';\n this.target = target;\n }\n}\n\nexport class GenerationError extends AgentsMeshError {\n constructor(message: string, options?: { cause?: unknown }) {\n super('AM_GENERATION_FAILED', message, options);\n this.name = 'GenerationError';\n }\n}\n\nexport class RemoteFetchError extends AgentsMeshError {\n readonly source: string;\n\n constructor(source: string, message: string, options?: { cause?: unknown }) {\n super('AM_REMOTE_FETCH_FAILED', `Remote fetch for \"${source}\" failed: ${message}`, options);\n this.name = 'RemoteFetchError';\n this.source = source;\n }\n}\n\nexport class LockAcquisitionError extends AgentsMeshError {\n readonly lockPath: string;\n readonly holder: string;\n\n constructor(lockPath: string, holder: string, options?: { cause?: unknown }) {\n super(\n 'AM_LOCK_ACQUISITION_FAILED',\n `Could not acquire generate lock at ${lockPath}: currently held by ${holder}. ` +\n `Wait for the other process to finish, or remove ${lockPath} manually if you are sure no agentsmesh process is running.`,\n options,\n );\n this.name = 'LockAcquisitionError';\n this.lockPath = lockPath;\n this.holder = holder;\n }\n}\n\nexport class FileSystemError extends AgentsMeshError {\n readonly path: string;\n readonly errnoCode?: string;\n\n constructor(path: string, message: string, options?: { cause?: unknown; errnoCode?: string }) {\n super('AM_FILESYSTEM', message, options);\n this.name = 'FileSystemError';\n this.path = path;\n this.errnoCode = options?.errnoCode;\n }\n}\n","/**\n * File system helpers for agentsmesh.\n */\n\nimport {\n readFile,\n writeFile,\n access,\n mkdir,\n rename,\n readdir,\n copyFile,\n rm,\n stat,\n symlink,\n unlink,\n lstat,\n readlink,\n realpath,\n} from 'node:fs/promises';\nimport { dirname, join, resolve } from 'node:path';\nimport { constants } from 'node:fs';\nimport { FileSystemError } from '../../core/errors.js';\n\nconst UTF8_BOM = '\\uFEFF';\n\ninterface ErrnoLike {\n code?: string;\n message: string;\n}\n\n/**\n * Read file as utf-8 string. Strips BOM. Returns null on ENOENT.\n * @param path - Absolute or relative file path\n * @returns File content or null if not found\n */\nexport async function readFileSafe(path: string): Promise<string | null> {\n try {\n const data = await readFile(path, 'utf-8');\n return data.startsWith(UTF8_BOM) ? data.slice(UTF8_BOM.length) : data;\n } catch (err) {\n const e = err as ErrnoLike;\n if (e.code === 'ENOENT') return null;\n throw new FileSystemError(\n path,\n `Failed to read ${path}: ${e.message}. Ensure the file exists and is readable.`,\n { cause: err, errnoCode: e.code },\n );\n }\n}\n\n/**\n * Write content atomically (write to .tmp, then rename).\n * Creates parent directories.\n * @param path - Target file path\n * @param content - Content to write\n */\nexport async function writeFileAtomic(path: string, content: string): Promise<void> {\n const dir = dirname(path);\n await mkdir(dir, { recursive: true });\n try {\n const info = await lstat(path);\n if (info.isDirectory()) {\n throw new FileSystemError(\n path,\n `Failed to write ${path}: target exists and is a directory. Remove it or choose a different path.`,\n { errnoCode: 'EISDIR' },\n );\n }\n } catch (err) {\n if (err instanceof FileSystemError) throw err;\n const e = err as ErrnoLike;\n if (e.code !== 'ENOENT') throw err;\n }\n const tmpPath = `${path}.tmp`;\n try {\n await writeFile(tmpPath, content, 'utf-8');\n await rename(tmpPath, path);\n } catch (err) {\n await rm(tmpPath, { force: true }).catch(() => {});\n const e = err as ErrnoLike;\n throw new FileSystemError(\n path,\n `Failed to write ${path}: ${e.message}. Check permissions and disk space.`,\n { cause: err, errnoCode: e.code },\n );\n }\n}\n\n/**\n * Check if path exists.\n * @param path - File or directory path\n * @returns true if exists, false otherwise\n */\nexport async function exists(path: string): Promise<boolean> {\n try {\n await access(path, constants.F_OK);\n return true;\n } catch {\n return false;\n }\n}\n\n/**\n * Create directory recursively. No-op if already exists.\n * @param path - Directory path\n */\nexport async function mkdirp(path: string): Promise<void> {\n await mkdir(path, { recursive: true });\n}\n\n/**\n * List all files recursively under dir. Returns absolute paths only.\n * Skips revisiting the same real directory (breaks symlink cycles).\n * @param dir - Directory to scan\n * @returns Array of absolute file paths\n */\nexport async function readDirRecursive(dir: string, visited?: Set<string>): Promise<string[]> {\n let canonicalDir: string;\n try {\n canonicalDir = await realpath(dir);\n } catch (err) {\n const e = err as ErrnoLike;\n if (e.code === 'ENOENT' || e.code === 'ENOTDIR' || e.code === 'ELOOP') return [];\n throw new FileSystemError(\n dir,\n `Failed to read directory ${dir}: ${e.message}. Check permissions.`,\n { cause: err, errnoCode: e.code },\n );\n }\n const seen = visited ?? new Set<string>();\n if (seen.has(canonicalDir)) return [];\n seen.add(canonicalDir);\n try {\n const entries = await readdir(dir, { withFileTypes: true });\n const files: string[] = [];\n for (const ent of entries) {\n const full = join(dir, ent.name);\n const walkChild =\n ent.isDirectory() ||\n (ent.isSymbolicLink() &&\n (await stat(full).then(\n (s) => s.isDirectory(),\n () => false,\n )));\n if (walkChild) {\n files.push(...(await readDirRecursive(full, seen)));\n } else {\n files.push(full);\n }\n }\n return files;\n } catch (err) {\n const e = err as ErrnoLike;\n if (e.code === 'ENOENT' || e.code === 'ENOTDIR' || e.code === 'EACCES') return [];\n throw new FileSystemError(\n dir,\n `Failed to read directory ${dir}: ${e.message}. Check permissions.`,\n { cause: err, errnoCode: e.code },\n );\n }\n}\n\n/**\n * Copy directory recursively preserving structure.\n * @param src - Source directory\n * @param dest - Destination directory\n */\nexport async function copyDir(src: string, dest: string): Promise<void> {\n await mkdirp(dest);\n const entries = await readdir(src, { withFileTypes: true });\n for (const ent of entries) {\n const srcPath = join(src, ent.name);\n const destPath = join(dest, ent.name);\n const info = await stat(srcPath);\n if (info.isDirectory()) {\n await copyDir(srcPath, destPath);\n } else {\n await mkdirp(dirname(destPath));\n await copyFile(srcPath, destPath);\n }\n }\n}\n\n/**\n * Ensure .agentsmeshcache symlink exists pointing to the agentsmesh cache dir.\n * Creates or updates the symlink so devs can inspect cached remote extends.\n * @param cacheDir - Absolute path to the cache (e.g. ~/.agentsmesh/cache)\n * @param linkPath - Absolute path where the symlink should live\n */\nexport async function ensureCacheSymlink(cacheDir: string, linkPath: string): Promise<void> {\n const targetPath = resolve(cacheDir);\n try {\n const info = await lstat(linkPath);\n if (!info.isSymbolicLink()) return; // leave existing non-symlink alone\n const currentTarget = resolve(dirname(linkPath), await readlink(linkPath));\n if (currentTarget === targetPath) return;\n await unlink(linkPath);\n } catch (err) {\n const e = err as ErrnoLike;\n if (e.code !== 'ENOENT') throw err;\n }\n await symlink(targetPath, linkPath, 'dir');\n}\n","// Frontmatter parsing\n\nimport { parse as yamlParse, stringify as yamlStringify } from 'yaml';\n\n/**\n * Parse YAML frontmatter and body from markdown/MDC content.\n * @param content - Raw content with optional --- delimited frontmatter\n * @returns Parsed frontmatter object and trimmed body\n */\nexport function parseFrontmatter(content: string): {\n frontmatter: Record<string, unknown>;\n body: string;\n} {\n const open = content.indexOf('---');\n if (open !== 0) {\n return { frontmatter: {}, body: content.trim() };\n }\n const close = content.indexOf('---', 3);\n if (close === -1) {\n return { frontmatter: {}, body: content.trim() };\n }\n const yamlStr = content.slice(3, close).trim();\n const body = content.slice(close + 3).trim();\n const frontmatter = yamlStr === '' ? {} : ((yamlParse(yamlStr) as Record<string, unknown>) ?? {});\n return { frontmatter, body };\n}\n\n/**\n * Serialize frontmatter and body back to string.\n * @param frontmatter - Key-value pairs for YAML\n * @param body - Markdown body content\n * @returns Full content with --- delimiters when frontmatter has keys\n */\nexport function serializeFrontmatter(frontmatter: Record<string, unknown>, body: string): string {\n const keys = Object.keys(frontmatter);\n if (keys.length === 0) return body;\n const yamlStr = yamlStringify(frontmatter, { lineWidth: 0 }).trimEnd();\n return `---\\n${yamlStr}\\n---\\n\\n${body}`;\n}\n","/**\n * Parse .agentsmesh/rules/*.md into CanonicalRule objects.\n */\n\nimport { basename } from 'node:path';\nimport type { CanonicalRule } from '../../core/types.js';\nimport { readFileSafe, readDirRecursive } from '../../utils/filesystem/fs.js';\nimport { parseFrontmatter } from '../../utils/text/markdown.js';\n\nconst VALID_TRIGGERS = ['always_on', 'model_decision', 'glob', 'manual'] as const;\ntype Trigger = (typeof VALID_TRIGGERS)[number];\n\n/**\n * Coerce value to string array. Handles string, string[], or invalid.\n * @param v - Raw value from YAML\n * @returns Normalized string array\n */\nfunction toStrArray(v: unknown): string[] {\n if (Array.isArray(v)) return v.filter((x): x is string => typeof x === 'string');\n if (typeof v === 'string') return v ? [v] : [];\n return [];\n}\n\n/**\n * Parse all rule files in a rules directory.\n * @param rulesDir - Absolute path to .agentsmesh/rules\n * @returns Array of parsed CanonicalRule, or [] if dir missing/empty\n */\nexport async function parseRules(rulesDir: string): Promise<CanonicalRule[]> {\n const files = await readDirRecursive(rulesDir);\n const mdFiles = files.filter((f) => {\n if (!f.endsWith('.md')) return false;\n const name = basename(f, '.md');\n return name === '_root' || !name.startsWith('_');\n });\n const rules: CanonicalRule[] = [];\n for (const path of mdFiles) {\n const content = await readFileSafe(path);\n if (!content) continue;\n const { frontmatter, body } = parseFrontmatter(content);\n const name = basename(path, '.md');\n const rootFromFilename = name === '_root';\n const rootFromFm = frontmatter.root === true;\n const triggerRaw = frontmatter.trigger;\n const trigger: Trigger | undefined =\n typeof triggerRaw === 'string' && VALID_TRIGGERS.includes(triggerRaw as Trigger)\n ? (triggerRaw as Trigger)\n : undefined;\n const codexEmitRaw = frontmatter.codex_emit;\n const codexEmit =\n codexEmitRaw === 'execution'\n ? ('execution' as const)\n : codexEmitRaw === 'advisory'\n ? ('advisory' as const)\n : undefined;\n const instrRaw = frontmatter.codex_instruction;\n const codexInstructionVariant = instrRaw === 'override' ? ('override' as const) : undefined;\n rules.push({\n source: path,\n root: rootFromFilename || rootFromFm,\n targets: toStrArray(frontmatter.targets),\n description: typeof frontmatter.description === 'string' ? frontmatter.description : '',\n globs: toStrArray(frontmatter.globs),\n body,\n ...(trigger !== undefined && { trigger }),\n ...(codexEmit !== undefined && { codexEmit }),\n ...(codexInstructionVariant !== undefined && { codexInstructionVariant }),\n });\n }\n return rules;\n}\n","/**\n * Parse .agentsmesh/commands/*.md into CanonicalCommand objects.\n */\n\nimport { basename } from 'node:path';\nimport type { CanonicalCommand } from '../../core/types.js';\nimport { readFileSafe, readDirRecursive } from '../../utils/filesystem/fs.js';\nimport { parseFrontmatter } from '../../utils/text/markdown.js';\n\n/**\n * Coerce value to tools array. Handles comma-separated string, string[], or invalid.\n * @param v - Raw value from YAML (e.g. \"Read, Grep\" or [\"Read\", \"Grep\"])\n * @returns Normalized string array\n */\nfunction toBool(v: unknown): boolean {\n return v === true || v === 'true' || v === 1 || v === '1';\n}\n\nfunction toToolsArray(v: unknown): string[] {\n if (Array.isArray(v)) {\n return v\n .filter((x): x is string => typeof x === 'string')\n .map((s) => s.trim())\n .filter(Boolean);\n }\n if (typeof v === 'string') {\n return v\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean);\n }\n return [];\n}\n\n/**\n * Parse all command files in a commands directory.\n * @param commandsDir - Absolute path to .agentsmesh/commands\n * @returns Array of parsed CanonicalCommand, or [] if dir missing/empty\n */\nexport async function parseCommands(commandsDir: string): Promise<CanonicalCommand[]> {\n const files = await readDirRecursive(commandsDir);\n const mdFiles = files.filter((f) => f.endsWith('.md') && !basename(f).startsWith('_'));\n const commands: CanonicalCommand[] = [];\n for (const path of mdFiles) {\n const content = await readFileSafe(path);\n if (!content) continue;\n const { frontmatter, body } = parseFrontmatter(content);\n const name = basename(path, '.md');\n const fromCamel = toToolsArray(frontmatter.allowedTools);\n const fromKebab = toToolsArray(frontmatter['allowed-tools']);\n const allowedTools = fromCamel.length > 0 ? fromCamel : fromKebab;\n commands.push({\n source: path,\n name,\n description: typeof frontmatter.description === 'string' ? frontmatter.description : '',\n allowedTools,\n outputStyle: toBool(frontmatter.outputStyle) || toBool(frontmatter['output-style']),\n body,\n });\n }\n return commands;\n}\n","/**\n * Parse .agentsmesh/agents/*.md into CanonicalAgent objects.\n */\n\nimport { basename } from 'node:path';\nimport type { CanonicalAgent, Hooks } from '../../core/types.js';\nimport { readFileSafe, readDirRecursive } from '../../utils/filesystem/fs.js';\nimport { parseFrontmatter } from '../../utils/text/markdown.js';\n\n/**\n * Coerce value to string array. Handles comma-separated string, YAML array, or invalid.\n * @param v - Raw value from YAML\n * @returns Normalized string array\n */\nfunction toStrArray(v: unknown): string[] {\n if (Array.isArray(v)) {\n return v\n .filter((x): x is string => typeof x === 'string')\n .map((s) => s.trim())\n .filter(Boolean);\n }\n if (typeof v === 'string') {\n return v\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean);\n }\n return [];\n}\n\n/**\n * Coerce value to positive integer.\n * @param v - Raw value from YAML\n * @returns Number or 0 if invalid\n */\nfunction toBool(v: unknown): boolean {\n return v === true || v === 'true' || v === 1 || v === '1';\n}\n\nfunction toInt(v: unknown): number {\n if (typeof v === 'number' && Number.isInteger(v) && v >= 0) return v;\n if (typeof v === 'string') {\n const n = parseInt(v, 10);\n return Number.isInteger(n) && n >= 0 ? n : 0;\n }\n return 0;\n}\n\n/**\n * Extract hooks object from frontmatter. Must be a plain object.\n * @param v - Raw value\n * @returns Record or empty object\n */\nfunction toHooks(v: unknown): Hooks {\n if (v !== null && typeof v === 'object' && !Array.isArray(v)) {\n return v as Hooks;\n }\n return {};\n}\n\n/**\n * Parse all agent files in an agents directory.\n * @param agentsDir - Absolute path to .agentsmesh/agents\n * @returns Array of parsed CanonicalAgent, or [] if dir missing/empty\n */\nexport async function parseAgents(agentsDir: string): Promise<CanonicalAgent[]> {\n const files = await readDirRecursive(agentsDir);\n const mdFiles = files.filter((f) => f.endsWith('.md') && !basename(f).startsWith('_'));\n const agents: CanonicalAgent[] = [];\n for (const path of mdFiles) {\n const content = await readFileSafe(path);\n if (!content) continue;\n const { frontmatter, body } = parseFrontmatter(content);\n const name = basename(path, '.md');\n const toolsCamel = toStrArray(frontmatter.tools);\n const toolsKebab = toStrArray(frontmatter['tools']);\n const tools = toolsCamel.length > 0 ? toolsCamel : toolsKebab;\n const disallowedCamel = toStrArray(frontmatter.disallowedTools);\n const disallowedKebab = toStrArray(frontmatter['disallowed-tools']);\n const disallowedTools = disallowedCamel.length > 0 ? disallowedCamel : disallowedKebab;\n const mcpCamel = toStrArray(frontmatter.mcpServers);\n const mcpKebab = toStrArray(frontmatter['mcp-servers']);\n const mcpServers = mcpCamel.length > 0 ? mcpCamel : mcpKebab;\n const skills = toStrArray(frontmatter.skills);\n const maxTurnsCamel = toInt(frontmatter.maxTurns);\n const maxTurnsKebab = toInt(frontmatter['max-turns']);\n const maxTurns = maxTurnsCamel > 0 ? maxTurnsCamel : maxTurnsKebab > 0 ? maxTurnsKebab : 0;\n agents.push({\n source: path,\n name,\n description: typeof frontmatter.description === 'string' ? frontmatter.description : '',\n tools,\n disallowedTools,\n model: typeof frontmatter.model === 'string' ? frontmatter.model : '',\n permissionMode:\n typeof frontmatter.permissionMode === 'string'\n ? frontmatter.permissionMode\n : typeof frontmatter['permission-mode'] === 'string'\n ? frontmatter['permission-mode']\n : '',\n maxTurns,\n mcpServers,\n hooks: toHooks(frontmatter.hooks),\n skills,\n memory: typeof frontmatter.memory === 'string' ? frontmatter.memory : '',\n outputStyle: toBool(frontmatter.outputStyle) || toBool(frontmatter['output-style']),\n body,\n });\n }\n return agents;\n}\n","/**\n * Parse .agentsmesh/skills/{name}/SKILL.md into CanonicalSkill objects.\n */\n\nimport { basename, join } from 'node:path';\nimport { readdir } from 'node:fs/promises';\nimport type { CanonicalSkill, SkillSupportingFile } from '../../core/types.js';\nimport { readFileSafe, readDirRecursive } from '../../utils/filesystem/fs.js';\nimport { parseFrontmatter } from '../../utils/text/markdown.js';\n\n/** Read file content; returns empty string if unreadable */\nasync function readContent(path: string): Promise<string> {\n const c = await readFileSafe(path);\n return c ?? '';\n}\n\nconst SKILL_FILE = 'SKILL.md';\n\n/** Directories that are never valid skill supporting content. */\nconst EXCLUDED_DIR_PREFIXES = ['.git', 'node_modules'];\n\n/** Sanitize a frontmatter name into a valid directory/skill name. */\nfunction sanitizeSkillName(raw: string): string {\n return raw\n .toLowerCase()\n .replace(/[^a-z0-9-]+/g, '-')\n .replace(/-+/g, '-')\n .replace(/^-|-$/g, '');\n}\n\n/**\n * List supporting files in a skill directory (all files except SKILL.md).\n * @param skillDir - Absolute path to skill directory\n * @returns Supporting files with relative and absolute paths\n */\nasync function listSupportingFiles(skillDir: string): Promise<SkillSupportingFile[]> {\n const files = await readDirRecursive(skillDir);\n const result: SkillSupportingFile[] = [];\n for (const absPath of files) {\n const raw = absPath.slice(skillDir.length + 1);\n const name = raw.replace(/\\\\/g, '/');\n if (name === SKILL_FILE || name.endsWith(`/${SKILL_FILE}`)) continue;\n const firstSegment = name.split('/')[0]!;\n if (EXCLUDED_DIR_PREFIXES.some((p) => firstSegment === p)) continue;\n if (name === '.DS_Store' || name.endsWith('/.DS_Store')) continue;\n const content = await readContent(absPath);\n result.push({ relativePath: name, absolutePath: absPath, content });\n }\n return result.sort((a, b) => a.relativePath.localeCompare(b.relativePath));\n}\n\n/**\n * Parse all skill directories under skillsDir.\n * Each skill lives in skillsDir/{name}/SKILL.md.\n * @param skillsDir - Absolute path to .agentsmesh/skills\n * @returns Array of parsed CanonicalSkill, or [] if dir missing/empty\n */\n/**\n * Parse a single skill directory containing SKILL.md (Anthropic-style leaf folder).\n */\nexport async function parseSkillDirectory(skillDir: string): Promise<CanonicalSkill | null> {\n const skillPath = join(skillDir, SKILL_FILE);\n const content = await readFileSafe(skillPath);\n if (!content) return null;\n const { frontmatter, body } = parseFrontmatter(content);\n const supportingFiles = await listSupportingFiles(skillDir);\n const fmName = typeof frontmatter.name === 'string' ? sanitizeSkillName(frontmatter.name) : '';\n return {\n source: skillPath,\n name: fmName || basename(skillDir),\n description: typeof frontmatter.description === 'string' ? frontmatter.description : '',\n body,\n supportingFiles,\n };\n}\n\nexport async function parseSkills(skillsDir: string): Promise<CanonicalSkill[]> {\n let entries: { name: string; isDirectory: () => boolean }[];\n try {\n entries = await readdir(skillsDir, { withFileTypes: true });\n } catch {\n return [];\n }\n const skills: CanonicalSkill[] = [];\n for (const ent of entries) {\n if (!ent.isDirectory()) continue;\n if (ent.name.startsWith('_')) continue;\n const skillDir = join(skillsDir, ent.name);\n const skillPath = join(skillDir, SKILL_FILE);\n const content = await readFileSafe(skillPath);\n if (!content) continue;\n const { frontmatter, body } = parseFrontmatter(content);\n const supportingFiles = await listSupportingFiles(skillDir);\n skills.push({\n source: skillPath,\n name: ent.name,\n description: typeof frontmatter.description === 'string' ? frontmatter.description : '',\n body,\n supportingFiles,\n });\n }\n return skills.sort((a, b) => a.name.localeCompare(b.name));\n}\n","/**\n * Parse .agentsmesh/mcp.json into McpConfig.\n */\n\nimport { readFileSafe } from '../../utils/filesystem/fs.js';\nimport type { McpConfig, McpServer } from '../../core/types.js';\n\nfunction parseStringMap(raw: unknown): Record<string, string> {\n if (raw === null || typeof raw !== 'object' || Array.isArray(raw)) return {};\n return Object.fromEntries(\n Object.entries(raw).filter((entry): entry is [string, string] => typeof entry[1] === 'string'),\n );\n}\n\nfunction parseServer(raw: unknown): McpServer | null {\n if (!raw || typeof raw !== 'object') return null;\n const obj = raw as Record<string, unknown>;\n const type = typeof obj.type === 'string' ? obj.type : 'stdio';\n const env = parseStringMap(obj.env);\n const description = typeof obj.description === 'string' ? obj.description : undefined;\n\n const url = typeof obj.url === 'string' ? obj.url : '';\n if (url) {\n return {\n ...(description !== undefined && { description }),\n type,\n url,\n headers: parseStringMap(obj.headers),\n env,\n };\n }\n\n const command = typeof obj.command === 'string' ? obj.command : '';\n if (!command) return null;\n\n const args = Array.isArray(obj.args)\n ? obj.args.filter((x): x is string => typeof x === 'string')\n : [];\n return {\n ...(description !== undefined && { description }),\n type,\n command,\n args,\n env,\n };\n}\n\n/**\n * Parse mcp.json at the given path.\n * @param mcpPath - Absolute path to .agentsmesh/mcp.json\n * @returns McpConfig or null if file missing, malformed, or lacks mcpServers\n */\nexport async function parseMcp(mcpPath: string): Promise<McpConfig | null> {\n const content = await readFileSafe(mcpPath);\n if (!content) return null;\n let parsed: unknown;\n try {\n parsed = JSON.parse(content) as unknown;\n } catch {\n return null;\n }\n if (!parsed || typeof parsed !== 'object') return null;\n const mcpServersRaw = (parsed as Record<string, unknown>).mcpServers;\n if (mcpServersRaw === undefined) return null;\n if (typeof mcpServersRaw !== 'object' || mcpServersRaw === null) return null;\n const mcpServers: Record<string, McpServer> = {};\n for (const [name, val] of Object.entries(mcpServersRaw)) {\n const server = parseServer(val);\n if (server) mcpServers[name] = server;\n }\n return { mcpServers };\n}\n","/**\n * Parse .agentsmesh/permissions.yaml into Permissions.\n */\n\nimport { parse as parseYaml } from 'yaml';\nimport { readFileSafe } from '../../utils/filesystem/fs.js';\nimport type { Permissions } from '../../core/types.js';\n\nfunction ensureStringArray(val: unknown): string[] {\n if (!Array.isArray(val)) return [];\n return val.filter((x): x is string => typeof x === 'string');\n}\n\n/**\n * Parse permissions.yaml at the given path.\n * @param permissionsPath - Absolute path to .agentsmesh/permissions.yaml\n * @returns Permissions or null if file missing or malformed\n */\nexport async function parsePermissions(permissionsPath: string): Promise<Permissions | null> {\n const content = await readFileSafe(permissionsPath);\n if (content === null) return null;\n if (!content.trim()) return { allow: [], deny: [], ask: [] };\n let parsed: unknown;\n try {\n parsed = parseYaml(content) as unknown;\n } catch {\n return null;\n }\n if (!parsed || typeof parsed !== 'object') return null;\n const obj = parsed as Record<string, unknown>;\n const allow = ensureStringArray(obj.allow);\n const deny = ensureStringArray(obj.deny);\n const ask = ensureStringArray(obj.ask);\n return { allow, deny, ask };\n}\n","type HookLike = {\n command?: unknown;\n prompt?: unknown;\n type?: unknown;\n};\n\nfunction trimString(value: unknown): string {\n return typeof value === 'string' ? value.trim() : '';\n}\n\nexport function getHookCommand(entry: HookLike): string {\n return trimString(entry.command);\n}\n\nexport function getHookPrompt(entry: HookLike): string {\n return trimString(entry.prompt);\n}\n\nexport function getHookText(entry: HookLike): string {\n const command = getHookCommand(entry);\n const prompt = getHookPrompt(entry);\n return entry.type === 'prompt' ? prompt || command : command || prompt;\n}\n\nexport function hasHookCommand(entry: HookLike): boolean {\n return getHookCommand(entry).length > 0;\n}\n\nexport function hasHookText(entry: HookLike): boolean {\n return getHookText(entry).length > 0;\n}\n","/**\n * Parse .agentsmesh/hooks.yaml into Hooks.\n */\n\nimport { parse as parseYaml } from 'yaml';\nimport { readFileSafe } from '../../utils/filesystem/fs.js';\nimport type { HookEntry, Hooks } from '../../core/types.js';\nimport { getHookText, getHookPrompt } from '../../core/hook-command.js';\n\nconst VALID_TYPES = ['command', 'prompt'] as const;\n\nfunction toHookEntry(raw: unknown): HookEntry | null {\n if (!raw || typeof raw !== 'object') return null;\n const obj = raw as Record<string, unknown>;\n const matcher = obj.matcher;\n if (typeof matcher !== 'string') return null;\n const command = getHookText(obj);\n if (!command) return null;\n const type =\n typeof obj.type === 'string' && VALID_TYPES.includes(obj.type as (typeof VALID_TYPES)[number])\n ? (obj.type as 'command' | 'prompt')\n : undefined;\n const timeout =\n typeof obj.timeout === 'number' && Number.isFinite(obj.timeout) ? obj.timeout : undefined;\n const prompt = getHookPrompt(obj) || undefined;\n return {\n matcher,\n command,\n ...(timeout !== undefined && { timeout }),\n ...(type && { type }),\n ...(prompt && { prompt }),\n };\n}\n\n/**\n * Parse hooks.yaml at the given path.\n * @param hooksPath - Absolute path to .agentsmesh/hooks.yaml\n * @returns Hooks or null if file missing or malformed\n */\nexport async function parseHooks(hooksPath: string): Promise<Hooks | null> {\n const content = await readFileSafe(hooksPath);\n if (content === null) return null;\n if (!content.trim()) return {};\n let parsed: unknown;\n try {\n parsed = parseYaml(content) as unknown;\n } catch {\n return null;\n }\n if (!parsed || typeof parsed !== 'object') return null;\n const result: Hooks = {};\n const obj = parsed as Record<string, unknown>;\n for (const [key, val] of Object.entries(obj)) {\n if (!Array.isArray(val)) continue;\n const entries: HookEntry[] = [];\n for (const item of val) {\n const entry = toHookEntry(item);\n if (entry) entries.push(entry);\n }\n if (entries.length > 0) result[key] = entries;\n }\n return result;\n}\n","/**\n * Parse .agentsmesh/ignore into gitignore-style patterns.\n */\n\nimport { readFileSafe } from '../../utils/filesystem/fs.js';\nimport type { IgnorePatterns } from '../../core/types.js';\n\n/**\n * Parse ignore file at the given path.\n * @param ignorePath - Absolute path to .agentsmesh/ignore\n * @returns Array of ignore patterns (empty array if file missing or empty)\n */\nexport async function parseIgnore(ignorePath: string): Promise<IgnorePatterns> {\n const content = await readFileSafe(ignorePath);\n if (content === null || !content.trim()) return [];\n\n const lines = content.split(/\\r?\\n/);\n const patterns: string[] = [];\n\n for (const line of lines) {\n const trimmed = line.trim();\n if (trimmed === '' || trimmed.startsWith('#')) continue;\n patterns.push(trimmed);\n }\n\n return patterns;\n}\n","/**\n * Load all canonical files from a canonical directory into CanonicalFiles.\n */\n\nimport { join } from 'node:path';\nimport type { CanonicalFiles } from '../../core/types.js';\nimport { parseRules } from '../features/rules.js';\nimport { parseCommands } from '../features/commands.js';\nimport { parseAgents } from '../features/agents.js';\nimport { parseSkills } from '../features/skills.js';\nimport { parseMcp } from '../features/mcp.js';\nimport { parsePermissions } from '../features/permissions.js';\nimport { parseHooks } from '../features/hooks.js';\nimport { parseIgnore } from '../features/ignore.js';\nimport { exists } from '../../utils/filesystem/fs.js';\n\n/**\n * Load all canonical files from a canonical directory or project root.\n * Missing directories/files yield empty arrays or null as per each parser.\n *\n * @param canonicalDirOrProjectRoot - Absolute path to canonical directory or project root\n * @returns CanonicalFiles with all parsed data\n */\nexport async function loadCanonicalFiles(\n canonicalDirOrProjectRoot: string,\n): Promise<CanonicalFiles> {\n const nestedCanonicalDir = join(canonicalDirOrProjectRoot, '.agentsmesh');\n const canonicalDir = (await exists(nestedCanonicalDir))\n ? nestedCanonicalDir\n : canonicalDirOrProjectRoot;\n\n const [rules, commands, agents, skills, mcp, permissions, hooks, ignore] = await Promise.all([\n parseRules(join(canonicalDir, 'rules')),\n parseCommands(join(canonicalDir, 'commands')),\n parseAgents(join(canonicalDir, 'agents')),\n parseSkills(join(canonicalDir, 'skills')),\n parseMcp(join(canonicalDir, 'mcp.json')),\n parsePermissions(join(canonicalDir, 'permissions.yaml')),\n parseHooks(join(canonicalDir, 'hooks.yaml')),\n parseIgnore(join(canonicalDir, 'ignore')),\n ]);\n\n return {\n rules,\n commands,\n agents,\n skills,\n mcp,\n permissions,\n hooks,\n ignore,\n };\n}\n","/**\n * Public API — canonical loading (package.json \"exports\".\"./canonical\").\n */\n\nimport type { CanonicalFiles } from '../core/types.js';\nimport { loadCanonicalFiles } from '../canonical/load/loader.js';\n\nexport { loadCanonicalFiles };\n\nexport type {\n CanonicalFiles,\n CanonicalRule,\n CanonicalCommand,\n CanonicalAgent,\n CanonicalSkill,\n SkillSupportingFile,\n Permissions,\n IgnorePatterns,\n} from '../core/canonical-types.js';\n\nexport type { McpServer, StdioMcpServer, UrlMcpServer, McpConfig } from '../core/mcp-types.js';\n\nexport type { Hooks, HookEntry } from '../core/hook-types.js';\n\n/** Load `.agentsmesh/` from a project root (or an explicit canonical directory). */\nexport async function loadCanonical(projectRoot: string): Promise<CanonicalFiles> {\n return loadCanonicalFiles(projectRoot);\n}\n"]}
|