Maximus

An LLM harness for contest ML, with a human on the train gate.

Python · CLI + MCP · gated train · Code on GitHub

The problem

Contest work with a coding agent usually degrades into the same mess: you paste logs into chat, the model suggests a tweak, and then either you babysit every train yourself or you let it fire runs unsupervised. I have done both. One wastes my attention; the other burns compute I meant to approve. I wanted a fixed loop where the agent does the grunt work and I still own when training happens.

Why I built it

Day to day, I wanted the agent to iterate on contest models without me pasting logs by hand, and without unsupervised compute burn.

The shape is fixed on purpose: propose → (you approve train) → eval → log → improve. The agent may request a train. I run it.

What I built

Maximus is a Python harness around competition folders. There is a CLI for train, eval, submit, status, log, and new, plus an MCP server so a Cursor agent can check status, read logs, make scoped edits, run eval, prep a local submission, and call request_train. Training stays on the human path: the agent writes a proposal; I run maximus train. MCP train is refused unless MAXIMUS_ALLOW_TRAIN=1, and I would rather keep that flag off.

Each successful eval appends to an experiment log (experiments/log.md and history.jsonl) under a strict metrics.json contract: a finite float metric, with soft or partial parses failing. A built-in toy_binary competition proves the loop on CPU (logistic regression, optional random forest, ROC-AUC). maximus new scaffolds another contest from a template. Real contests land later as new folders; the MVP does not upload to DrivenData or Kaggle, and it is not a GEMS solution or AutoML that trains in a loop on its own.

This is the primary MVP. Future changes are already in the works toward the final shape: enough of the loop to use and trust today, without pretending the product is finished.

Three decisions

These are the craft bets I would defend in a design review, each one about honesty, ownership, or maintainability.

1. You approve train; the agent only asks.

The agent inspects, makes one change, and calls request_train. That writes a pending proposal. I review it, then run maximus train myself. Human owns train and any cloud spend. I was counting on that gate holding when the agent gets eager, because the failure I care about is unsupervised compute I meant to approve. There are no autonomous multi-train loops on the default path.

2. MCP for grunt work, not for burning GPUs.

Status, logs, scoped file I/O, eval, submit prep, and diagnose are agent tools. Train is gated. Per competition, eval can be locked down too if it is expensive. The agent edits only allowed_edit_globs, one change per cycle. I was counting on scoped tools so the agent can improve without owning the spend. If train rides the same MCP path as status, the harness stops being something I trust with a GPU bill.

3. A hard metrics contract and a real log.

Eval has to leave artifacts/metrics.json with a numeric metric. Soft or partial parses fail. Successful runs land in the experiment log so the next propose step has evidence, not a chat scrollback I copied by hand. I was counting on a log a peer can read later. If the metric is fuzzy, the improve step is guessing.

Proof

You can follow the same loop the harness enforces: propose, approve train, eval, log, improve.

Maximus runtime architecture: propose to approve-train to eval to log to improve; MCP agent path with human CLI train gate
Runtime map. Fixed propose → (you approve train) → eval → log → improve. The agent path is MCP (status, scoped edits, request_train, eval). Train stays on the human CLI unless MAXIMUS_ALLOW_TRAIN=1. This diagram is the MVP shape; more is planned toward the final product.

From the public repo (README, docs/QUICK-START.md, docs/OPERATOR-GUIDE.md), the same story shows up in writing: the fixed propose → approve-train → eval → log → improve loop; MCP train refused unless MAXIMUS_ALLOW_TRAIN=1; the toy_binary CPU path for train, eval, and status; the experiment log plus strict metrics.json (metric as a finite float); and guardrails (one change per cycle, allowed edit globs, no contest-site upload in the MVP).

Why I built it this way

These boundaries are the same ones I hold elsewhere: clear ownership, real evidence, and something a technical peer can judge quickly.

If an agent is going to help on contest ML, it should not get unsupervised compute. It can propose, edit within the globs, eval, and log. I keep the train gate. That boundary is the product, and this MVP is where that product starts, with more shape still coming.