fix(installer): stop duplicating agent instructions; MCP server is the single source of truth (#529) (#538)
The installer wrote a `## CodeGraph` usage block into each agent's
instructions file (CLAUDE.md / AGENTS.md / GEMINI.md / .cursor/rules /
Kiro steering) that duplicated, almost verbatim, the guidance the MCP
server already emits in its `initialize` response — so agents that
surface MCP instructions (Claude Code) read the same playbook twice
every turn.
All 6 instruction-writing targets (claude, cursor, codex, opencode,
gemini, kiro) now stop writing the block. install self-heals by
stripping a block a previous version wrote (uninstall already did), so
the next `codegraph install`/`uninstall` cleans up existing installs;
upgrading the package alone does not (the leftover block is harmless).
server-instructions.ts is now the single source of truth — the two
steers unique to the old template ("trust codegraph, don't re-verify
with grep" and the not-initialized -> `init -i` hint) are ported there.
Removes the now-dead INSTRUCTIONS_TEMPLATE / CLAUDE_MD_TEMPLATE,
claude-md-template.ts, writeClaudeMd / hasClaudeMdSection, and the
Cursor-only wireProjectSurfaces bootstrap. The install log learned a
"Removed" verb. Tests rewritten to the new contract + self-heal
coverage (140/140 installer tests pass).
Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 4.8
parent
cea78ceb1b
commit
a9c9e76d8c
+4
-36
@@ -21,7 +21,7 @@ import {
|
||||
getTarget,
|
||||
resolveTargetFlag,
|
||||
} from './targets/registry';
|
||||
import type { AgentTarget, Location, TargetId, WriteResult } from './targets/types';
|
||||
import type { AgentTarget, Location, TargetId } from './targets/types';
|
||||
import { getGlyphs } from '../ui/glyphs';
|
||||
// Import the lightweight submodules directly (not the ../sync barrel, which
|
||||
// re-exports FileWatcher and would transitively pull in ../extraction — the
|
||||
@@ -35,10 +35,8 @@ import { isGitRepo, isSyncHookInstalled, installGitSyncHook } from '../sync/git-
|
||||
export {
|
||||
writeMcpConfig,
|
||||
writePermissions,
|
||||
writeClaudeMd,
|
||||
hasMcpConfig,
|
||||
hasPermissions,
|
||||
hasClaudeMdSection,
|
||||
} from './config-writer';
|
||||
export type { InstallLocation } from './config-writer';
|
||||
|
||||
@@ -194,7 +192,9 @@ export async function runInstallerWithOptions(opts: RunInstallerOptions): Promis
|
||||
for (const file of result.files) {
|
||||
const verb = file.action === 'unchanged'
|
||||
? 'Unchanged'
|
||||
: file.action === 'created' ? 'Created' : 'Updated';
|
||||
: file.action === 'created' ? 'Created'
|
||||
: file.action === 'removed' ? 'Removed'
|
||||
: 'Updated';
|
||||
clack.log.success(`${target.displayName}: ${verb} ${tildify(file.path)}`);
|
||||
}
|
||||
for (const note of result.notes ?? []) {
|
||||
@@ -378,38 +378,6 @@ export async function runUninstaller(opts: RunUninstallerOptions): Promise<void>
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* For every target that has a global config and exposes
|
||||
* `wireProjectSurfaces`, write its project-local surfaces (e.g.
|
||||
* Cursor's `.cursor/rules/codegraph.mdc`). Idempotent — runs
|
||||
* silently when there's nothing to write.
|
||||
*
|
||||
* Called by `codegraph init` so that a user who ran
|
||||
* `codegraph install` once globally doesn't have to re-run it per
|
||||
* project to get full agent support.
|
||||
*
|
||||
* Returns the list of `(target, file)` pairs that were created or
|
||||
* updated — caller decides how to surface them.
|
||||
*/
|
||||
export function wireProjectSurfacesForGlobalAgents(): Array<{
|
||||
target: AgentTarget;
|
||||
file: WriteResult['files'][number];
|
||||
}> {
|
||||
const written: Array<{ target: AgentTarget; file: WriteResult['files'][number] }> = [];
|
||||
for (const target of ALL_TARGETS) {
|
||||
if (typeof target.wireProjectSurfaces !== 'function') continue;
|
||||
const detection = target.detect('global');
|
||||
if (!detection.alreadyConfigured) continue;
|
||||
const result = target.wireProjectSurfaces();
|
||||
for (const file of result.files) {
|
||||
if (file.action === 'created' || file.action === 'updated') {
|
||||
written.push({ target, file });
|
||||
}
|
||||
}
|
||||
}
|
||||
return written;
|
||||
}
|
||||
|
||||
/**
|
||||
* Replace home-directory prefix in a path with `~/` for cleaner log
|
||||
* lines. Pure cosmetic.
|
||||
|
||||
Reference in New Issue
Block a user