fix(codex): align adapter with current docs + cross-vendor install propagation#47
Merged
Conversation
Multiple corrections to the Codex adapter, all driven by triaging issue #22 item 5 (Codex extension support): - skill_dirs: scan canonical ~/.agents/skills first; keep ~/.codex/skills as deprecated-but-functional fallback per Codex's own loader source comment at v0.130.0. - global_memory_files: defensive comment forbidding any future extension to scan ~/.codex/memories_extensions/chronicle/. Chronicle stores unencrypted OCR'd screen content; surfacing it would be a privacy footgun even though the files are technically readable. - project_hook_config_relpath: implement (.codex/hooks.json). The trait + scanner already supported project-level hook discovery for Claude/Cursor/Windsurf; only Codex was missing the override. - Rules file fallback: read project_doc_fallback_filenames from ~/.codex/config.toml (defaults to AGENTS.override.md, AGENTS.md, TEAM_GUIDE.md, .agents.md per Codex docs) and feed it into both global_rules_files and project_rules_patterns. Empty/malformed configs fall through to the default list. Empty strings filtered to avoid base_dir().join("") footgun. Tests added: 7 doc_fallback cases + 1 scanner regression test for project Codex hook discovery. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Codex deprecated `[features] codex_hooks = true` in favor of
`[features] hooks = true` (user observed deprecation warning on CLI
0.130.0). Update ensure_codex_hooks_enabled to:
- write the new flag name on first install
- skip rewriting if either form is already present (Codex still
honors `codex_hooks` with a deprecation warning, so we don't
editorialize)
Refactored from string-append to parse-modify-serialize, mirroring
the existing set_codex_plugin_enabled pattern. Old approach had two
real bugs that this rewrite fixes:
- duplicate [features] section: when the user already had
[features] (e.g. memories = true) without our flag, the old
string-append wrote a second [features] block, which TOML rejects
on re-parse and Codex would refuse to load.
- substring false-positive: contains("codex_hooks") matched the
literal string anywhere in the file (including comments). The
TOML-parsing version only inspects the actual table.
Corrupted-TOML reads now surface as ConfigCorrupted instead of
silently appending and producing a worse-broken file.
Added 5 unit tests covering: missing config, canonical flag present,
deprecated flag present, preexisting [features] table without our
flag, and corrupted TOML.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
When a skill is installed to a directory that multiple detected adapters scan (e.g. ~/.agents/skills/ is scanned by Codex, Gemini CLI, Cursor, Copilot, and OpenCode at user-global scope per their official docs), every other adapter's row produced by the next scan_all lacks install_meta. The Marketplace's URL-based "is this installed?" check keys on install_meta.url, so it falsely showed all those siblings as not installed even though the file was on disk and would be picked up by their next runtime scan. Fix: in post_install_sync, after the existing per-target write, find every other detected adapter whose skill_dir for the install scope equals the target_dir, scan-and-sync each, and set_install_meta on the resulting sibling row. New helper adapter_scans_dir handles the Global vs Project comparison. Also refactored install_to_agent's skill arm to delegate to post_install_sync after the deploy. Previously it had a parallel sibling-propagation loop that did the same thing minus pack propagation and audit; collapsing the two paths means cross-agent deploy now also gets pack propagation and audit for free, and removes ~25 lines of duplicated logic. Two tests pin both entry points: install_to_agent (cross-agent deploy button) and post_install_sync (the path Marketplace install actually runs through). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Codex CLI 0.129+ enforces hook trust: a hook will not execute until the user explicitly trusts it via `codex /hooks`. After installing a hook to Codex, users without this awareness see "the hook silently doesn't run" with no obvious cause. Add a static reminder banner in the extension detail panel, shown whenever an extension is a hook AND has codex in its agents list. Theme-colored info style, stays put until the hook is uninstalled. Deliberately not detecting actual trust state (Trusted / Modified / Untrusted): replicating Codex's hash algorithm requires matching Codex's internal canonicalization exactly, and the upstream source flags both the positional hook key and parts of the hash recipe as churn-prone. A static reminder is more durable than a detector that silently breaks when Codex evolves. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Comprehensive Codex adapter audit driven by issue #22 point 5b ("Codex full extension installation support"). Cross-checked HK's adapter against Codex's current published docs and rust-v0.130.0 source code; fixed multiple alignment gaps and one user-visible installation correctness bug along the way.
What changed
5eb723dfix(codex)~/.agents/skillsas canonical user-skill path, missing project-level<repo>/.codex/hooks.jsondiscovery, hardcoding only 2 of Codex's 4 default rule-doc filenames, and at risk of silently scanning the privacy-sensitive Chronicle directory.3f62df8fix(codex)[features].hooksflag rename + duplicate-section bugcodex_hooksin favor ofhooks. Old string-append also produced duplicate[features]sections that TOML rejects on re-parse. Refactored to parse-modify-serialize.b0fab1efix~/.agents/skills/(a directory Codex/Gemini/Cursor/Copilot/OpenCode all scan per their docs), only the explicit target's row gotinstall_meta. Marketplace's URL-based "installed?" check then falsely showed siblings as not installed. Now propagates to every adapter that scans the install dir. Also collapses duplicate sibling-propagation logic that existed ininstall_to_agentandpost_install_sync.4565f7afeat(ui)codex /hooksbefore it executes. Static reminder banner shown in the detail panel when a hook has Codex in its agent list. Deliberately not detecting actual trust state — Codex's hash recipe and hook-key format are explicitly flagged as churn-prone in upstream source.Verification
cargo test --workspace— 400 tests pass (15 new across the four commits)cargo clippy --workspace --all-targets -- -D warningscleannpm run lintandnpx tsc --noEmitclean~/.agents/skills/<name>/SKILL.md[features].hooks = true(not deprecatedcodex_hooks); merges into a preexisting[features]table without producing a duplicate section<project_root>/:AGENTS.override.md,AGENTS.md,TEAM_GUIDE.md,.agents.md<project>/.codex/hooks.jsondiscovered as a project-scoped hookagentsOut of scope (deferred)
~/.codex/.agents/skillswalk into nested subdirectories for monorepos. Existing HK convention of scanning at the project root only matches HK's project-MCP behavior. No issue reports.[[skills.config]] enabled = falsenative disable mechanism. Cross-cutting design issue tracked alongside MCP per-agent state in `project_mcp_per_agent_native_state_roadmap.md`.Refs #22 (point 5b).
🤖 Generated with Claude Code