Summary
After installing codebase-memory-mcp, Codex starts with this warning:
loading hooks from both ~/.codex/hooks.json and ~/.codex/config.toml; prefer a single representation for this layer
It looks like the installer writes hook configuration into both hook representations at the same time.
What happened
The installation added a SessionStart hook to ~/.codex/config.toml:
[[hooks.SessionStart]]
matcher = "startup|resume|clear|compact"
[[hooks.SessionStart.hooks]]
type = "command"
command = 'echo "Code discovery: prefer codebase-memory-mcp (search_graph, trace_path, get_code_snippet, query_graph, search_code) over grep/file-read; run index_repository first if the project is not indexed."'
# <<< codebase-memory-mcp SessionStart <<<
At the same time, ~/.codex/hooks.json also contains hook definitions, including a matching SessionStart hook with the same message:
{
"hooks": {
"SessionStart": [
{
"matcher": "startup|resume|clear|compact",
"hooks": [
{
"type": "command",
"command": "echo \"Code discovery: prefer codebase-memory-mcp (search_graph, trace_path, get_code_snippet, query_graph, search_code) over grep/file-read; run index_repository first if the project is not indexed.\""
}
]
}
]
}
}
This causes Codex to warn that hooks are being loaded from both hooks.json and config.toml.
Impact
For this specific hook, the impact is minor but visible:
- the startup/session hook message can appear more than once;
- Codex emits the warning about mixed hook representations;
- users may think their Codex or MCP setup is broken;
- if future hooks have side effects, duplicate hook sources could cause duplicate execution, slower startup, duplicated state writes, etc.
Expected behavior
The installer should prefer a single hook representation for the same layer, for example:
- write codebase-memory-mcp hooks only to
~/.codex/hooks.json if that file is already being used; or
- write only to
~/.codex/config.toml; or
- detect the existing representation and avoid adding the same hook to both places.
Suggested fix
During installation/setup, detect whether ~/.codex/hooks.json exists or whether Codex is already using TOML hooks, then install the SessionStart hook into only one location.
It may also be useful to add cleanup/migration logic that removes the duplicate codebase-memory-mcp SessionStart block from config.toml when the same hook already exists in hooks.json.
Summary
After installing
codebase-memory-mcp, Codex starts with this warning:It looks like the installer writes hook configuration into both hook representations at the same time.
What happened
The installation added a
SessionStarthook to~/.codex/config.toml:At the same time,
~/.codex/hooks.jsonalso contains hook definitions, including a matchingSessionStarthook with the same message:{ "hooks": { "SessionStart": [ { "matcher": "startup|resume|clear|compact", "hooks": [ { "type": "command", "command": "echo \"Code discovery: prefer codebase-memory-mcp (search_graph, trace_path, get_code_snippet, query_graph, search_code) over grep/file-read; run index_repository first if the project is not indexed.\"" } ] } ] } }This causes Codex to warn that hooks are being loaded from both
hooks.jsonandconfig.toml.Impact
For this specific hook, the impact is minor but visible:
Expected behavior
The installer should prefer a single hook representation for the same layer, for example:
~/.codex/hooks.jsonif that file is already being used; or~/.codex/config.toml; orSuggested fix
During installation/setup, detect whether
~/.codex/hooks.jsonexists or whether Codex is already using TOML hooks, then install theSessionStarthook into only one location.It may also be useful to add cleanup/migration logic that removes the duplicate
codebase-memory-mcp SessionStartblock fromconfig.tomlwhen the same hook already exists inhooks.json.