<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Vanshaj Kakkar</title>
    <description>The latest articles on DEV Community by Vanshaj Kakkar (@vanshaj1999).</description>
    <link>https://dev.to/vanshaj1999</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F4227444%2Faf3084f7-7f55-43ee-8c3a-69f3e0bb925f.jpg</url>
      <title>DEV Community: Vanshaj Kakkar</title>
      <link>https://dev.to/vanshaj1999</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/vanshaj1999"/>
    <language>en</language>
    <item>
      <title>Crysto: how I run Claude, Codex and other AI models as one team. The models were the easy part.</title>
      <dc:creator>Vanshaj Kakkar</dc:creator>
      <pubDate>Thu, 05 Nov 2026 04:24:58 +0000</pubDate>
      <link>https://dev.to/vanshaj1999/crysto-how-i-run-claude-codex-and-other-ai-models-as-one-team-the-models-were-the-easy-part-3af4</link>
      <guid>https://dev.to/vanshaj1999/crysto-how-i-run-claude-codex-and-other-ai-models-as-one-team-the-models-were-the-easy-part-3af4</guid>
      <description>&lt;p&gt;Early on, two of my AI agents tried to use the same browser at the same time. The browser fell over. Neither of them had really done anything wrong. They had each followed their instructions to the letter. They just had no idea the other one was there.&lt;/p&gt;

&lt;p&gt;That was when I realised the hard part of running AI agents isn't the AI. Getting a model to write decent code is close to solved. Getting four of them to work on the same projects for weeks, without stepping on each other, redoing each other's work, or cheerfully telling me something was done when it wasn't, is where all my time has gone.&lt;/p&gt;

&lt;p&gt;I call the whole setup Crysto. It started as a way to keep my own projects organised, and grew into something I lean on for my professional work too, with the two sides kept completely separate. Here's how it works, and what broke along the way.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why I built it
&lt;/h2&gt;

&lt;p&gt;I'm an AI engineer, so I spend most of my day with these tools anyway. But my own projects were scattered: side projects, research, writing and the important things I needed to keep on top of, all half-done across different chat windows. Every new chat started from nothing, and I was the only one keeping track of where anything was up to.&lt;/p&gt;

&lt;h2&gt;
  
  
  Who's on the team
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fw44kkyhzv2z06g1mfotf.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fw44kkyhzv2z06g1mfotf.png" alt="The Crysto stack" width="800" height="577"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;The Crysto stack. Click through it at &lt;a href="https://vanshaj1999.github.io/crysto/" rel="noopener noreferrer"&gt;vanshaj1999.github.io/crysto&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Claude Code runs the show. It plans the work, writes briefs for the others, reviews everything they hand back, and decides what actually ships. I run it on two separate accounts, one for work and one personal, and a small shell hook switches between them depending on which folder I'm in.&lt;/p&gt;

&lt;p&gt;Codex gets the long jobs. Give it a clear brief and it will build a small project, or grind through a pile of browser forms, while I get on with something else.&lt;/p&gt;

&lt;p&gt;Smaller models, through a tool called OpenCode, handle the bounded fixes. I can hand the same task to five of them at once and keep whichever result is best.&lt;/p&gt;

&lt;p&gt;Claude on my phone connects through a small MCP server on Cloudflare Workers, with KV storage behind it. That gives the phone and laptop access to the same stored data without relying on a shared chat.&lt;/p&gt;

&lt;p&gt;The coding agents also run headless. These are the command shapes I use, with a model and brief supplied for each run:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;opencode run &lt;span class="nt"&gt;--format&lt;/span&gt; json &lt;span class="nt"&gt;-m&lt;/span&gt; &amp;lt;model&amp;gt; &lt;span class="s2"&gt;"&amp;lt;brief&amp;gt;"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;codex &lt;span class="nb"&gt;exec&lt;/span&gt; &lt;span class="nt"&gt;-s&lt;/span&gt; workspace-write &lt;span class="s2"&gt;"&amp;lt;brief&amp;gt;"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Each run gets its own copy of the repo. OpenCode runs one model per invocation; Codex works inside its workspace-write sandbox. Separate copies matter when I'm comparing results: otherwise a later model could inherit an earlier model's edits, and I'd have no clean way to tell who did what.&lt;/p&gt;

&lt;p&gt;The catch is that none of them share a conversation. Everything below comes from that.&lt;/p&gt;

&lt;h2&gt;
  
  
  Nobody remembers anything
