Anton Taranovskyi Switzerland · --:-- · index

note · no. 012

A small MLX model can turn a sentence into a flow

17 May 2026 · 6 min read

I've been turning over an idea for a while: if a flow is just structured JSON (triggers, modules, connections, parameters), then generating one from a natural-language sentence is exactly the kind of task a small model can do well, given the right examples.

Big foundation models already do this with prompting; that's not the question. The question is whether a small, locally-runnable, fine-tuned model can do it better than a generic large model on a specific flow grammar, and fast enough to feel instant inside an authoring tool. Apple's MLX framework is the obvious place to try this on a Mac, so this post is the plan, written down before any runs. I'll come back with numbers.

(Why MLX, since people will ask: llama.cpp is great for inference but less ergonomic for fine-tuning, PyTorch on Apple silicon works but runs slower and rougher, and cloud GPUs defeat the privacy point. MLX keeps fine-tuning and inference on the same machine with the least friction. That's the whole rationale.)

If you're not on the engineering side: this is how flow authoring stops being a UI exercise and becomes a sentence, the way you stopped writing formulas to filter a spreadsheet and started describing the filter. A small local model is what could make that feel instant, and private enough to actually use.

Why fine-tuned and small, not GPT-class prompting

Three reasons, in order of how much they actually matter:

  1. Latency. A 0.5B–3B model on MLX can plausibly hit sub-second generation for a typical flow on an M-series chip, and sub-second is the difference between a feature people use and a spinner they avoid.
  2. Determinism on a fixed schema. A model fine-tuned on one flow JSON schema should make fewer schema mistakes than a generic model that has seen a million unrelated schemas. The grammar gets baked into the weights.
  3. Privacy and runtime location. The flow being generated will usually end up touching private data. Generating it on the same hardware the flow will run on is much easier to govern than routing it through a third-party API. This fits how flow8 is positioned generally (AI running where the data lives), so a local flow-generation model is the right shape for that worldview.

The target task

Input: a natural-language description of a business process. Output: valid flow-schema JSON (modules, parameters, connections, triggers).

A toy example:

INPUT:
"Every morning at 7am, pull yesterday's invoices from QuickBooks,
generate a one-page summary PDF, save it to S3, and email it to the
finance group."

EXPECTED OUTPUT:
{
  "trigger": {"type": "schedule", "cron": "0 7 * * *"},
  "modules": [
    {"id": "qb_fetch", "type": "quickbooks.invoices.list",
     "params": {"date": "yesterday"}},
    {"id": "summarize", "type": "ai.summarize",
     "params": {"format": "one-page", "input": "$qb_fetch.items"}},
    {"id": "pdf", "type": "pdf.generate",
     "params": {"content": "$summarize.text"}},
    {"id": "s3", "type": "aws.s3.upload",
     "params": {"bucket": "fin-reports", "body": "$pdf.bytes"}},
    {"id": "email", "type": "smtp.send",
     "params": {"to": "[email protected]",
                "attachments": ["$pdf.bytes"]}}
  ],
  "edges": [
    ["qb_fetch", "summarize"], ["summarize", "pdf"],
    ["pdf", "s3"], ["pdf", "email"]
  ]
}

A small model trained on a few thousand of these should learn the structure cold. That's the hypothesis, anyway.

Candidate base models

The shortlist for an initial sweep, all available in MLX-compatible format:

All small enough to fit comfortably on an M-series laptop, all supported by mlx-lm.

Training plan

Dataset.

Method.

Validation.

Benchmark plan

Being honest about what hasn't been run yet: everything below is a placeholder until it isn't.

Hardware. M3 Max, 64 GB unified memory (later an M4 Pro for comparison).

Compared systems.

Targets per system.

Metric Target
JSON parseable ≥ 99%
Schema-valid ≥ 97%
Module-name valid 100%
Functional equivalence (held-out test) ≥ 90%
p50 latency (single flow gen) ≤ 500 ms local; ≤ 1.5 s API
p95 latency ≤ 1.2 s local
Cost per 1k generations < $0.05 local; tracked for API

Results table, to be filled in.

Model Params Method JSON valid Schema valid Functional eq. p50 latency p95 latency
Qwen 2.5 0.5B LoRA FT TBD TBD TBD TBD TBD
Qwen 2.5 1.5B LoRA FT TBD TBD TBD TBD TBD
Qwen 2.5 3B LoRA FT TBD TBD TBD TBD TBD
Llama 3.2 1B LoRA FT TBD TBD TBD TBD TBD
Llama 3.2 3B LoRA FT TBD TBD TBD TBD TBD
Phi-3.5 mini 3.8B LoRA FT TBD TBD TBD TBD TBD
GPT-4o n/a zero-shot TBD TBD TBD TBD TBD
Claude Sonnet n/a zero-shot TBD TBD TBD TBD TBD

What I expect (written down now, so the follow-up has to be honest):

How this lands in a product

If the numbers come out the way I expect, the path is fairly clean: ship the fine-tuned model as an optional flow-authoring assistant that runs locally next to the execution layer. For customers running the platform on their own infrastructure (the default), the same model runs on the same box: no cloud round-trip, no egress. Every new module in the catalog becomes a new "verb" the model can compose with. And for enterprises, the approach repeats per customer: fine-tune on their own flow history, so the assistant learns their conventions.

The bigger point: fine-tuned small models are the right shape for narrow, structured, frequent tasks like this one. The reflex to reach for the biggest available model is usually wrong when the problem rewards specialization.

Numbers in a follow-up. And if they come out worse than the expectations above, I'll say so plainly. If you've fine-tuned small models on MLX for structured output, curious what you saw, especially on latency!