Kit · Claude Code and Codex · no API

The mistake that comes back becomes a guard

Your agent makes a mistake, you correct it, and tomorrow it makes the same one again. This kit finds where you corrected the agent, finds the mistake that keeps recurring — even in another project — and turns the lesson into a hook, validator, or test the model can't skip.

Banner: agente-que-aprende — the mistake that comes back becomes a guard
In short

agente-que-aprende is a kit of four Python scripts for people who work with AI coding agents such as Claude Code and Codex. It reads your sessions and the files where you record failures and lessons (FALHAS.md, LESSONS.md), shows where you corrected the agent and which mistakes keep coming back, and helps turn each lesson into an automatic guard instead of yet another written rule. It needs only Python 3; it uses no internet or API, and no rule is adopted without your decision.

Video

Watch the explainer

The project explained in a few minutes.

What it is

The model stays the same. The system around it gets better.

A written rule is the weakest correction: the model can skip it. The order of strength is architecture (the mistake becomes impossible) > hook/validator (blocks it) > test (catches it) > checklist > prose.

The kit's six parts: retro, climb a rung, gardener, hook, validator, and SIL Loop R

🔁 One-minute retro

retro.py reads the session and lists every time you corrected the agent and every tool error that repeated, with the suggested rung. It runs on its own when the session closes.

🪜 Climb a rung

degrau.py and jardineiro.py read FALHAS and LESSONS, group the same mistake written in different ways, and show what is still only prose and keeps recurring.

🔒 A hook that blocks

gancho.py is a Claude Code hook: each lesson becomes a line in ganchos.json, and the command that already went wrong is blocked, with the explanation sent back to the agent. It works in Claude Code; in Codex, the retro and the gardener already work, the hook doesn't yet.

How it works

The cycle, and where each script fits

The agent runs, gets feedback, the feedback is checked, you approve, and the lesson lands where the next run can't ignore it.

Session ends→ retro.py (corrections + errors)→ You choose (human gate)→ FALHAS / LESSONS / SIL→ jardineiro.py weekly→ hook, validator, or test→ recurrence drops

The 6 rungs

1 protections (tests, types, lint) · 2 skills · 3 memory · 4 impossible mistake · 5 automation · 6 self-improvement. The top is the last rung: without the ones below, there's nothing to learn from. The ladder is the team's path; the order of strength (architecture > hook > test > checklist > prose) applies to each lesson.

Transparent guess

The current rung and the suggestion come from signal words in aprende/comum.py ("ausente/pulou" (missing/skipped) → architecture; "conferir antes" (check first) → validator; dangerous command → hook). The words and reports are in Portuguese (with some English); you adjust the list and decide.

Integrates with SIL Loop R

SIL Loop R is another open project: a local notebook (SQLite) of incidents and lessons, where nothing becomes a rule without a human decision. With --sil <projeto>, each kit proposal goes in there as an incident + proposed lesson. It's optional.

Prerequisites

Just Python 3

No dependencies, no keys, no network calls. SIL Loop R is optional.

Python 3.10+

Standard library only.

# check
python3 --version

Your records

Files with these names: FALHAS.md (table: date | what broke | smallest fix | prompt/infra), LICOES.md (3-column table) and/or LESSONS.md (list "- rule (date)"). Each table row starts with the date (YYYY-MM-DD or dd/mm).

# example row
| 2026-11-06 | render caiu: template ausente | rodar o passo antes | prompt |

Optional

Claude Code (for the hooks), systemd (weekly timer), and SIL Loop R (to receive the proposals). The kit looks for SIL in ~/projetos/sil-loop-r/, on the PATH (sil), or in AQA_SIL.

git clone https://github.com/inematds/sil-loop-r.git ~/projetos/sil-loop-r
python3 ~/projetos/sil-loop-r/sil.py --project ~/projetos/meu-app init
User guide · step by step

From clone to your first guard

Each step uses the repository's commands. The tests use fictional data and run without a network.

1

Download and test

The 10 tests check table parsing, the retro, the hook, and the SIL integration.

git clone https://github.com/inematds/agente-que-aprende.git && cd agente-que-aprende
python3 -m unittest discover -s tests -v   # OK
2

See what should climb a rung in a project

Reads the project's failures and lessons and lists what keeps recurring and is still only prose, with the suggested rung and the source lines.

python3 degrau.py tests/dados/FALHAS.md   # demo with the repo's data
python3 degrau.py ~/projetos/meu-app/FALHAS.md ~/projetos/meu-app/LESSONS.md --top 10
3