&lt;/h2&gt;

&lt;p&gt;Codex can't see my Claude chats. Tomorrow's Claude session can't see today's. Every agent wakes up with amnesia.&lt;/p&gt;

&lt;p&gt;What fixed it was embarrassingly low-tech: files. Every project lives in a folder with a &lt;code&gt;STATUS.md&lt;/code&gt; that says where things are up to. Every session reads it first and updates it before it finishes. Longer-term memory is one fact per file with a one-line summary, and only a short index of those gets loaded each time. Each memory file has front matter for its name, description and type. The four types are user, feedback, project and reference. The index tells the agent what exists; it can read the relevant file when the task needs it.&lt;/p&gt;

&lt;p&gt;The part that surprised me was how much it helps to give every rule a reason. "Only one agent uses the browser at a time" is a rule. Add "because two agents on the same debugging port will crash each other" and an agent can work out the case I never wrote down, like a second browser tool on the same machine.&lt;/p&gt;

&lt;p&gt;It sounds almost too simple to write about. But it's the reason any agent, on any model, can pick up a project cold.&lt;/p&gt;

&lt;h2&gt;
  
  
  Who's doing what
&lt;/h2&gt;

&lt;p&gt;Back to the browser crash. The fix was one more file, &lt;code&gt;COORDINATION.md&lt;/code&gt;, which lives in the hub. Before an agent touches files or the browser, it writes down that it's taking the job:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# Website copy review, 4 November: CLAIMED BY CODEX
Owner: Codex. Claimed 4 Nov 10:05.
Done: 12 of 18 claims checked.
Evidence: drafts/about.md diff.
Next: check the last 6, then hand back to Claude.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F54wr49zujoq733acy9n8.gif" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F54wr49zujoq733acy9n8.gif" alt="A real terminal run of new-project.sh and make check" width="790" height="560"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;A real run: creating a project, then the 17 tests in make check&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The rules fit on an index card. Check the file before you start. If someone else has claimed a task, leave it and ask me. Only one agent on the browser. And nothing actually enforces any of it. There's no lock. It works because every agent's instructions tell it to respect the file, and so far they do.&lt;/p&gt;

&lt;p&gt;It earned its keep this week. A work session already had the browser, so my personal session switched to a different browser tool instead of grabbing it.&lt;/p&gt;
&lt;h2&gt;
  
  
  Tests that pass and still lie
&lt;/h2&gt;

&lt;p&gt;The whole setup depends on the smaller models building and Claude reviewing. That only works if the review actually catches things, so I tested it.&lt;/p&gt;

&lt;p&gt;The bug was pydynox issue #560. Its &lt;code&gt;MemoryBackend&lt;/code&gt; decorator wrapped an async function, but exited its context before the coroutine ran. That's a useful failure to test because returning a coroutine and executing it aren't the same event. The context has to cover the actual async execution.&lt;/p&gt;

&lt;p&gt;I gave it to 9 models, with tests I'd written beforehand and kept hidden from them. Eight passed those hidden tests; the fastest finished in 84 seconds. Nemotron 3.5 Lightning passed, but also deleted an existing test. If I'd only read the final test result, I'd have missed that change entirely.&lt;/p&gt;

&lt;p&gt;The refactor task was in awslabs/stickler, with a 4,091-test suite. Five models kept it green without editing a test. Flint 40B also ran &lt;code&gt;ruff --fix&lt;/code&gt; over 8 unrelated notebooks. Its diff touched 11 files, while the others touched 3. The extra changes weren't necessary for the task, even though the suite still passed.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Ffi0pwr3k20khxfmd19fq.jpg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Ffi0pwr3k20khxfmd19fq.jpg" alt="Glasses in front of screens of code" width="800" height="600"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;Photo by &lt;a href="https://unsplash.com/@ikukevk?utm_source=medium&amp;amp;utm_medium=referral" rel="noopener noreferrer"&gt;Kevin Ku&lt;/a&gt; on &lt;a href="https://unsplash.com/?utm_source=medium&amp;amp;utm_medium=referral" rel="noopener noreferrer"&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;So now Claude does three things with every change. It writes tests up front that the building agent never sees, runs them afterwards, and reads the whole diff. A green test run tells you the tests passed. That's all it tells you.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fx08tmc5lb8oppq8inog0.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fx08tmc5lb8oppq8inog0.png" alt="The build loop" width="800" height="575"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;The build loop. Interactive version at &lt;a href="https://vanshaj1999.github.io/crysto/" rel="noopener noreferrer"&gt;vanshaj1999.github.io/crysto&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  Everyone exaggerates a little
&lt;/h2&gt;

