Fredy Acuna
  • Posts
  • Projects
  • Tools
  • Contact
LinkedInXGitHubMedium

© 2026 Fredy Acuna

Back to posts
Organic Driven Development (ODD): How I Work With AI Agents Every Day

Organic Driven Development (ODD): How I Work With AI Agents Every Day

Fredy Acuna / October 30, 2026 / 10 min read

A Workflow, Not a Prompt

Most of my code today is written with an AI agent in the loop. The hard part was never getting the agent to write code. It was getting it to write the right code, to stop when a real decision was mine, and to leave a trail I could pick up the next morning.

The workflow I use for that is Organic Driven Development (ODD). I did not invent it. It ships with Gentle AI, the agent harness by Gentleman Programming that configures Claude Code (and other agents) with an orchestrator, persistent memory through Engram, skills and a review layer. ODD is the default workflow that orchestrator runs on every request.

This post is how ODD works from the point of view of someone who uses it every day, with real artifacts from my own repos: HitZero (a SaaS for sports clubs), bici.taxi (a ride request app) and NOVALYX (an AI music video project).


What You'll Learn

  • The seven steps ODD runs on every request
  • How it decides if a task is small or large (and why it never counts files)
  • What a feature document looks like and why it exists
  • When the agent delegates to subagents, and when it refuses to
  • Why every change ends with a Risk line

The Seven Steps

ODD runs the same protocol, in order, on every request. No one has to ask for "planning mode".

  1. Authorize. Does the request actually authorize a change? "Why is the sitemap empty?" is read-only. "Fix the sitemap" is not. Investigation, review and proposals never write files.
  2. Explore. Read the existing code and requirements first, proportionally to the request.
  3. Resolve uncertainty. Ask one focused question only when there is a real product decision open, then stop and wait. No questionnaires.
  4. Classify. Small or large (more on this below).
  5. Track. For large work, create a feature document before the first source write.
  6. Implement task by task. Test first when a deterministic test exists, check each task off only after its checks were observed.
  7. Close. Report what was verified, what was not, the next step, and a Risk line.

The first step is the one I underestimated. Before ODD, asking an agent "what do you think about this function?" could end with the function rewritten. Now a question gets an answer, and a change needs an explicit request.


Small vs Large: The "Resume From the Diff" Test

This is my favorite rule. A task is small when three things hold:

  1. Understood: the outcome is clear, what to change is known, and no product decision is open.
  2. Contained risk: it touches none of the high-risk areas (stored data, security, public contracts, concurrency, delivery and environment, or code no test would catch).
  3. Resumable from the diff: if the session stopped right now, someone could finish the work from the original request and git diff alone.

A task is large only when that third test fails: it spans several sessions, waits on something external, or the requirements are too long to survive a context compaction.

What the rule explicitly does not use is file count, line count, or how many tests are involved. A rename across 30 files is small. A three-line change to a billing cron that every free club depends on can be large. Size is about whether the work survives an interruption, not about how it looks in the file tree.

Small work stays inline: read, edit, see the test fail, fix, run the focused test and the suite once. No documents, no ceremony.


The Feature Document

Large work gets a markdown file at odd/tasks/<feature-name>.md, plus a copy in Engram so it survives a lost session. It has a fixed order:

  • A two or three line header: objective, branch, delivery strategy, test runner.
  • ## Specs: numbered requirements S1..Sn, quoting the user's exact words, error messages and examples. Never summarized.
  • ## Tasks: one line per task with its linked specs, route (inline or delegated), status and evidence.
  • ## Log: L1 is the original request verbatim; later corrections, decisions and verification results are appended.

Here is a trimmed excerpt from a real one in HitZero, for importing athletes from a spreadsheet:

# Athlete spreadsheet import (Excel/CSV + AI header mapping)

Objective: let an admin bulk-create athletes from a spreadsheet, with Cerebras suggesting the column mapping.
Branch: feat/athlete-spreadsheet-import. Delivery: ask-on-risk. Test runner: vitest (unit)

## Specs

- S4. Normalization is deterministic code, not AI: phone to +57 10 digits, dates to `YYYY-MM-DD` (not future), ...
- S8. Plan limit: ... reject the whole batch with `PLAN_LIMIT_REACHED` (409) if `active + batch > limit`, before inserting.

## Tasks

- [x] T1 (S2, S4-S6, S9): shared row validator and normalizer. Route: inline. RED: module missing; GREEN: 9/9, types suite 253/253, tsc + biome clean.
- [x] T2 (S7-S9, S13): `POST /organizations/{orgId}/athletes/import`. Route: inline. ... Risk: item 4 (advisory lock + batch limit).

## Log

