AI agents · OpenClaw · self-hosting · automation

Quick Answer

What Is CUA-S1-FORMS? Cua's 706K-Param System 1 Model

Published:

The short version

CUA-S1-FORMS is what happens when you stop asking a frontier model to decide whether the “Phone number” field should get the phone number. Cua founder Francesco Bonacci open-sourced it on September 17, 2026: a 706,048-parameter, 2.8 MB, MIT-licensed model that makes exactly that class of decision in one forward pass, at 99.95% top-1 on its synthetic test and 100% on real forms, and that runs in a browser tab.

It matters less as a form filler than as a pattern: the first checkpoint in a planned family of small “System 1” models for bounded interface decisions inside computer-use agents, sitting beneath a large model that does the planning. Cua’s frame borrows from Kahneman — fast, intuitive System 1 for recurring narrow choices; slow, deliberate System 2 (the LLM) for everything else.

Verified September 20, 2026 against the Hugging Face model card and the trycua/cua repository.

How it works

AspectDetail
TaskGiven one actionable form element and the entities extracted from a source document, decide: fill with entity i, CHECK, CLICK or SKIP
Input (context)Up to 224 bytes: TASK …, FORM <title>, ELEMENT Edit "Phone number" value=""
Input (options)One per document entity (e.g. fill Tel: (503) 555-0142, fill DOB: 03/14/1987) plus check, click, skip, each ≤ 96 bytes
OutputOne probability per live option, softmax over the option count
ArchitectureByte-level embedding → 2-layer Transformer encoder (width 128, 4 heads) over context and, separately, over each option; a Jev-style attention head turns each option into a query against the context, and a shared dot product yields one logit per option
Size706,048 trainable parameters; 2.8 MB checkpoint (state dict + config + training history + best validation metrics)
What it does not doGenerate new text, read screenshots, decide execution order
ExecutionEvery actionable element is scored independently and in parallel in one batch; downstream code orders fills → checkboxes → the single submit click and sends set_value/click to Cua Driver

This is the same input/output contract as TypeSafe’s Jev, the hosted “System One” model that introduced the pattern. Cua’s contribution is an open, tiny, locally trained equivalent that beats the hosted API on its own task.

Training

  • 10,000 synthetic episodes from cua_s1/synth.py: a random form of 2–16 fields drawn from a 55-concept catalogue with form-label/document-label synonyms; a random person; a random document with distractor entities and forced look-alike confuser pairs (email vs street, phone vs emergency-contact phone, state vs university); random window-title suffixes and 20% title dropout.
  • Splits are disjoint by exact form field signature — no test form’s field set appears in training.
  • AdamW, cosine schedule with warmup, 6 epochs, batch size 128, cross-entropy over the live option count.

Results

EvaluationTop-1Note
Synthetic test (form-disjoint, ~15K decisions)99.95%Hard confuser pairs forced in
Real demo eval (3 real forms + 3 real PDFs, 196 decisions)100%Nothing synthetic
Shuffled-context control37%Confirms it reads the element, not option statistics
vs hosted Jev (jev-latest, zero fine-tuning, same task)99.7% vs 83.6%Jev: 96% on judgment decisions (fill/check/click), 74% on recognising an already-filled field as a no-op — a convention this model was trained on and Jev was not

Read the last row carefully: the head-to-head is on Cua’s task definition, and the “already filled → skip” convention is one Jev never saw. The fair claim is that a purpose-trained 700K-parameter model beats a general hosted System-1 API on the exact task it was trained for — which is the point of the pattern, not a knock on Jev.

How to use it

from pathlib import Path
from huggingface_hub import hf_hub_download
from cua_s1.model import load_checkpoint, select_device

repo = "cua-ai/cua-s1-forms"
weights = Path(hf_hub_download(repo, "cua-s1-forms.safetensors"))
hf_hub_download(repo, "cua-s1-forms.json", local_dir=weights.parent)  # sidecar next to the weights
# validates format, version and SHA-256 tensor signature before returning
model, collator, config = load_checkpoint(weights, select_device("auto"))

cua_s1/planner.py in the repository has the full snapshot → score → order → execute loop against a live Cua Driver session.

Notes from the model card:

  • The checkpoint format is safetensors + JSON sidecar (architecture config, a SHA-256 signature over the tensors, metadata). cua_s1’s loader rejects pickled .pt/.pth files by design — arbitrary pickle is a code-execution risk for a public checkpoint. A .pt is kept only for people calling torch.load(..., weights_only=False) directly; both encode identical weights.
  • The live Cua Driver integration, synthetic data generator, training and eval code live in libs/cua-s1 of the trycua/cua repository. Cua itself is the open-source framework that gives agents full control of macOS, Linux and Windows desktops.
  • A community ONNX conversion runs the model in the browser through ONNX Runtime Web, WebAssembly or WebGPU — no server inference at all.

When to use a System 1 model instead of the LLM

Use CUA-S1-FORMS (or train your own on the released code) when a decision is:

  1. Recurring and bounded — a fixed set of actions per element;
  2. Too variable for a script — labels, synonyms and layouts change;
  3. Latency- or cost-sensitive — a 2.8 MB model scores every field of a form in one batch in milliseconds, versus one LLM call per field at frontier prices;
  4. Private — the document entities never leave the machine.

Keep the LLM for extracting the entities from the source document in the first place, for deciding what the task is, and for anything requiring generated text. The stack Cua is pointing at is LLM for System 2, a shelf of tiny specialists for System 1, and CUA-S1-FORMS is specialist number one. For where this fits among full computer-use agents, see best computer-use AI agents 2026 and how to deploy a computer-use agent safely.

Sources