&lt;p&gt;When an agent finishes, it writes a handover: what it changed, the proof, what went wrong, and what it didn't get to test. The rule is that "done" means a command ran and the output is in the file. Plans and good intentions don't count.&lt;/p&gt;

&lt;p&gt;Even so, claims creep. When the smaller models built my retrieval benchmark, their handover was upfront that one feature, the Claude answer path, had never actually run. Their README still made it sound like part of the results. The review also found a threshold that had been tuned on the very questions it was being scored on. Both are fixed now, and the README says so.&lt;/p&gt;

&lt;p&gt;That project, rag-eval-lab, uses 745 Python PEPs split into 17,933 chunks, stored in PostgreSQL with pgvector and an HNSW index. Vector search scored recall@1 of 0.70 against 0.36 for full-text search. Hybrid search with reciprocal rank fusion, or RRF, scored 0.66. Here, recall@1 asks whether the expected result came first. Adding another retrieval method didn't automatically improve that score.&lt;/p&gt;

&lt;p&gt;Those numbers describe this benchmark. They don't prove that vector search wins on every corpus, and they say nothing about an answer path that never ran. That's the distinction I need the handover and README to preserve.&lt;/p&gt;

&lt;p&gt;Claude isn't immune either. While drafting my last article, it wrote that my fixes had been sent to the project maintainers. They hadn't, not yet. We only caught it because the check went back to the actual pull requests.&lt;/p&gt;

&lt;p&gt;I've stopped hoping for a model that never overstates things. What I want is a check that doesn't take its word for it.&lt;/p&gt;
&lt;h2&gt;
  
  
  The rules that weren't about AI
&lt;/h2&gt;

&lt;p&gt;Two of my most expensive lessons had nothing to do with models.&lt;/p&gt;

&lt;p&gt;My work and personal Claude accounts are kept apart by separate config folders. But both read the same keychain entry, so logging out of one to switch logs out every session on the machine. Now the shell hook handles the switch and prints a line every time it happens, and I never log out.&lt;/p&gt;

&lt;p&gt;The account folders use &lt;code&gt;CLAUDE_CONFIG_DIR&lt;/code&gt; for Claude and &lt;code&gt;GH_CONFIG_DIR&lt;/code&gt; for the GitHub CLI. The hook checks the current directory and selects the matching config. These lines come straight from &lt;code&gt;account-switch.zsh&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;autoload &lt;span class="nt"&gt;-Uz&lt;/span&gt; add-zsh-hook
add-zsh-hook chpwd _crysto_claude_account
add-zsh-hook chpwd _crysto_gh_account
_crysto_claude_account
_crysto_gh_account
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;chpwd&lt;/code&gt; hook runs the account functions when the directory changes. The final calls also select the accounts when the shell starts. Separate config folders solve the selection problem; they don't remove the shared keychain behaviour.&lt;/p&gt;

&lt;p&gt;Then the voice assistant. My first design for "Hey Crysto" was a small Cloudflare Worker that called Claude with my subscription login. Anthropic's terms don't allow that: a subscription is for their own apps, and anything running on your own server needs a paid API key. So I split the problem. The part that matters most, Crysto's connection to my data, is built and running: a personal MCP gateway on Cloudflare Workers with OAuth and PKCE, read-only by default, where any write needs my explicit consent. Codex signs in to it and reads my mail, calendar and project data through one endpoint. For voice, I use the Claude app and Siri today. The always-on brain, a model that runs by itself and also runs the lights at home, is designed and waiting. The main thing stopping me is the API bill: I'm not ready to pay per request for a side project yet. Next time I'll read the terms before I draw the diagram.&lt;/p&gt;

&lt;h2&gt;
  
  
  Under the hood
&lt;/h2&gt;

&lt;p&gt;Crysto is mostly Markdown files and shell commands. Claude Code coordinates the work, while headless OpenCode and Codex runs produce changes for review. Project status and task claims live beside the work, so the next session can read them with ordinary file tools.&lt;/p&gt;

&lt;p&gt;The public repo includes a bash script to create a project, plus 17 tests, shellcheck and GitHub Actions CI. The Cloudflare Workers MCP server uses KV for stored state. PostgreSQL, pgvector and HNSW belong to the retrieval benchmark, rather than the coordination protocol. I don't need a database query to find out who owns the browser.&lt;/p&gt;

