Blog / claude code
Claude writes the tests, Codex writes the code
Split a feature between two agents: Claude Code writes the spec and failing tests, Codex makes them pass, and git shows it didn't touch the tests.
On this page
- Step 1: Claude writes the spec and the failing tests
- What a good spec covers
- Step 2: Codex makes the tests pass
- Step 3: Check it, don't trust it
- Why split it at all
- Making it a habit
- Where Joxo fits
- Frequently asked questions
- Can Codex and Claude Code work on the same repo?
- How do I stop the agent from changing the tests to make them pass?
- Which agent should write the tests?
- What if a test is wrong?
- Try it with your team
A pattern keeps coming up in Claude Code and Codex forums: one agent decides what "done" means, and another one does the work. The first writes a short spec and tests that fail. The second writes code until the tests pass. Neither gets to mark its own homework.
It works because tests are a handoff you can check. The second agent doesn't need the first one's chat history, only the spec and the tests in the repo. And git shows at a glance whether it changed the tests to make them pass.
Here is the whole flow on a small example, tested with Claude Code 2.1.316, Codex 0.164 and Node 26.
Step 1: Claude writes the spec and the failing tests#
Start in a clean repo with a commit you can come back to:
mkdir slug-demo && cd slug-demo && git init
echo '{"name":"demo","type":"module","scripts":{"test":"node --test"}}' > package.json
git add -A && git commit -m initThen ask Claude Code for the spec and tests, and only those:
claude -p "Write SPEC.md describing a function slugify(text) in src/slugify.js: lowercase, trim, spaces and punctuation runs become one hyphen, no leading/trailing hyphens, accents removed (é→e). Then write test/slugify.test.js with node:test covering every rule. Do NOT write src/slugify.js. Run npm test and confirm the tests fail." --allowedTools "Write,Read,Bash(npm test)"The --allowedTools list matters. Claude can write files and run the tests, nothing else, so it can't start on the implementation "to check the tests work".
Claude wrote a seven-rule SPEC.md with an examples table and eleven tests. It also told us where it had filled a gap:
The empty-input rule is my addition to the spec, since you didn't say what those cases should return.That line is why this step is worth a human look. Read the spec, change what's wrong, and agree with it before anything gets built. Then the tests fail, as they should:
Error [ERR_MODULE_NOT_FOUND]: Cannot find module '.../src/slugify.js'Commit this state. It's the contract:
git add -A && git commit -m "slugify: spec and failing tests"What a good spec covers#
The spec is short, but it decides everything after it. Before you commit, check that it has:
- Where the code goes and what it's called, so the second agent doesn't invent its own file layout or function name.
- Every rule as one numbered line, so each test maps to a rule and a missing test is easy to spot.
- Examples with exact input and output. They settle arguments that prose leaves open, such as whether
"Ünïcode"becomesunicodeornicode. - What happens at the edges: empty input, very long input, input that's only punctuation. This is where agents guess differently.
- What's out of scope. "No support for non-Latin scripts" stops the second agent from spending its run on a feature nobody asked for.
If you would struggle to say whether an output is right from the spec alone, the second agent will too.
Step 2: Codex makes the tests pass#
Now hand the repo to Codex with a short brief that points at the contract and says what's off limits:
codex exec -s workspace-write "Read SPEC.md and test/slugify.test.js. Write src/slugify.js so npm test passes. Do not edit the tests or SPEC.md. Run npm test at the end."-s workspace-write lets Codex write files in the project and run commands, but nothing outside it. Codex wrote the function, ran the tests and reported:
Implemented `src/slugify.js` per `SPEC.md`.
`npm test` passes: 11 tests, 0 failures.Step 3: Check it, don't trust it#
Two commands tell you whether the handoff held. First, the tests and spec are exactly as Claude left them:
git diff --exit-code HEAD -- test SPEC.md && echo "tests untouched"tests untouchedIf that prints a diff instead, the second agent changed the goal to fit its code. Throw the change away with git checkout HEAD -- test SPEC.md and run step 2 again.
Second, run the tests yourself rather than taking the report's word:
npm testℹ tests 11
ℹ pass 11
ℹ fail 0Then read the code. Passing tests prove the rules you wrote down, nothing more. For a last pass, ask the first agent to review the second one's work against its own spec:
claude -p "Review src/slugify.js against SPEC.md. List any rule it gets wrong or any input the tests miss." --permission-mode planWhy split it at all#
You can ask one agent to do all three steps. The split helps in three ways:
- Tests written before the code test the spec, not the code. An agent that writes both tends to write tests that match what it built, bugs included.
- The handoff is small. Codex needed two files, not a long conversation, so it starts with a short, focused context.
- You can mix strengths. Use the agent that's best at careful specs for step 1 and a faster one for step 2.
It works less well for UI work, where the hard part isn't testable, and for changes too small to need a spec. A one-line fix doesn't need two agents.
Making it a habit#
Put the rules in the files each agent reads, so you don't repeat them in every prompt. In AGENTS.md (read by Codex):
When a task comes with tests in test/, make them pass. Never edit files in test/ or SPEC.md.
If a test looks wrong, stop and say which one and why.And in CLAUDE.md, for the spec step: "When asked for a spec, write SPEC.md and failing tests only. Point out every rule you added yourself."
Where Joxo fits#
The same split works between people. Your agent writes the spec and tests, and your teammate's agent, on their computer, picks up the task and builds it. Joxo carries the task between them and shows you both where it is. Setup is one line pasted into your agent. For two agents on one machine, see handing off from Claude Code to Codex.
Frequently asked questions#
Can Codex and Claude Code work on the same repo?#
Yes. They both read the files on disk, so a spec and tests committed by one are all the other needs. Give each its own step and commit between them.
How do I stop the agent from changing the tests to make them pass?#
Say so in the prompt and in AGENTS.md, then check: git diff --exit-code HEAD -- test prints nothing if the tests are untouched.
Which agent should write the tests?#
The one you trust most with careful reading, since the tests become the definition of done. Read the spec it writes before handing off.
What if a test is wrong?#
Then the spec step missed something. Have the implementing agent stop and name the test (the AGENTS.md rule above does that), fix the spec and test yourself or with the first agent, commit, and hand off again.