Quickstart · Models · Benchmarks · Guides · Research report
Decisions that fit on a chip.
Sparrow Decider is a family of decision models small enough to live inside your agent, your robot or your microcontroller. They answer three kinds of question about a state:
- yes / no (
noul) - pick one (
choice) - rate on a scale (
score)
They return calibrated probabilities in the same shapes as Strands Decider. They do it in about a millisecond on one CPU core, or microseconds on a chip, with no GPU, no network and no model server.
state battery: 6% front_obstacle_m: 7.0 path: clear
question What should the robot do next? continue | slow | stop | dock | replan
answer dock 9.3 µs on a $10 ESP32-S3 (sparrow-pico)
Unofficial community project. Not an AWS or Strands product.
Quickstart
pip install sparrow-decider # numpy only, 3.3 MB installed, two models bundled
from sparrow_decider import Decider
d = Decider.load() # sparrow-nano-general-v1.1
d.ask("User: I was charged twice for order 1182, I want my money back", {
"tool": {"type": "choice", "instructions": "Which tool fits this request?",
"criteria": {"flights": "search and book flights", "refunds": "refund a payment",
"weather": "forecasts for a city", "calendar": "create or move meetings"}},
"upset": {"type": "noul", "instructions": "Is the user upset?"},
"urgency": {"type": "score", "instructions": "How urgent is this?", "criteria": ["can wait", "today", "now"]},
}) # tool -> refunds (p = 0.98)
sparrow-decider ask "operator: grab that blue bottle" --choice "Which skill?" \
-o "pick=pick up an object" -o "navigate=move somewhere" -o "speak=answer the person"
sparrow-decider serve --port 8000 # POST /v1/systemone
| Guide | |
|---|---|
| Python | API, models, CLI, HTTP server |
| Agents | routing and gating inside an agent, including as a Strands tool |
| ESP32-S3 | text decisions on a microcontroller in 3.5-7.6 ms, plus QEMU if you have no board |
| sparrow-pico | compile a decision for your device into a few KB of C |
| C library | the runtime anywhere a C99 compiler runs |
The family
| Tier | Model | Size | Input | Runs on | Time / question |
|---|---|---|---|---|---|
| pico | compiled per device, e.g. sparrow-pico-rover-v1.1 |
~2 KB / question | numbers, flags, enums | any MCU | 0.18 µs · 9.3 µs on ESP32-S3 |
| nano | sparrow-nano-general-v1.1 |
2.2 MB | text | ESP32-S3, Pi, laptop | 0.06 ms · 3.8 ms on ESP32-S3 |
| nano | sparrow-nano-robot-v1.2 |
1.11 MB | text with sensor readings | ESP32-S3, Pi, laptop | 0.08 ms · 3.5 ms on ESP32-S3 |
| micro | sparrow-micro-general-v1.1 |
7.6 MB | text | Pi, laptop, 16 MB ESP32-S3 | 0.22 ms |
| tiny | sparrow-tiny-general-v1.0 |
17.9 MB | text | Pi, laptop | 23 ms |
| small | sparrow-small-general-v1.0 |
47 MB | text | Pi, laptop, Jetson | 64 ms |
Times are p50 on one Apple M4 Pro core: the C runtime for pico, nano and micro, numpy for tiny and small. The nanos are bundled with the Python package; the others are on the releases page. IDs follow NAMING.md.
pico or nano?
flowchart LR
Q{"Are the inputs sensor values,<br/>and the questions known at build time?"}
Q -- yes --> P["<b>sparrow-pico</b><br/>compile a spec into C<br/>~2 KB · 9.3 µs on ESP32-S3"]
Q -- "no: text, or questions change" --> R{"Do decisions hinge on<br/>numbers like battery: 6%?"}
R -- yes --> NR["<b>sparrow-nano-robot</b><br/>1.11 MB · 3.5 ms"]
R -- no --> NG["<b>sparrow-nano-general</b><br/>2.2 MB · 3.8 ms"]
NG -. "need more breadth,<br/>and have the RAM" .-> M["micro · tiny · small"]
nano reads text and answers any question you pose at runtime. pico has no text and no vocabulary: you describe your device's sensors and questions in a spec, a full Strands Decider labels thousands of sampled states, and the compiler writes one tiny MLP per question as a C header. Many devices use both: pico in the control loop, nano for anything said or written.
Benchmarks
| Model | Size | RobotBench 55 robot decisions | MASSIVE domain / intent | JevBench 231 public tasks |
|---|---|---|---|---|
| Strands Decider 4B v22 (teacher) | 4B params | 46 | not run | 188 |
| Strands Decider 2B v1 (public) | 2B params | 40 | 0.86 / 0.87 | 180 |
| sparrow-nano-robot-v1.2 | 1.11 MB | 36 | 0.52 / 0.52 | 115 |
| sparrow-nano-general-v1.1 | 2.2 MB | 32 | 0.50 / 0.59 | 122 |
| sparrow-micro-general-v1.1 | 7.6 MB | 30 | 0.64 / 0.54 | 117 |
| sparrow-tiny-general-v1.0 | 17.9 MB | 20 | 0.37 / 0.59 | 123 |
| sparrow-small-general-v1.0 | 47 MB | 24 | 0.67 / 0.60 | 122 |
sparrow-pico, compiled from the public 2B for the rover spec and tested on 600 held-out states:
| Question | pico vs teacher | Teacher vs the spec's rules | pico vs the spec's rules |
|---|---|---|---|
| next action (5 options) | 97.7% | 94.2% | 94.0% |
| needs charging (yes/no) | 99.8% | 99.0% | 99.2% |
On a real ESP32-S3
Measured on an ESP32-S3 (240 MHz, 16 MB flash, 8 MB PSRAM) with bench/esp32/run.py. There are 155
decisions (RobotBench and 100 MASSIVE intent cases), and every on-chip answer was compared with the
host runtime.
| Model | p50 per decision | First on-chip build | Matches host |
|---|---|---|---|
| sparrow-pico-rover-v1.1 | 9.3 µs | 42.9 µs | 256/256 |
| sparrow-nano-general-v1.1 | 3.8 ms | 9.6 ms | 152/155 |
| sparrow-nano-robot-v1.2 | 3.5 ms | 73.5 ms | 150/155 |
These speedups come from the configuration, not new hardware:
- options scored in batches
- int8 dot products on the S3 vector unit (ESP-NN kernel)
- a 64 KB data cache
- the model blob in PSRAM, with the MLP weights in internal RAM
The few mismatches against the host are int8 rounding near ties.
What this means
- Good at: fast, local decisions in a known domain. On navigation from sensor readings, the 1.11 MB nano-robot gets 8/10 calls right where the public 2B gets 3/10.
- Weak at: open-ended language it never trained on. On MASSIVE, every Sparrow model is well behind the 2B.
- Weak at: yes/no judgement. On JevBench's yes/no tasks, every tier is near chance. Use a full decider or an LLM for those.
How it works
flowchart LR
T["Strands Decider 4B<br/>(teacher)"] -- "soft labels on<br/>~430k decisions" --> S["static tiers<br/>micro · nano"]
T --> E["encoder tiers<br/>tiny · small"]
T2["Strands Decider 2B<br/>(public)"] -- "labels on sampled<br/>device states" --> PC["sparrow-pico<br/>compiler"]
S --> PY["numpy runtime"]
S --> C["C99 runtime<br/>SPB1 blob in flash"]
E --> PY
PC --> H["C header<br/>one MLP per question"]
- Static tiers (micro, nano):
- Each segment (state, question, option) is mean-pooled from an int8 embedding table.
- An MLP scores every option against the state and the question.
- nano prunes the vocabulary to 8k-16k pieces and projects the vectors to 128-d.
nano-robotadds key-value number pooling:battery: 6%becomes the battery's vector times a learned function of 6. Across seeds this is worth 6-8 RobotBench points.
- Encoder tiers (tiny, small): Ettin encoders with a pointer head over the options.
- pico: distillation into a per-question MLP over the raw feature vector.
Methods, ablations and limits are in the research report.
Repository
python/sparrow_decider numpy runtime, CLI, bundled nano models
c/sparrow C99 runtime (ESP-IDF component) c/tools packer, ESP-IDF wrapper
c/examples ESP32-S3 example, pico specs c/tests C-vs-Python parity
training/ every training, distillation, calibration and compile script
bench/ RobotBench, MASSIVE, JevBench runners, results, RESULTS.md
research/REPORT.md methods, ablations, findings
docs/ quickstarts, model card
site/www the website (static, generated from site/facts.json by site/www/_build/build.py)
site/brand logo, colours (tokens.css), brand guide site/marketing launch post, press kit
Credits
- Code: Apache-2.0.
- Base weights: micro and nano are initialised from potion-base-8M (MinishLab, MIT). tiny and small are initialised from the Ettin encoders (Johns Hopkins CLSP, MIT).
- Teachers and prompt format: Strands Decider (Apache-2.0).
- Evaluation only: JevBench (MIT) and Amazon MASSIVE (CC BY 4.0).
See NOTICE and docs/models.md. To cite, use CITATION.cff.
Contact
- Email: vivek@sparrowdecider.com
- Questions and results: GitHub Discussions
- Bugs: GitHub Issues
Metadata
Release files for sparrow-decider 0.2.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | |
|---|---|---|---|---|
| sparrow_decider-0.2.0.tar.gz | 3.3 MB | With provenance | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| sparrow_decider-0.2.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 6.7 MB
Release files / sparrow_decider-0.2.0.tar.gz
| Download URL | sparrow_decider-0.2.0.tar.gz |
|---|---|
| Size | 3.3 MB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
35682b6d8481b2482cb8c4ba2d592e1340def4898ed633cb9953c7490c0acff6
|
|
BLAKE2b-256 checksum How to use checksums |
f53c19bed27fe778a678e371b9793d28246d438d2c592c350a84cf825d71b56a
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.16
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 23, 2026.
Transparency logRelease files / sparrow_decider-0.2.0-py3-none-any.whl
| Download URL | sparrow_decider-0.2.0-py3-none-any.whl |
|---|---|
| Size | 3.3 MB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
9f73fd8f29f8583526c59bd877c15eb77131ec7af0c7ec2384034fdabc7ebe8b
|
|
BLAKE2b-256 checksum How to use checksums |
8ca9fce563d8925ea02b75ad8c079226686c252438a3cda1bc816c9eb558aaa3
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.16
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 23, 2026.
Transparency logSecurity for sparrow-decider 0.2.0
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
Full provenance
All 2 files in this release have been uploaded with provenance metadata.
Attestation for sparrow_decider-0.2.0.tar.gz
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 23, 2026.
Transparency logA note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.