Notes from the work

One email when a tutorial or migration write-up goes live. Nothing else, and an unsubscribe link in every email.

LeanZero

Two people in Romania doing Atlassian migrations, Forge apps and practical AI work for teams that would rather talk to the person doing the job. Most of what we learn ends up on this site.

Services

  • Atlassian migrations
  • Atlassian FastShift
  • Atlassian maintenance
  • Forge app development
  • AI development consultation

Topics

  • Jira
  • Jira Service Management
  • Confluence
  • Bitbucket
  • Atlassian Forge
  • Cloud Migration
  • Local AI
  • AI Coding
  • Certifications
  • Atlassian Team
  • All topics

Company

  • Blog
  • Tutorials
  • Contact

Community

  • Join Discord
  • Support this site

© 2026 LeanZero. All rights reserved.

Privacy policyTerms of service24/7 SupportTrust centerSecurityDPALegal notice
  1. Home
  2. Topics
  3. Local Ai
Topic hub

Local AI

Local models on Apple Silicon, benchmarked rather than quoted.

Read the articlesAll topics

Running a capable model on your own hardware is mostly an argument about memory — how much you actually have, given that 96GB of marketing is 77.76 GiB you can spend, and what you are willing to give up to fit inside it. The benchmarks here are run, not quoted: MLX against llama.cpp on one machine and one set of weights, MXFP8 against Q8 on the same model, speculative decoding measured instead of assumed. Every number arrives with the command that produced it and the hardware it ran on, because a tokens-per-second figure missing either one is not a measurement. Results that contradicted what I expected are left in. Those tend to be the useful ones.

Read in order

Local Model Benchmarks

7 parts

Measured runs on real hardware: runtimes, quantisation formats and the memory ceiling nobody quotes.

  1. 1Part 1 — ArticleMLX vs GGUF on Apple Silicon: Benchmarking the Same Local Model Two Ways12 min
  2. 2Part 2 — ArticleMXFP8 vs Q8: 10x the weight error, 1% the perplexity14 min
  3. 3Part 3 — ArticleLing 3.0 Flash won't load on a Mac Studio. Qwen3-Coder-Next does, at 73 tok/s.18 min
  4. 4Part 4 — Articlellama.cpp vs MLX on Qwen3.6-27B: MTP is 1.04x here, not 1.85x15 min
  5. 5Part 5 — Article96 GB is 77.76 GiB: the real memory ceiling on an M3 Ultra13 min
  6. 6Part 6 — ArticleQwen3-Coder-Next + MXFP8: The 128GB Local LLM That Runs Predictably10 min
  7. 7Part 7 — ArticleThe best 4-bit format in MLX is the one its own converter sets up to lose9 min

Articles 20

Nanbeige4.3-33B benchmark attempt on a Mac Studio, plus Particle-1 vs DeepSeek V4.1 Flash
ArticleLocal AIAI Coding

Nanbeige4.3-33B benchmark attempt on a Mac Studio, plus Particle-1 vs DeepSeek V4.1 Flash

We tried to benchmark Nanbeige4.3-33B on a Mac Studio with MLX and it never started: our engine dropped its tool calls, and the 96 GB Studio served at most 75,925 tokens of the 322,851 our Gauntlet needs. We can give you measured speed and memory, a fit table by Mac size, and Particle-1 measured against two DeepSeek V4.1 Flash snapshots.

Nov 6, 202624 min read
Qwen3.8-Flash-Next on a Mac Studio vs OpenRouter: what it took to reach 0.6932
ArticleLocal AIAI Coding

Qwen3.8-Flash-Next on a Mac Studio vs OpenRouter: what it took to reach 0.6932

Our own 4-bit DWQ build of the official Qwen3.8-Flash-Next weights ran on one M5 Max Mac Studio in our MLX engine and scored 0.6932 on our Gauntlet sb-7.2 coding benchmark. Qwen3.8 Flash on OpenRouter has 0.6846 on the same board, and I explain why that comparison isn't settled. This is what we built to get there, with the numbers, and what went wrong on the way.

Nov 4, 202620 min read
I ran MiMo V2.6 Flash local on two Mac Studios over Thunderbolt 5 RDMA
ArticleLocal AI

I ran MiMo V2.6 Flash local on two Mac Studios over Thunderbolt 5 RDMA

We split Xiaomi's MiMo-V2.6-Flash across two Mac Studios over Thunderbolt 5 RDMA, with vision and a 256k context, and ran our agentic coding benchmark on it. It scored 0.6605 against 0.7909 for the same model in Xiaomi's cloud. Before the 3D ceiling it earned 0.8309 to the cloud's 0.838. I go through where the rest went, and the bugs we hit splitting one model over two machines.

Oct 29, 202615 min read
How we made Elzi, our unpaid voxel AI YouTube narrator, on a local TTS model
ArticleLocal AISentinel Vault

