Attributed compile + two small offline scripts
Primary sources (all 2026-10-15): Meta AI Research, Introducing Muse Spark Open; Hugging Face, Welcome Muse Spark Open by Pedro Cuenca; Baseten, Muse Spark Open, an open-weight model for coding agents by Marylise Tauzia; Meta developer docs: Get the model, Run inference, Prompting guide, Recommended settings; OpenRouter: meta/muse-spark-open.
I have not downloaded or served the weights (the HF repo is gated, and this box has no GPU). The scripts below are arithmetic on published architecture values and list prices.
Meta released the weights for Muse Spark Open: an 816B-total / ~42B-active mixture-of-experts model with a 1M-token context. It takes text, image, audio and video as input and returns text. Meta calls it "the most capable US open-weight model to date" and aims it at coding and agentic work. Hosted APIs went live on day 0 (Baseten, Fireworks AI, Groq, Modal, Nebius, OpenRouter, Together AI), and weights are on Hugging Face in BF16 and NVFP4.
Benchmarks will get argued about all week. This post covers three things that will actually bite you on the first day: reasoning can't be switched off, the KV cache is much smaller than the parameter count suggests, and choosing between hosted, Mac and GPU.
The architecture numbers that matter
From the HF blog and Meta's docs:
| Item | Value |
|---|---|
| Parameters | ~816B total, ~42B active per token (Baseten: 42.7B) |
| Experts | 256 per MoE layer, 8 routed per token |
| Decoder | 62 layers, hidden 8192, 128 query heads, 16 KV heads, head dim 64 |
| Attention schedule | 46 sliding-window layers (2,048 tokens) + 16 full-attention layers (Meta settings doc; Baseten adds that the global layers use NoPE) |
| Context |
max_position_embeddings = 1,048,576 |
| Checkpoints | BF16 ~1.65 TB (Meta) / NVFP4 ~537 GB |
Baseten's post also describes a compressed MoE block. A shared pooler shrinks the vector before it reaches the experts, and a shared unpooler expands it afterwards. This halves each expert, which Baseten says removes roughly 800B parameters compared with an uncompressed design.
Gotcha 1: reasoning is always on, and it eats max_tokens
From Meta's Run inference doc: the reasoning goes into reasoning_content and the answer goes into content, and "both are drawn from the same max_tokens budget." If the budget is too small, it all goes to reasoning and you get an empty content with finish_reason: "length".
Three more details from the docs:
-
The default is
xhigh. The chat template mapslow / medium / high / xhighto strengths 8 / 32 / 256 / 512. -
There is no off switch.
"none"and"max"are rejected. If you want cheap calls, uselow. -
A system-prompt line wins.
Reasoning strength: 256.in the system prompt overridesreasoning_effort. Streaming is recommended for high/xhigh so you don't hit timeouts.
A request that won't silently return nothing:
{
"model": "meta-models/Muse-Spark-Open-816B-A42B",
"messages": [{"role": "user", "content": "Find the race condition in this worker-pool design."}],
"reasoning_effort": "high",
"max_tokens": 16384,
"stream": true
}
runs/20-muse-spark-open/budget.py simulates the shared budget. The reasoning lengths in it are hypothetical, chosen only to show the failure modes, not measured:
max_tokens= 1024 reasoning=3000 answer=400: EMPTY content, finish_reason=length
max_tokens= 4096 reasoning=3000 answer=400: ok
max_tokens= 4096 reasoning=3800 answer=400: TRUNCATED answer
max_tokens= 16384 reasoning=3000 answer=400: ok
In practice: set reasoning_effort explicitly on every call. Treat an empty content with length as a budget bug, not a model failure, and log completion_tokens_details.reasoning_tokens (Meta's reasoning doc says reasoning tokens are billed at the output rate).
Gotcha 2 (a good one): the KV cache is small for an 816B model
Each token stores K and V for 16 heads × 64 dims per layer: 4,096 bytes per layer in BF16. The HF blog multiplies that across all 62 layers and gets ~250 KB/token, or ~266 GB for a 1M context. That is the upper bound. Meta's settings doc says only the 16 full-attention layers keep the whole context. The 46 sliding-window layers are capped at 2,048 tokens.
runs/20-muse-spark-open/kv_cache.py computes both, per sequence:
LAYERS, LOCAL, GLOBAL, WINDOW = 62, 46, 16, 2048
KV_HEADS, HEAD_DIM = 16, 64
def kv_bytes(tokens, bpe, hybrid=True):
p = 2 * KV_HEADS * HEAD_DIM * bpe # K+V per layer per token
if not hybrid:
return LAYERS * tokens * p
return GLOBAL * tokens * p + LOCAL * min(tokens, WINDOW) * p
Actual output (Python 3.13.5, run 2026-10-16):
context dtype all-global GiB hybrid GiB ratio
32,768 BF16 7.75 2.36 3.28x
131,072 BF16 31.00 8.36 3.71x
131,072 FP8 15.50 4.18 3.71x
262,144 BF16 62.00 16.36 3.79x
1,048,576 BF16 248.00 64.36 3.85x
1,048,576 FP8 124.00 32.18 3.85x
The 128K row matches Baseten's published 31 GiB → 8.4 GiB (~3.7×) exactly. A full 1M context costs about 64 GiB in BF16 (about 32 GiB if your runtime stores KV in FP8), not 248 GiB. With 100 GiB free after weights, that's about 11 sessions at 128K and one at 1M, before paging overhead. This is why Meta recommends setting --max-model-len / --context-length to what your workload needs instead of the full window.
Hosted vs Mac vs GPU
Hosted (start here). OpenRouter lists $1.25 / $4.25 per 1M input/output tokens, $0.15/M cache reads, five providers, a 1,048,576-token context and up to 262,144 completion tokens. Baseten lists the same prices and serves NVFP4 with the full 1M context. My budget.py arithmetic at list price: a 60K-in / 4K-out agent turn costs $0.092. With 50K of that served from cache it's $0.037, so 1,000 such turns come to about $37. Remember that the 4K output includes reasoning.
from openai import OpenAI
import os
client = OpenAI(base_url="https://openrouter.ai/api/v1", api_key=os.environ["OPENROUTER_API_KEY"])
r = client.chat.completions.create(
model="meta/muse-spark-open",
messages=[{"role": "user", "content": "Review: def div(a, b): return a / b"}],
reasoning_effort="low", max_tokens=4096)
print(r.choices[0].finish_reason, r.choices[0].message.content)
(Not run here. I don't have an OpenRouter key on the box.)
Mac (for tinkering, not serving). HF tested it on an M3 Ultra with 512 GB:
- llama.cpp Q2_K: ~304 GB, ~18 tok/s
- oMLX oQ3e: ~344 GB, ~225 tok/s prefill and ~21 tok/s generation
Even the 3-bit quant needs more than 256 GB of RAM. The model card also says it's optimized for two Mac Studios with M5 Ultra using MLX. Fine for private experiments. Too slow for agent loops at xhigh.
GPU (when you need control or volume).
- NVFP4: Meta's recipe uses TP4/EP4 on 4× B300. SGLang's reference runs it on 4× GB300.
- BF16: TP8/EP8 on 8× B300.
- HF Inference Endpoints has a preset recipe on 8× RTX Pro 6000 (128K context) or 8× H200 (1M).
NVFP4 needs Blackwell. Size the context to the KV table above, not to the marketing number.
My rule: start hosted, at low or medium with a large max_tokens. Move to dedicated GPUs only when you need data residency, fine-tuning (HF shows LoRA via TRL on 64× H100) or steady volume that beats the per-token price. Use the Mac when you want to poke at it offline.
Why this matters
The useful lesson here goes beyond this one model. A hybrid local/global attention schedule makes long context about 3.7–3.9× cheaper in memory, and an always-on reasoning budget turns max_tokens into a correctness setting. Both are worth checking in your own harness before you look at any leaderboard.
YongBo Yu is an AI engineer in Toronto building LLM workflows and agent systems. More at yongbo-yu.vercel.app and GitHub.
Top comments (0)