{"record":{"id":"59a18e29638c753d","repo":"EveryInc/compound-engineering-plugin","slug":"the-codex-plugin-manifest-does-not-point-at-this-r","errorCode":null,"errorMessage":"The Codex plugin manifest does not point at this repository's skills directory","messagePattern":"The Codex plugin manifest does not point at this repository's skills directory","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"src/dev/codex-dev.ts","lineNumber":135,"sourceCode":"    return JSON.parse(await fs.readFile(filePath, \"utf8\")) as Record<string, unknown>\n  } catch (error) {\n    throw new Error(`Could not read ${filePath}: ${error instanceof Error ? error.message : String(error)}`)\n  }\n}\n\nasync function assertCompoundEngineeringRepo(repoRoot: string): Promise<void> {\n  const packageJson = await readJson(path.join(repoRoot, \"package.json\"))\n  if (packageJson.name !== \"compound-engineering\") {\n    throw new Error(`${repoRoot} is not the compound-engineering repository`)\n  }\n  const pluginJson = await readJson(path.join(repoRoot, \".codex-plugin\", \"plugin.json\"))\n  if (pluginJson.name !== \"compound-engineering\") {\n    throw new Error(`${repoRoot} is not the compound-engineering repository`)\n  }\n\n  const skills = pluginJson.skills\n  if (typeof skills !== \"string\" || path.resolve(repoRoot, skills) !== path.join(repoRoot, \"skills\")) {\n    throw new Error(\"The Codex plugin manifest does not point at this repository's skills directory\")\n  }\n\n  const unsupported = [\"apps\", \"hooks\", \"mcpServers\"].filter((key) => pluginJson[key] !== undefined)\n  if (unsupported.length > 0) {\n    throw new Error(\n      `Local skill mode cannot represent Codex runtime components: ${unsupported.join(\", \")}. Update the developer workflow before using it.`,\n    )\n  }\n\n  try {\n    const defaultHooks = await fs.stat(path.join(repoRoot, \"hooks\", \"hooks.json\"))\n    if (defaultHooks.isFile()) {\n      throw new Error(\n        \"Local skill mode cannot represent default Codex hooks at hooks/hooks.json. Update the developer workflow before using it.\",\n      )\n    }\n  } catch (error) {\n    if ((error as NodeJS.ErrnoException).code !== \"ENOENT\") throw error","sourceCodeStart":117,"sourceCodeEnd":153,"githubUrl":"https://github.com/EveryInc/compound-engineering-plugin/blob/c9c10f8c75412c7232cb2bd663e5fd1cea98d84e/src/dev/codex-dev.ts#L117-L153","documentation":"The library reads the skills field from .codex-plugin/plugin.json and requires it to be a string that resolves (via path.resolve against the repo root) exactly to <repoRoot>/skills. Otherwise it throws this error, because local skill mode symlinks that directory and cannot operate if the manifest points anywhere else.","triggerScenarios":"plugin.json has no skills field, skills is not a string (e.g. an object/array), or path.resolve(repoRoot, skills) !== path.join(repoRoot, \"skills\") — e.g. skills: \"./src/skills\" or a path with ../ traversal (src/dev/codex-dev.ts:135).","commonSituations":"Experimenting with a relocated skills directory and updating the manifest locally; a manifest authored for a different layout; copying a manifest from another plugin that stores skills elsewhere.","solutions":["Check the manifest: jq .skills .codex-plugin/plugin.json — it should be \"skills\".","git restore .codex-plugin/plugin.json if you changed it for an experiment.","If you genuinely moved the skills directory, move it back to <repoRoot>/skills rather than editing the manifest for local dev mode."],"exampleFix":"// before: .codex-plugin/plugin.json\n{ \"name\": \"compound-engineering\", \"skills\": \"./src/skills\" }\n// after\n{ \"name\": \"compound-engineering\", \"skills\": \"skills\" }","handlingStrategy":"validation","validationCode":"import { readFile } from \"node:fs/promises\"\nimport path from \"node:path\"\nconst m = JSON.parse(await readFile(\".codex-plugin/plugin.json\", \"utf8\"))\nif (typeof m.skills !== \"string\" || path.resolve(m.skills) !== path.resolve(\"skills\")) {\n  throw new Error(\"plugin.json skills must be \\\"skills\\\" for local dev mode\")\n}","typeGuard":"function pointsAtSkillsDir(m: { skills?: unknown }): m is { skills: string } {\n  return typeof m.skills === \"string\"\n}","tryCatchPattern":"try {\n  await activateLocalCollection(ctx)\n} catch (error) {\n  if ((error as Error).message.includes(\"does not point at this repository's skills directory\")) {\n    console.error(\"Restore the manifest: git restore .codex-plugin/plugin.json\")\n  } else throw error\n}","preventionTips":["Do not relocate the skills directory without a matching dev-workflow update.","Keep skills as a top-level directory named exactly \"skills\".","Validate manifest changes with bun run release:validate before running local mode."],"tags":["validation","manifest","paths"],"backgroundTag":"manifest-schema-mismatch","analyzedSha":"c9c10f8c75412c7232cb2bd663e5fd1cea98d84e","analyzedAt":"2026-08-31T15:18:07.959Z","schemaVersion":2},"datasetVersion":"2026-08-31T19:17:28.585Z"}