&lt;h2&gt;
  
  
  What it costs
&lt;/h2&gt;

&lt;p&gt;Not much beyond the subscriptions I already had. Money isn't really the limit. Attention is, so the whole thing is set up to spend it on briefs and reviews rather than on typing code.&lt;/p&gt;

&lt;h2&gt;
  
  
  If you want to try this
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Keep shared state in files, not in chats.&lt;/li&gt;
&lt;li&gt;Have agents claim work before they start, and give the browser one driver.&lt;/li&gt;
&lt;li&gt;Write your own tests and keep them away from the agent writing the code.&lt;/li&gt;
&lt;li&gt;Read every diff, even when it's green.&lt;/li&gt;
&lt;li&gt;Ask for proof, then check it.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F72jc4r19t3ki2ew94q10.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F72jc4r19t3ki2ew94q10.png" alt="The crysto repo on GitHub" width="800" height="500"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;The crysto repo on GitHub&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The design, the coordination rules, the templates and a script that sets up a new project are all open source at &lt;a href="https://github.com/vanshaj1999/crysto" rel="noopener noreferrer"&gt;github.com/vanshaj1999/crysto&lt;/a&gt;. My memory, notes and data aren't, and that's on purpose.&lt;/p&gt;

&lt;p&gt;Want to click through it yourself? The interactive diagrams are at &lt;a href="https://vanshaj1999.github.io/crysto/" rel="noopener noreferrer"&gt;vanshaj1999.github.io/crysto&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Cover photo by &lt;a href="https://unsplash.com/@jstrippa?utm_source=medium&amp;amp;utm_medium=referral" rel="noopener noreferrer"&gt;James Harrison&lt;/a&gt; on &lt;a href="https://unsplash.com/?utm_source=medium&amp;amp;utm_medium=referral" rel="noopener noreferrer"&gt;Unsplash&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>ai</category>
      <category>llm</category>
      <category>programming</category>
      <category>opensource</category>
    </item>
    <item>
      <title>I gave 9 free AI coding models the same real bug. Here is what happened.</title>
      <dc:creator>Vanshaj Kakkar</dc:creator>
      <pubDate>Thu, 05 Nov 2026 02:10:55 +0000</pubDate>
      <link>https://dev.to/vanshaj1999/i-gave-9-free-ai-coding-models-the-same-real-bug-here-is-what-happened-pk3</link>
      <guid>https://dev.to/vanshaj1999/i-gave-9-free-ai-coding-models-the-same-real-bug-here-is-what-happened-pk3</guid>
      <description>&lt;p&gt;Everyone has an opinion about which AI coding model is best. Most of those opinions come from toy prompts or leaderboards. I wanted to see what happens on a real bug in a real open source repo, with tests the models cannot see.&lt;/p&gt;

&lt;p&gt;So I gave the same bug to 9 free models at the same time and graded every result the same way.&lt;/p&gt;

&lt;h2&gt;
  
  
  The bug
&lt;/h2&gt;

&lt;p&gt;The repo is &lt;a href="https://github.com/ferrumio/pydynox" rel="noopener noreferrer"&gt;pydynox&lt;/a&gt;, a Python DynamoDB library. &lt;a href="https://github.com/ferrumio/pydynox/issues/560" rel="noopener noreferrer"&gt;Issue #560&lt;/a&gt;: the &lt;code&gt;MemoryBackend&lt;/code&gt; test helper works as a decorator, but on an &lt;code&gt;async&lt;/code&gt; function it exits its context before the coroutine runs. So the test runs against the real backend instead of the in-memory one. It is a small, realistic bug: easy to describe, easy to get subtly wrong.&lt;/p&gt;