Run the gardener across all projects

Measures recurrence (how much of the record is the same mistake again), shows the mistakes that "moved house," and the overall ranking.

python3 jardineiro.py --raiz tests   # demo
python3 jardineiro.py --raiz ~/projetos --saida jardim/$(date +%F).md
4

Run a retro on a session

Point it at the session file (the most recent ones: ls -t ~/.claude/projects/*/*.jsonl | head -3). --pergunta appends the retro prompt to paste into the agent ("what went wrong here?").

python3 retro.py tests/dados/sessao.jsonl --pergunta   # demo
python3 retro.py ~/.claude/projects/<pasta>/<id>.jsonl --pergunta
python3 retro.py ~/.codex/sessions/<aaaa/mm/dd>/rollout-<…>.jsonl   # Codex too
5

Turn a lesson into a hook

One more item in the ganchos.json list (comma-separated): the pattern of the wrong command, the exception (optional), the message, and where the lesson came from. The kit already ships with a universal guard (pkill-f); more examples in modelos/ganchos-exemplo.json. To leave the kit's file untouched, use your own file via AQA_GANCHOS=/caminho/meus.json. Test before turning on step 6: the hook ignores what's inside quotes and inside a heredoc, so quoting the command in a text, a commit, or a grep isn't blocked.

{"id": "pkill-f", "ferramenta": "Bash", "padrao": "\\bpkill\\b[^|;&]*\\s-f\\b",
 "mensagem": "Liste com pgrep -af e mate por PID em outro comando.", "origem": "FALHAS (7x)"}

echo '{"tool_name":"Bash","tool_input":{"command":"pkill -f x"}}' | python3 gancho.py; echo $?   # 2 = blocked
6

Turn it on in Claude Code

In ~/.claude/settings.json: the hook before every Bash command and the retro when the session closes (reports in ~/.local/share/agente-que-aprende/retro/, only when there was a correction or a repeated error).

"hooks": {
  "PreToolUse": [{"matcher": "Bash", "hooks": [{"type": "command", "command": "python3 /caminho/agente-que-aprende/gancho.py"}]}],
  "SessionEnd": [{"hooks": [{"type": "command", "command": "bash /caminho/agente-que-aprende/hooks/fim-de-sessao.sh"}]}]
}
7

Gardener every week

Copy the timer and, in jardineiro.service, change KIT (where the kit lives), SAIDA (where to save the reports), and the --raiz %h/projetos (where your projects live). Every Monday at 07:30 a new report comes out.

cp modelos/systemd/jardineiro.{service,timer} ~/.config/systemd/user/
systemctl --user daemon-reload && systemctl --user enable --now jardineiro.timer
8

Send the proposals to SIL (optional)

With SIL installed and initialized in the project (see Prerequisites), the top 5 candidates become an incident + proposed lesson in SIL Loop R (retro.py also accepts --sil). Nothing is adopted without you.

python3 jardineiro.py --raiz ~/projetos --sil ~/projetos/meu-app
AQA_SIL=/outro/lugar/sil.py python3 retro.py sessao.jsonl --sil ~/projetos/meu-app   # SIL outside ~/projetos
Examples

What it found on the first pass

Run on INEMA's real records on Nov 7, 2026: 196 failure and lesson files, 1,880 records, in under 1 second.

10% is the same mistake again

180 records in 84 repetition groups; 57 groups cross projects — the mistake just moved house.

pkill -f: 7× in 6 projects

Killing a process by pattern killed the shell itself. Each time it became a line of prose. Now it's the pkill-f hook: the command is blocked on the spot, with the right way in the message.

"Template ausente" (missing template) 4×

The render failed because an earlier step didn't run. The kit's suggestion: architecture — the chain generates what's missing (modelos/validador-passo.sh).

# excerpt from the gardener report
- 196 arquivos em 190 projetos · 1880 registros
- reincidência: 10% (180 registros em 84 grupos de 2+)
1. pkill -f "<padrão>" no mesmo comando matou o próprio shell — 7× em 6 projetos · texto → gancho/validador
4. produce_blocks caiu (templates/pt/scene-01.html ausente) — 4× · texto → servidor/arquitetura
Roadmap

From here on

There's only one measure: weekly recurrence has to go down.

v1.0
Retro, rung, gardener, and hookThe four scripts, Claude Code hooks, weekly timer, SIL Loop R integration, 10 tests.
Next
Hooks for CodexThe same hook list applied to Codex sessions.
Later
Recurrence chartHistory of the weekly reports on a timeline, to see whether the guards are working.