mirror of
https://github.com/pbakaus/impeccable.git
synced 2026-09-11 21:57:14 +03:00
fix: stop emitting the "agents" key so the four subagents actually load (#494)
build.js derives plugin/.claude-plugin/plugin.json from the root manifest and injects an `agents` array built from the generated agent files. In Claude Code that array is exactly what stops them loading. Verified on a throwaway local marketplace, across the plausible shapes: array of file paths (what build.js emits) -> 0 agents load, skills fine a string, e.g. "./agents" -> whole plugin fails to load array containing a directory -> whole plugin fails to load key omitted -> all agents load, skills fine Claude Code discovers agents/*.md on its own, and the identifier it uses is the file name rather than the frontmatter `name`. So the key is not needed, and any present form of it is worse than its absence. Confirmed end to end on this repo: with the key emitted, `claude plugin details impeccable` reports "Agents (0)"; with it omitted it reports "Agents (4) impeccable-asset-producer, impeccable-documenter, impeccable-finish-reviewer, impeccable-manual-edit-applier". The agent files themselves are still copied by the existing copyDirSync a few lines below — only the manifest key goes away. Two things make this hard to notice: with a breaking shape `claude plugin details` prints "Plugin not found" instead of a validation error, and `claude plugin validate` does not catch it because it validates the marketplace manifest, not the plugin manifest. The only reliable signal is the "Agents (N)" line. The same defect is reported against another project at addyosmani/agent-skills#449, with the full reproduction. Scope note: verified on Claude Code only. plugin/ is the Claude-Code / Grok subtree, and the Grok manifest is written separately just below, so this does not touch the other harnesses.
This commit is contained in:
+7
-11
@@ -627,22 +627,18 @@ async function build() {
|
||||
|
||||
const rootManifest = JSON.parse(fs.readFileSync(path.join(ROOT_DIR, '.claude-plugin/plugin.json'), 'utf-8'));
|
||||
const claudeAgentsSrc = path.join(DIST_DIR, 'claude-code', '.claude', 'agents');
|
||||
const pluginAgentEntries = fs.existsSync(claudeAgentsSrc)
|
||||
? fs.readdirSync(claudeAgentsSrc)
|
||||
.filter(file => file.endsWith('.md'))
|
||||
.sort()
|
||||
.map(file => `./agents/${file}`)
|
||||
: [];
|
||||
// Trailing slash on the skills path matches the documented schema in
|
||||
// code.claude.com/docs/en/plugins-reference. Issue #86 has 3 reporters
|
||||
// converging on "add trailing slash to fix slash commands not registering";
|
||||
// the docs schema example consistently uses `"./custom/skills/"` form.
|
||||
const pluginManifest = { ...rootManifest, skills: './skills/' };
|
||||
if (pluginAgentEntries.length) {
|
||||
pluginManifest.agents = pluginAgentEntries;
|
||||
} else {
|
||||
delete pluginManifest.agents;
|
||||
}
|
||||
// No `agents` key: Claude Code discovers agents/*.md by itself, and the
|
||||
// identifier it uses is the file name. Declaring the key as an array of
|
||||
// file paths makes it load ZERO agents, so the four shipped subagents were
|
||||
// never reachable. The other plausible shapes are worse: a string, or an
|
||||
// array containing a directory, and the whole plugin fails to load.
|
||||
// Omitting the key is the only shape that works.
|
||||
delete pluginManifest.agents;
|
||||
fs.mkdirSync(pluginManifestDir, { recursive: true });
|
||||
fs.writeFileSync(
|
||||
path.join(pluginManifestDir, 'plugin.json'),
|
||||
|
||||
Reference in New Issue
Block a user