&lt;h2&gt;
  
  
  The setup
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Agent:&lt;/strong&gt; &lt;a href="https://opencode.ai" rel="noopener noreferrer"&gt;OpenCode&lt;/a&gt;, run headless with &lt;code&gt;opencode run&lt;/code&gt;, one model per run.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Models:&lt;/strong&gt; 9 free models from the OpenCode catalogue, all started at the same time, each in its own copy of the repo.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Brief:&lt;/strong&gt; identical for all 9. Read the issue and the repo's own AI guidelines, make the smallest correct change, add tests that fail without the fix, do not commit.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Hidden tests:&lt;/strong&gt; before the run I wrote my own tests for the bug. They fail twice on the original code. The models never saw them. After each run I added them and ran the suite.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Grading:&lt;/strong&gt; hidden tests pass, the model's own tests pass, and a diff review for anything outside the task.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  The results
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fhoax600lv2newhqs17d6.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fhoax600lv2newhqs17d6.png" alt="Time to a finished fix for each of the 9 free models. Big Pickle and Pulse Alpha were fastest at 84 seconds. Crouton Alpha gave up after 10 seconds." width="800" height="464"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;8 of 9 models produced a fix that passed the hidden tests. Big Pickle and Pulse Alpha both finished in 84 seconds. DeepSeek V4.1 Flash took 2 minutes 11 seconds. The rest took between 4 and 6.5 minutes. Total model cost: $0.&lt;/p&gt;

&lt;p&gt;Speed was not the story, though. The failures were.&lt;/p&gt;

&lt;h2&gt;
  
  
  How the models went wrong
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Crouton Alpha gave up after 10 seconds.&lt;/strong&gt; No fix, no tests. That is the easy failure, because you notice it.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Nemotron 3.5 Lightning passed, but deleted an existing test.&lt;/strong&gt; Its fix was correct and the hidden tests passed. It also removed a test that was already in the file. A green test run would never tell you that. Only reading the diff does.&lt;/p&gt;

&lt;p&gt;That is the failure I worry about most with coding agents. Not "it did not work", but "it worked, and quietly changed something you did not ask for".&lt;/p&gt;

&lt;h2&gt;
  
  
  A second test: a refactor in a 4,091-test suite
&lt;/h2&gt;

&lt;p&gt;One bug is a small sample, so I ran a different kind of task. &lt;a href="https://github.com/awslabs/stickler/issues/517" rel="noopener noreferrer"&gt;awslabs/stickler #517&lt;/a&gt; asks for two classes to share their state handling through one private base class. The repo has 4,091 tests, so a refactor has nowhere to hide.&lt;/p&gt;

&lt;p&gt;I gave it to 5 free models. All 5 kept the full suite green without editing a single test. Big Pickle was fastest again, at 4 minutes 34 seconds.&lt;/p&gt;

&lt;p&gt;One model, Flint 40B, also ran &lt;code&gt;ruff --fix&lt;/code&gt; across 8 Jupyter notebooks that had nothing to do with the task. Its diff touched 11 files. The others touched 3. Again: the tests passed, and the change was still not one you would merge.&lt;/p&gt;

&lt;h2&gt;
  
  
  Free versus paid
&lt;/h2&gt;

&lt;p&gt;For comparison I gave the first bug to three paid models: GLM 5.3 Flash, Kimi K3.1 Pro and Qwen 3.8 Max. All three fixed it, with tests that fail without the fix. They were not faster than the best free models.&lt;/p&gt;

&lt;p&gt;There was one real quality difference. Only Qwen detected coroutine functions with &lt;code&gt;inspect.iscoroutinefunction&lt;/code&gt;. The other two used &lt;code&gt;asyncio.iscoroutinefunction&lt;/code&gt;, which is deprecated from Python 3.14. Both pass today's tests. Only one is still right next year. No test suite catches that. A reviewer who knows the language does.&lt;/p&gt;

&lt;h2&gt;
  
  
  What I took from it
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;For small, well-described bugs, free models are good enough.&lt;/strong&gt; 8 of 9 got it right. The gap between free and paid was smaller than I expected.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Write your own tests, and keep them hidden.&lt;/strong&gt; A model grading itself with its own tests tells you little. Tests it never saw tell you a lot.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Read every diff.&lt;/strong&gt; The two most worrying results both passed their tests. One deleted a test, one reformatted files outside the task.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;The human work moved, it did not disappear.&lt;/strong&gt; Choosing the issue, writing the brief and the hidden tests, and reviewing the diff took longer than the fixes did. That is the job now.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;One more lesson from the open source side: by the time I had a fix for one issue, a human contributor had claimed it 6 minutes earlier. Check the issue again right before you post.&lt;/p&gt;

&lt;p&gt;I now use the same workflow for real contributions. Each pull request is reviewed and tested by me and labelled as AI-assisted, which is what the maintainers ask for.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Caveats: one run per model, on two tasks. Free models in this catalogue change often, so treat the names as a snapshot from November 2026, not a ranking.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>ai</category>
      <category>opensource</category>
      <category>python</category>
      <category>llm</category>
    </item>
  </channel>
</rss>
