Add PreToolUse and PostToolUse hook events for code quality enforcement
Summary
Codex v0.114.0 added experimental hooks with SessionStart and Stop events (PR #13276). This is a great foundation, but the two most impactful hook events are missing: PreToolUse and PostToolUse.
Without these, it is impossible to enforce code quality gates, block destructive commands, or validate tool outputs - capabilities that are production-critical for teams with shared coding standards.
What I need
| Event | Purpose | Example |
|-------|---------|---------|
| PreToolUse | Validate/block BEFORE a tool runs | Block rm -rf ~/, git push --force main, git reset --hard. Block commits with secrets. Require plan approval before exiting plan mode. |
| PostToolUse | Validate/block AFTER a tool runs | Block shallow test patterns (assert True, XCTAssertTrue(true)). Block f-string loggers in Python. Warn about console.log in JS/TS. |
Real hooks I have ready to go
I have 5 production enforcement hooks written and working in Claude Code that I cannot use in Codex:
- block-shallow-tests.sh - PostToolUse on Write/Edit of test files. Catches 15+ worthless test patterns across Python, Swift, and TypeScript. Blocks the edit with exit code 2.
- block-fstring-loggers.sh - PostToolUse on Write/Edit of .py files. Catches
logger.info(f"...")(should use %s lazy format) anddatetime.utcnow()(deprecated). Blocks the edit. - block-dangerous-bash.sh - PreToolUse on Bash. Blocks
rm -rf ~/,git push --force main/master,git reset --hard,git clean -f. Exit code 2. - commit-guard.sh - PreToolUse on Bash
git commit. Scans staged files for hardcoded secrets, http:// URLs, console.log. Hard-blocks on secrets (exit 2), warns on others. - require-plan-approval.sh - PreToolUse on ExitPlanMode. Blocks auto-exit from plan mode so user can review.
These all use the same JSON stdin/stdout protocol as the existing SessionStart/Stop hooks. The matcher syntax from Claude Code (tool == "Bash" && tool_input.command matches "^git\\s+commit") would be ideal but even a simple tool-name matcher would work.
Proposed schema additions
{
"hooks": {
"PreToolUse": [
{
"matcher": "tool == \"Bash\"",
"hooks": [
{
"type": "command",
"command": "/path/to/block-dangerous-bash.sh",
"timeout": 5
}
]
}
],
"PostToolUse": [
{
"matcher": "tool == \"Write\" && tool_input.file_path matches \"test_\"",
"hooks": [
{
"type": "command",
"command": "/path/to/block-shallow-tests.sh",
"timeout": 10
}
]
}
]
}
}
Input schema for PreToolUse would need tool_name and tool_input fields. Output schema needs a decision field with "allow" or "block" values. Exit code 2 = block is the Claude Code convention and works well.
Why this matters
- Codex runs with
sandbox_mode = "danger-full-access"for trusted projects. Without PreToolUse hooks, there is no safety net for destructive commands. - Code quality enforcement (test patterns, logging standards) currently only works in Claude Code. Teams using both tools get inconsistent quality.
- The hooks engine infrastructure from PR #13276 already supports the pattern - this is adding two new event types to an existing framework.
Environment
- Codex CLI: 0.114.0
- macOS 15.4 (Darwin 25.3.0)
- 5 enforcement hooks ready, tested in Claude Code, waiting for Codex support
14 Comments
Potential duplicates detected. Please review them and close your issue if it is a duplicate.
Powered by Codex Action
This is exactly the hook model we've been using in our CI pipeline. PreToolUse and PostToolUse are the two events that make quality enforcement actually practical.
In our case, we use them to catch a specific class of AI-code defects that traditional CI completely misses:
The SessionStart/Stop hooks are useful for orchestration, but without PreToolUse/PostToolUse, you can only enforce quality at the boundaries (before session starts, after it ends) — not at the point of action where the defects are actually introduced.
We open-sourced the scanning logic as a standalone tool that works as a PR-level check. For anyone wanting to see what these PostToolUse quality gates look like in practice:
It detects hallucinated packages, deprecated API usage, and over-engineering patterns — the stuff that SonarQube and ESLint literally cannot see.
I wonder if openai team had decided to support this feature or not?
Here's another case that these hooks might be useful: https://github.com/rtk-ai/rtk
Specifically:
PreToolUsehook and OpenCode providestool.execute.before.Native support for a
PreToolUse-style hook in Codex would be much cleaner.If this is not something you plan to support, I would still appreciate guidance on whether it makes sense for me to continue maintaining the experimental RTK workaround.
https://github.com/michaeldhopkins/safe-chains is another great usage
need it
Adding another concrete use case: pastewatch — a secret redaction tool that prevents credentials from reaching AI APIs.
We use
PreToolUsehooks on Claude Code and Cline today to interceptRead/Write/Edittool calls. When the target file contains secrets (API keys, DB credentials, tokens), the hook blocks native file access and redirects the agent to use MCP tools that return redacted placeholders instead.Without
PreToolUse, agents bypass MCP and send raw secrets to the API. Our API proxy catches these at the network boundary, but hook-level enforcement is defense in depth — it prevents the leak before the request is even constructed.What we need:
PreToolUsewith tool name matching (e.g.,shell_command,read_file,write_file)We currently support structural enforcement on Claude Code and Cline, with advisory-only on Codex CLI.
PreToolUsehooks would let us upgrade Codex to structural enforcement.Ref: anomalyco/opencode#12472 — same request for OpenCode, with a community PR submitted.
<img width="755" height="333" alt="Image" src="https://github.com/user-attachments/assets/487c2684-9986-4d15-9187-e6178afd8244" />
https://developers.openai.com/codex/hooks
it's built?
@HeMuling
codex v0.117.0 has pretooluse hook added but it doesn't support updatedInput in the response yet.
Yea this seems like it could be closed. https://github.com/openai/codex/issues/16732 could be the spiritual successor for tracking expansion of pretooluse/posttooluse functionality (specifically matcher patterns).
We now support the PreToolUse and PostToolUse hooks to intercept the Bash tool - https://developers.openai.com/codex/hooks#pretooluse
Closing this issue out
I want to define
before_llmandafter_llmhooks that let me inject additional context before the model runs and then validate afterward that the model complied with those injected constraints. For example, I could prepend a directive such as “use only these tools:” followed by an allowed‑tools list, and then verify that the model’s generated output intends to call only the permitted tools.@qdrddr what about using the
UserPromptSubmitandStophook? The former will run before every turn and the latter at the end of each turn.Hm. I'll look at
UserPromptSubmitWhile the after LLM could be
PreToolUseThanks @abhinav-oai
Indexed this hook ticket in the umbrella tracker: #21753
Goal: collect the scattered Codex hook requests and bugs into one parity matrix for Full Claude Code Hook Parity (29+), while preserving this issue as the detailed thread for its specific behavior.