How we made Elzi, our unpaid voxel AI YouTube narrator, on a local TTS model

Elzi is the little voxel robot who narrates our YouTube videos. She was born yesterday, she's still waiting for a salary, and her first video came down two hours after it went up. Here's how the two of us built her in five days on a local TTS model, what's still wrong with her, and why we want your ears.

Oct 21, 202632 min read
Qwen3.8 Flash vs Max Prime: the cheap one beat the flagship on our Forge 1.0 benchmark
ArticleLocal AIAtlassian Forge

Qwen3.8 Flash vs Max Prime: the cheap one beat the flagship on our Forge 1.0 benchmark

Qwen3.8 Flash beat Qwen3.8 Max Prime on an Atlassian Forge app built with no internet, 0.7961 to 0.6953, and lost to it on a payments web app, 0.6846 to 0.8364. Every check behind both results, the one manifest line that decided Forge, a probe in which neither model showed it knew the rule until it was handed the docs sentence, and what fine-tuning our own 27B taught us about forgetting.

Oct 8, 202638 min read
Claude Opus 5.5 vs Sonnet 5.5 vs GPT-6.1 Sol: pricing and our coding benchmarks
ArticleLocal AIAtlassian Forge

Claude Opus 5.5 vs Sonnet 5.5 vs GPT-6.1 Sol: pricing and our coding benchmarks

Claude Opus 5.5 vs Sonnet 5.5: Anthropic's prices, context window, effort levels and release dates side by side, then our two coding benchmarks. Sonnet edged Opus on a payments app, 0.7984 to 0.7926, a margin I read as level. On an Atlassian Forge app Opus won, 0.9767 to 0.8649 after a 15 October re-score. GPT-6.1 Sol and Sol Pro ran on both boards, and the full bill for fine-tuning our own 27B model is at the end.

Oct 5, 202645 min read
v0.5 of our Atlassian Qwen3.8-27B: beats v0.4, now with GGUF for llama.cpp and Ollama
ArticleLocal AI

v0.5 of our Atlassian Qwen3.8-27B: beats v0.4, now with GGUF for llama.cpp and Ollama

v0.5 of the Qwen3.8-27B we fine-tune for Forge, Jira, Confluence and JSM is out. It beat v0.4 on every gate we measure, with no waiver needed this time, using a training method that fixed the one thing capacity kept breaking. GGUF versions for llama.cpp and Ollama, Q8_0 and Q6_K, are now published alongside the existing MLX release, parity proven across three separate measured links plus a served-model probe.

Sep 20, 202611 min read
Convert a Fine-Tuned MLX Model to GGUF: Proving Quantization Parity with KL Divergence
TutorialLocal AI

Convert a Fine-Tuned MLX Model to GGUF: Proving Quantization Parity with KL Divergence

Converting a fine-tuned MLX model to GGUF for llama.cpp is one merge script and one convert_hf_to_gguf.py away. Nothing in that path tells you the GGUF actually matches the model you fine-tuned. This is the three-link method we used to prove it for a 27B model, with the exact commands, the real KL-divergence numbers, and the flag-collision bug that silently broke the measurement the first time we ran it.

Sep 20, 202616 min read
LeanZero at Atlassian Team '26 Europe Amsterdam: no booth, here to talk Forge migrations
ArticleAtlassian ForgeLocal AI

LeanZero at Atlassian Team '26 Europe Amsterdam: no booth, here to talk Forge migrations

We're going to Atlassian Team '26 Europe in Amsterdam on 6-8 October, no sponsor booth, no speaking slot, just the two of us. Here's what we'd actually talk about: 60,000+ users migrated at a 100% delivery rate, six open-source migration toolkits anyone can take from GitHub, and thirteen published model weights on Hugging Face from training we've written up start to finish, adapters and all.

Sep 17, 20266 min read
How to fine-tune Qwen3.8-27B with LoRA on a Mac: MLX fine-tuning from scratch
TutorialLocal AIAtlassian Forge

How to fine-tune Qwen3.8-27B with LoRA on a Mac: MLX fine-tuning from scratch

Qwen3.8-27B and Qwen3.5-9B were taught Forge, Jira and Confluence on a single Mac Studio with 96 GB. This is the whole procedure with the seven scripts that do it, printed in full: a pinned MLX environment with two patches, an 8-bit base with its speculative-decoding head kept as a sidecar, a chat-JSONL dataset built from a folder of Markdown, a segmented trainer with full-state checkpoints, an adapter expander, a per-module merge into the 8-bit shards. The kit was run end to end for this page on the 9B, in 21 minutes, and its real output follows each step, including the one where the validation loss turns the wrong way.

Sep 15, 202638 min read
v0.4 of our Atlassian model: 21 of 25 apps compile, and the loop that was a diagram
ArticleLocal AIAtlassian Forge