- L4 (agent finding): ... OPEN DECISION: is phase 1 athletes-only with guardian contact stored as emergency contact (S10), or must guardian invites ship in the same release?
- L6 (user answer to L4): "Emergency contact only (Recommended)". Phase 1 is athletes only; T5 stays out of phase 1.
- L8 (agent decision): S3 narrowed to headers only. No sample rows (minors' names and birth dates) are sent to Cerebras.
- L11 (independent verifier): S1-S3 and S6-S13 PASS, S4 FAIL, S5 PARTIAL. Blockers: B1 a number in the birth-date column threw `RangeError` ...
- L12 (parent): one correction batch. RED types 3/13, dialog 1/7; GREEN ...

A few things in there are worth pointing out:

  • The open decision is in the log, not in the agent's head. When the agent hit a real product question (guardians: invite them now or later?), it wrote it down, asked me, and recorded my answer verbatim.
  • Evidence is concrete. "RED: module missing; GREEN: 9/9" is a fact somebody observed, not "tests pass".
  • The verifier found real bugs. A number typed into the birth-date column crashed the preview. That became one correction batch with its own RED and GREEN.

The document is also the handoff. When work is delegated, the subagent does not get a paraphrase. It gets a reference like Spec: odd/tasks/<feature>.md, T2, S3-S4, reads the document up to ## Log, and reports which S# it covered. That kills the "telephone game" where requirements degrade every time they are summarized.

Even this blog post started as one: the task that produced it lives in odd/tasks/blog-posts-from-recent-work.md in this portfolio repo, with each post as a numbered spec.


Test First, When It Means Something

ODD applies one test-first policy: when a runnable, deterministic test and a clear expected outcome exist, observe RED before implementing, then GREEN, then refactor with tests green.

It also says when not to. Passive documentation, a missing runner, or no meaningful RED gets an explicit exception in the log instead of a fake test. In bici.taxi there was no runner at all when dispatch automation started, so the first task added vitest, and the document says so:

## TDD
- Mode: on (source: global user config "Strict TDD Mode: enabled").
- Runner: none existed; adding `vitest` (`pnpm test` → `vitest run`).

## Progress / evidence
- T1 c3a58bb: RED observed (3 files failed, modules missing) -> GREEN 23 tests.
- T3 b1b5bd2: ... buildTripView privacy tests written after the code (characterization)
- Unverified: real WAHA sends, real DB accept race, browser run of /viaje.

I like that last line a lot. The agent is not allowed to claim what it did not see.


When It Delegates (And When It Doesn't)

Gentle AI runs a parent orchestrator that can spawn subagents. The rule is not "use agents for big things". Delegation needs a named reason:

  • Mapping: understanding the code needs more than one small batch of reads (roughly 3 calls, about 10k tokens) or more than about 5 sequential lookups. One read-only explorer maps it and returns a short handoff with path:line evidence.
  • Parallel writers: two or more independent units of behavior, with disjoint files, each worth several minutes of work. One writer per unit, launched together.
  • High-risk verification: a change whose Risk line names a high-risk item gets one independent verifier after its own checks.

Size alone, file count, or "this feels complex" never fire a delegation. Without a reason, the parent writes inline, following its document.

The why is context. The parent session is the one talking to me and holding the plan. If it reads every file and dumps every test log into its own context, it gets slow and forgetful exactly when the work gets long. Subagents compress: an explorer reads 40 files and returns 2k tokens; a verifier runs the suite and returns a verdict per spec. The parent stays thin enough to keep orchestrating.


Closing With a Risk Line

Every code change ends with one line:

Risk: none
Risk: item 4 (advisory lock + batch limit)

The items are the high-risk list: (1) stored data and irreversible effects, (2) security, (3) contracts others consume, (4) concurrency, (5) delivery and environment, (6) no test would catch a regression.

There is one check before writing Risk: none that has saved me more than once: does the diff change a shared helper, option or parser that other behavior also uses? If yes, that is item 3, even if the request only mentioned one screen.

The Risk line is what decides whether a change gets an independent verifier, so it is not decoration. It also tells me, at a glance, which commits deserve a careful read.


What I Like and What Costs Me

What I like:

  • I can stop in the middle of a feature and resume tomorrow from the document and memory, without re-explaining anything.
  • My exact words survive. When the agent says "S8 is done", I can read S8 and see what I actually asked for.
  • Honest evidence: failed, skipped and unverified checks are written down instead of disappearing.

What it costs:

  • Large work has overhead. Writing specs and keeping the log current takes tokens and time.
  • Classification can be wrong. Sometimes a "small" fix grows, and the agent has to stop and create the document mid-way.
  • It is opinionated. If you want an agent that just types code fast, this will feel slow.

For me the trade is worth it. The feature documents across HitZero, bici.taxi and NOVALYX are now the most useful history I have of why the code looks the way it does.


Resources

  • Gentle AI
  • Engram
  • How to Self-Host Engram Cloud on Dokploy

Subscribe to my newsletter

Get notified when I publish new posts.

We care about your data. Read our privacy policy.