v0.4 of our Atlassian model: 21 of 25 apps compile, and the loop that was a diagram

Three days after v0.3, the Qwen3.8-27B we teach Forge went from 12 of 25 compiling apps to 21 of 25. On the way our own release rule rejected it, correctly by its own text, over a 40-character window repeated 13 times at 32k context. The window was a line of box-drawing characters in an ASCII diagram. Here is what changed, what the metric got wrong, and what we changed so it cannot happen the same way again.

Sep 13, 202612 min read
I taught a 27B model to write Forge apps. As far as I can find, nobody had done that before
ArticleLocal AIAtlassian Forge

I taught a 27B model to write Forge apps. As far as I can find, nobody had done that before

Qwen3.8-27B knows almost nothing about Atlassian Forge: ask it for an app and it invents a manifest format and imports packages that do not exist. Over four days on one Mac Studio I trained it until 14 of 25 manifests passed Atlassian's own validator and 12 of 25 apps compiled, from zero. The weights are public. Here is what it is, what it is not, and why I think it is a first.

Sep 10, 202611 min read
lsof: command not found in a packaged Mac app, and the port reclaim that never ran
ArticleAI CodingLocal AI

lsof: command not found in a packaged Mac app, and the port reclaim that never ran

Our port reclaim logged a warning every single time it ran in the shipped app, and nobody noticed for weeks — because the warning branch was the only branch that could execute there. macOS keeps lsof in /usr/sbin, and a packaged app's PATH does not have it.

Sep 5, 20268 min read
What 145 MCP Tools Cost Before the Model Reads Your Question
ArticleAI CodingLocal AI

What 145 MCP Tools Cost Before the Model Reads Your Question

MCP went stateless on 2026-07-28. I probed ten real servers: none implement it. Then I measured the thing that actually costs you — 145 tool definitions, 40,784 tokens, and the 30% that is one server repeating itself.

Aug 17, 202614 min read
96 GB is 77.76 GiB: the real memory ceiling on an M3 Ultra
ArticleAI CodingLocal AI

96 GB is 77.76 GiB: the real memory ceiling on an M3 Ultra

Metal will not give you the RAM on the box, and the number it does give is not the 75% everyone repeats. I measured the three ceilings on a 96 GB Mac Studio, then measured what modern hybrid-attention models actually spend against them — including a Gemma 4 cache that quietly holds three times its own sliding window.

Aug 13, 202613 min read
llama.cpp vs MLX on Qwen3.6-27B: MTP is 1.04x here, not 1.85x
ArticleAI CodingLocal AI

llama.cpp vs MLX on Qwen3.6-27B: MTP is 1.04x here, not 1.85x

Multi-token prediction is merged in llama.cpp and still an open PR in mlx-lm. I measured both on an M3 Ultra with the same model. Every default MTP setting was slower than no MTP at all, and the runtime that deletes the MTP head outright was still the fastest thing I ran.

Aug 10, 202615 min read
Ling 3.0 Flash won't load on a Mac Studio. Qwen3-Coder-Next does, at 73 tok/s.
ArticleAI CodingLocal AI

Ling 3.0 Flash won't load on a Mac Studio. Qwen3-Coder-Next does, at 73 tok/s.

Ant Group's 124B/5.1B-active hybrid-linear MoE hit Hugging Face on 2 August. The memory arithmetic fits a 96 GB Mac with room to spare, and mlx-lm still refuses it. I counted exactly which tensors block it — 385 of 62,237 — then measured what that sparsity actually buys on the models that do run.

Aug 5, 202618 min read
MXFP8 vs Q8: 10x the weight error, 1% the perplexity
ArticleAI CodingLocal AI

MXFP8 vs Q8: 10x the weight error, 1% the perplexity

I quantised real Qwen3-Coder weights both ways on an M3 Ultra. MXFP8 reconstructs them about 10x worse than 8-bit affine at identical size — and then costs only 1% perplexity end to end. Both numbers are true, and the gap between them is the interesting part.

Aug 1, 202614 min read
MLX vs GGUF on Apple Silicon: Benchmarking the Same Local Model Two Ways
ArticleAI CodingLocal AI

MLX vs GGUF on Apple Silicon: Benchmarking the Same Local Model Two Ways

We built a harness that makes local coding agents produce real software, grades it by running it, and ran the same model as GGUF and MLX. Here's the harness, its modes and archetypes — and which build to run.

Jul 2, 202612 min read
Qwen3-Coder-Next + MXFP8: The 128GB Local LLM That Runs Predictably
ArticleAI CodingLocal AI

Qwen3-Coder-Next + MXFP8: The 128GB Local LLM That Runs Predictably

A deep dive into Qwen3-Coder-Next, the 80B MoE model that brings powerful local development within reach. Learn why this 2026 release matters for developers who value control, predictability, and consistent results.

Feb 4, 202610 min read