Lyria Team, Google DeepMind · 2025

Live Music Models:
Magenta RealTime

A music generator you can play, not just press start on. It emits an unbroken stream of audio in real time and bends to your text and audio prompts mid-performance — the first open-weights model that turns "music as a noun" into "music as a verb."

Prerequisites: Transformers + basic audio/DSP intuition
11
Chapters
6
Simulations

Chapter 0: The Problem

Open a text-to-music model. Type "lo-fi jazz with a rainy night feel." Hit generate. Wait. Thirty seconds later a 30-second clip drops into your lap. Want it warmer? Want a sax to come in? You change the prompt and start over. You are a customer placing an order, not a musician.

The paper calls this the gap between music as a noun (a finished recording you receive) and music as a verb (a live thing you shape in real time). Almost every modern music AI — Jukebox, MusicGen, Stable Audio — lives firmly on the "noun" side: offline, turn-based generation.

The core question: Can a model produce an uninterrupted, infinite stream of music that responds to your controls while it plays — so you steer it the way a DJ rides a crossfader, with the sound changing under your hands within a fraction of a second?

Why "just make it faster" is not enough

You might think the fix is obvious: make the offline model fast. If it can generate T seconds of audio in less than T seconds of compute, isn't that "real time"?

Not quite. The paper is precise about what "live" demands. A model is a live music model only if it has all three of these properties:

PropertyWhat it meansWhy offline models fail it
1. Real-time throughput (RTF ≥ 1×)Generates audio at least as fast as it plays. RTF = T/L (output seconds ÷ latency seconds).Many are fast enough, but...
2. Causal streamingNew audio is generated continuously, conditioned on both your controls AND the audio already played.Offline models generate a whole clip in one shot — there is no "already playing" audio to continue from.
3. Responsive control (low delay D)The gap between you changing a control and that change reaching the audio is small.Restarting generation throws away the current performance; D is effectively the whole clip length.

The two latencies you must hold in your head

The paper distinguishes two quantities that beginners constantly conflate:

An offline model with RTF = 5× sounds great until you realize that to change the music you must stop and re-run it — so its effective D is the entire clip. A live model keeps the audio flowing and only lets your change "leak in" after D. That is the difference between a vending machine and an instrument.

Why open weights matter here: A live instrument should run on your device. Local inference removes the network round-trip (lower latency), works without internet (reliability on stage), keeps your audio private, and lets artists fine-tune. That is why the paper releases Magenta RT (760M params, open) alongside the bigger API-only Lyria RT.
Why is an RTF ≥ 1× offline model still not a "live music model"?

Chapter 1: The Key Insight

How do you generate infinite audio in real time with a Transformer, when Transformers were trained on fixed-length clips and slow down as context grows? Magenta RT's answer is three ideas stacked together — each one removing a different blocker.

The insight in one breath: Generate music in fixed 2-second chunks, each one predicted from only the last 10 seconds of audio (a Markov window) plus a style embedding — and represent that 10-second history with coarse tokens so the model stays under the real-time budget. Update the style embedding between chunks and the music bends to you, live.

The three moves

1
Chunk-based autoregression. Don't generate a 10-minute song. Generate one 2s chunk at a time, conditioned on a fixed 10s window of recent audio. Infinite length, stateless inference, no growing cache.
2
Coarse context. The audio history doesn't need full fidelity — only the salient structure. Keep just the first 4 (of 16) RVQ levels for the history, slashing the token count and hitting RTF ≥ 1×.
3
Style embedding control. A single 768-dim joint audio-text vector (from MusicCoCa) steers each chunk. Swap it between chunks → the stream responds, no restart.

The pipeline (Figure 1, in words)

Three trained components, chained, looping every 2 seconds:

ComponentRoleFrom / by
SpectroStreamAudio codec: turns waveform ↔ discrete tokens (RVQ).Li et al. 2025
MusicCoCaJoint audio-text embedder: turns prompts into a style vector.this paper (builds on MuLan + CoCa)
Encoder–Decoder LMPredicts the next chunk's audio tokens from history + style.T5-style Transformer

We will build each one, in the order the data flows: tokens (Ch 2–3), then the streaming trick (Ch 4), then the style control (Ch 5), then the LM that ties them together (Ch 6).

What lets Magenta RT generate music of arbitrary length without slowing down?

Chapter 2: Audio as Tokens (SpectroStream)

A Transformer predicts discrete tokens. But audio is a continuous waveform — at 48 kHz, that's 48,000 floating-point samples per second per channel. You cannot ask a language model to predict raw samples. So step one of any "codec language model" is to turn audio into something token-shaped.

That job belongs to a neural audio codec: a learned encoder/decoder pair. The encoder squeezes the waveform into a short sequence of integers; the decoder reconstructs the waveform from those integers with minimal perceptible loss. Think of it as a learned, lossy "JPEG for sound" — but the compressed form is a grid of codebook indices, which is exactly what an LM can model.

The shapes, made concrete

Formally, the encoder maps a stereo waveform a ∈ R(T·fs) × 2 into a token tensor of shape Vc(T·fk) × dc. Decode each symbol:

Read the shape like a sentence: a 2-second clip at full depth is 2 × 25 = 50 frames, each frame 64 integers → a 50 × 64 grid = 3,200 tokens. The decoder Dec ≈ Enc-1 turns that grid back into a stereo waveform. The codec is frozen — the LM never changes it; it just learns to predict the integers the codec defines.

Why a spectrogram-domain codec, and the bitrate math

SpectroStream operates in the spectral domain (hence the name) and is built on residual vector quantization (RVQ) — the next chapter's whole topic. Full SpectroStream runs at 16 kbps (fk=25, dc=64, |Vc|=1024). Sanity-check that number: each token carries log2(1024) = 10 bits. Tokens per second = 25 frames × 64 depth = 1600. So 1600 × 10 = 16,000 bits/s = 16 kbps. The math closes.

That's beautiful fidelity but far too many tokens for real time. The fix, previewed: keep only the first 16 of the 64 RVQ levels → 25 × 16 = 400 tokens/sec → 4 kbps. That "live throughput target of 400 tokens per second" is the number the whole system is engineered around.

Waveform → Tokens: watch the codec sample-and-quantize
Frame rate fk 25 Hz

Drag the frame rate. Low fk → few frames → the reconstruction can't track the wiggles (audible smearing). High fk → faithful, but more tokens to predict. SpectroStream sits at 25 Hz — a deliberate quality/throughput trade.

A 2-second clip is encoded at fk=25 Hz and RVQ depth 16. How many audio tokens is that?

Chapter 3: RVQ Depth — the dial that buys real time

We keep saying "the first 4 of 16 levels" as if dropping levels were free. To understand why coarse tokens are good enough for the history but not for the output, you have to understand what an RVQ level actually is.

One codebook can't be precise. So stack them.

Vector quantization replaces a continuous vector with the nearest entry in a learned codebook of, say, 1024 prototypes. The problem: 1024 prototypes is a coarse grid — the error (the leftover residual) can be large. You could grow the codebook to a billion entries, but the LM's vocabulary would explode.

Residual vector quantization is the elegant fix. Quantize the vector with codebook 1; you get a coarse approximation and a leftover residual. Quantize that residual with codebook 2. Quantize its residual with codebook 3. Each level is one integer; each level shrinks the error. This is exactly the move behind SoundStream and Encodec.

x ≈ e1[i1] + e2[i2] + e3[i3] + … + ed[id]

where ek is the k-th codebook and ik is the chosen index at level k. The first few levels carry the loudest, most salient structure (the gist of the sound); later levels add fine texture and air.

The key asymmetry the paper exploits: because lower levels carry the most information, a coarse reconstruction (first 4 levels) is a perfectly good summary of past audio — good enough to condition on. But for the audio you actually output and play, you need the full 16 levels or it sounds muddy. So: generate at depth 16, remember at depth 4.

Worked numbers: the cost of remembering

The model conditions on H = 5 chunks (10 s) of history. Compare the two choices for representing that history:

History representationTokens (10 s = 250 frames)Verdict
Full depth 16250 × 16 = 4000Too many — blows the budget
Coarse depth 4 (chosen)250 × 4 = 10004× smaller, keeps the gist

Add the 12 style tokens (next chapter) and the encoder input is exactly 1000 + 12 = 1012 tokens — the number the paper states. Every design choice is in service of that token count.

RVQ reconstruction: add levels, watch error fall
RVQ levels used 4

The green curve is the target signal; the orange curve is the RVQ reconstruction using only the chosen number of levels. Notice how the shape is mostly captured by level 4, and later levels only refine fine wiggles. That is precisely why 4 levels suffice for the memory but not the output.

Why does Magenta RT use only 4 RVQ levels for the audio history but 16 for the generated chunk?

Chapter 4: Chunked Streaming — SHOWCASE

Now the centerpiece. We have tokens (Ch 2) and a cheap way to represent history (Ch 3). The remaining problem: a Transformer trained on fixed clips behaves unpredictably when you ask it to extrapolate to sequences longer than it ever saw. Generating a 10-minute song token-by-token from position 0 means the model is soon operating far outside its training distribution.

The fix: a sliding Markov window of chunks

Operate on chunks of length C = 2 s. Under a Markov assumption, predict chunk i from only the last H = 5 chunks (10 s of history) and the current style vector. Slide the window forward 2 s, predict the next chunk, repeat — forever.

The formal modeling objective the paper writes is:

Pθ( Chunki | Coarsei-H : i , ci )

Reading it: predict the full-depth tokens of chunk i, given the coarse (4-level) tokens of the previous H chunks and the style vector ci. Two distinct token resolutions in one equation — that is the whole trick on a single line.

Three payoffs of chunking (this is the "why"): (1) Stateless inference — each chunk is a fresh forward pass over a fixed 1012-token input, so there is no KV cache to maintain, which makes deployment trivial. (2) Bounded error accumulation — the model never drifts arbitrarily far from training-length context. (3) Live control — because conditioning is re-supplied every chunk, you can change the style vector between chunks and the stream responds within one chunk (D ≈ 2 s).

What degrades when you change the knobs

This is the intuition the sim below makes physical:

Magenta RT's C=2 s, H=5 is the sweet spot the team found through play-testing with musicians: responsive enough to feel like an instrument, long enough to keep the music coherent.

The streaming loop: drag a prompt change in mid-stream
Chunk C 2.0 s History H 5
Press Play. The playhead emits chunks; the green band is the live H-chunk context window feeding the next prediction.

Watch the orange playhead advance one chunk at a time. The shaded green band is the context window the model "sees" to predict the next chunk. Hit Change prompt now mid-stream: the new style takes effect only at the next chunk boundary — that delay is D. Shrink C and the change lands sooner; grow H and the band stretches further back (more memory, more tokens).

In the streaming loop, what does the control delay D correspond to?

Chapter 5: Style Embeddings (MusicCoCa)

We've been calling ci "the style vector." Where does it come from, and why is a single 768-dim vector enough to mean "techno flute, but moodier"?

The control signal is produced by MusicCoCa — a joint audio–text embedding model. It has two towers that map into the same 768-dim space: an audio tower (a 12-layer Vision Transformer over log-mel spectrograms) and a text tower (a 12-layer Transformer over tokenized text). It's built on MuLan and CoCa (a "contrastive captioner").

Why a shared space is the whole point: because text and audio land in the same geometry, "techno" (typed) and a clip of techno (recorded) end up near each other. So a text prompt and an audio prompt are interchangeable controls — and you can do arithmetic on them. The paper's example: embed("techno") + embed("flute") ≈ embed("techno flute"). Style becomes a vector you can add, scale, and blend.

From embedding to tokens (the data flow)

The continuous 768-dim embedding is then quantized into 12 discrete tokens (codebook size |Vm| = 1024) so it can sit in the LM encoder's input alongside the audio tokens. That's the "12 style tokens" we kept adding to the 1000 audio tokens to reach 1012.

Symbol decode for ci in the objective:

ci = Quantize( MA(a)⌊Ci/10⌋ )

where MA is the MusicCoCa audio tower and the subscript picks the most-recent 10-s MusicCoCa embedding for chunk i. At training time the style comes from the target audio itself (the model sees what it should produce); at inference the user supplies it via text/audio prompts.

Train/infer asymmetry — a subtle but crucial decision: training on the audio embedding (not text) means the model learns the richest possible conditioning. Because text and audio share the space, swapping in a text embedding at inference still works. This is why audio prompts tend to steer more effectively than text — they match the training distribution exactly.
Shared embedding space: text and audio prompts as vectors you can blend
Weight: "techno" 0.50

The dot is the resulting style vector c, a weighted average of two prompt embeddings. Slide the weight and watch c travel along the line between "techno" and "flute" — that geometry is exactly what the model conditions on.

Why can a text prompt and an audio prompt be mixed into one style vector?

Chapter 6: The Encoder–Decoder LM

Everything funnels into one Transformer. Magenta RT uses a T5-style encoder–decoder language model (released at T5 Base = 220M and Large = 770M). Let's trace exactly what enters each half.

The encoder: digest history + style

The bidirectional encoder reads the concatenation:

xi = Coarsei-H ⊕ … ⊕ Coarsei-1 ⊕ ci

That's the 1000 coarse audio tokens (4 levels × 25 fps × 2 s × 5 chunks = 1000) plus 12 style tokens = 1012 tokens. Crucially the vocabulary is unified: V = {<S>, <P>} ∪ Vc ∪ Vm — special tokens, codec tokens, and quantized style tokens all share one embedding table.

The decoder: the depth trick that buys RTF ≥ 1×

Here is where naive approaches die. The output chunk is 50 frames × 16 levels = 800 tokens. A vanilla autoregressive decoder would predict 800 tokens one at a time — far too slow. MusicLM's answer was a hierarchical cascade of multiple LMs; MusicGen's was a delay pattern. Neither hits RTF ≥ 1× at full bandwidth.

Magenta RT instead uses a two-module decoder (following the "between-frame / within-frame" method, like Moshi/UniAudio):

T
Temporal module. Walks frame-by-frame. For each frame, it embeds and aggregates that frame's RVQ tokens into a single frame-level vector, building a temporal context. Runs once per frame (50 steps).
↓ frame context
D
Depth module. Given that frame context, autoregressively predicts the 16 RVQ indices within the frame. Runs the inner depth loop — small and fast.
Why this is fast: instead of one long 800-step autoregression, you factor it into 50 cheap temporal steps × a tiny 16-step depth loop each. The expensive temporal Transformer runs at the frame rate, not the token rate. Result: RTF = 1.8 on an H100 with the T5-Large config — comfortably above the 1.0× live threshold.

Working Python: the chunked streaming loop

The core insight, runnable. This is the inference loop — the exact thing the showcase sim animates:

# Magenta-RT-style live generation loop (pseudocode w/ real shapes) import numpy as np C, FK = 2, 25 # 2 s chunks, 25 frames/s H, D_OUT, D_HIST = 5, 16, 4 # 5-chunk window, 16 levels out, 4 in history def style_vector(prompts): # weighted avg of MusicCoCa embeddings, then quantize -> 12 tokens e = np.sum([w * musiccoca(p) for p, w in prompts], axis=0) e /= sum(w for _, w in prompts) return quantize(e) # shape (12,) history = [pad_chunk() for _ in range(H)] # cold-start: padding tokens while performing: # INFINITE stream c = style_vector(user_prompts()) # re-read controls EVERY chunk -> live coarse = [chunk[:, :D_HIST] for chunk in history] # keep 4 levels each enc_in = np.concatenate([*coarse, c[None]]) # 1000 + 12 = 1012 tokens new_chunk = lm.generate(enc_in) # shape (C*FK, D_OUT) = (50, 16) audio = spectrostream_decode(new_chunk) # -> 2 s of 48 kHz stereo play(audio) # emit before predicting the next chunk history = history[1:] + [new_chunk] # slide the window; STATELESS, no KV cache

Read the two load-bearing lines: c = style_vector(user_prompts()) is re-evaluated every loop, which is why the music is live; history = history[1:] + [new_chunk] is the sliding Markov window, which is why it's infinite and stateless.

How does the two-module decoder achieve RTF ≥ 1× where a flat autoregressive decoder cannot?

Chapter 7: Prompt Blending & Transitions

Live control isn't just "pick a style." It's moving between styles smoothly while the music keeps playing. Two mechanisms enable this: weighted prompt mixing (the algebra) and conditioning interpolation (the time dimension).

The weighted-average formula

With N prompts (text or audio), the target conditioning vector is:

c = ( Σi=1..N wi M(ci) ) / ( Σi wi )

Each wi is a slider on prompt i's influence; M is the relevant MusicCoCa tower. Set "techno"=0.8, "flute"=0.2 and you get techno that's faintly flute-tinted. This is the embedding arithmetic from Ch 5, now with a normalization so weights act like proportions.

Transitions: interpolate the conditioning over time

To cross-fade from prompt A to prompt B, linearly interpolate between their embeddings across the performance — the paper does it over 60 s in 6 steps (10 s each). At each chunk the style vector is a little more B and a little less A, so the music morphs continuously.

The surprising finding (Figure 2): the model doesn't snap to the target — it preserves elements of the earlier prompts because the 10-s audio context still carries them. This causes a slight mid-transition dip in similarity and lower final similarity, but it's a feature: the music evolves coherently instead of cutting abruptly. The history of your prompts becomes part of the performance. The audio context isn't just memory — it's musical inertia.
Prompt transition: interpolate A→B, watch the response track (and lag)
Context inertia 0.30

The dashed line is the conditioning we command (a clean A→B ramp). The solid orange line is the audio's measured similarity to B. Raise "context inertia" (the pull of the 10-s history) and watch the response lag and dip mid-transition — exactly the smooth, slightly-behind blending the paper observes.

Why does Magenta RT's output not perfectly reach the target embedding at the end of a transition?

Chapter 8: Audio Injection

Text and style vectors steer the mood. But what if you want to feed the model live sound — hum a melody, tap a rhythm, play a chord on a real instrument — and have the AI react to it? That's audio injection, and it's almost free given the architecture we've built.

The mechanism (and the clever non-obvious bit)

At each generation step: mix the user's input audio into the model's most recent output, tokenize the mixture, and feed it as the context for the next chunk. That's it. No new training, no new module — it rides on the existing "condition on the last 10 s of audio" loop.

The subtle part: the user's audio is never played back directly. The model predicts a continuation of a context that happens to include your audio. So depending on the target style, it may repeat your melody, transform it, or just absorb its dynamics/harmony/rhythm as influence. You're not overdubbing — you're biasing the prediction.

Data flow, and what degrades without it

Normally history = [past model chunks]. With injection, the most recent slot becomes tokenize(mix(model_out, user_audio)). If the user audio is silent, the mix is just the model's own output → identical to vanilla generation. If the user audio dominates the mix, the model leans hard on it and may echo it. The mix ratio is the dial between "ignore me" and "follow me."

Audio injection: mix your input into the context, see the model react
Inject mix ratio 0.40

Blue = your injected audio (a steady melody). Teal = the model's continuation. At mix 0 the model does its own thing; raise the mix and the teal output starts tracking the blue melody's contour — because that contour now lives in the context it's continuing from.

How does audio injection steer generation without retraining the model?

Chapter 9: Experiments & Sampling

Does this live model actually sound good — or did real-time come at the cost of quality? The headline result: Magenta RT beats bigger offline open models on standard metrics, while being the only one that's live.

The benchmark table (Song Describer Dataset, 47 s clips)

ModelLive?ParamsFDopenl3KLpasstCLAP ↑
Magenta RealTime760M72.10.470.35
Stable Audio Open1.1B96.50.550.41
MusicGen-stereo-large3.3B190.50.520.31

Read the columns: FDopenl3 (Fréchet distance, lower = output distribution matches real music) and KLpasst (lower = semantically closer to reference) — Magenta RT wins both, with 38% fewer params than Stable Audio Open and 77% fewer than MusicGen Large. CLAP (higher = text adherence) — it lands in the middle; the paper notes Stable Audio Open trains on CLAP embeddings, an apples-to-oranges advantage, while Magenta RT trains on MusicCoCa.

External validation: at time of writing, Magenta RT ranked the top open-weights model on the Music Arena leaderboard from 1k+ real-world human preference votes — so the metric wins aren't just gaming a benchmark.

The sampling recipe (the knobs that matter at inference)

Generation uses classifier-free guidance (CFG) with temperature 1.3, top-K 40, CFG weight 5.0. CFG pushes the sample toward the prompt by extrapolating away from the unconditional prediction:

logits = uncond + s · ( cond − uncond )

where s is the CFG weight. At s=1 you get plain conditional sampling; s=5 strongly amplifies the prompt's influence (sharper adherence, but too high can over-saturate and hurt diversity). Temperature 1.3 and top-K 40 keep the samples varied without going incoherent.

CFG & temperature: trade prompt adherence against diversity
CFG weight s 5.0 Temperature 1.3

Each dot is a sampled output around the prompt (the cross). Raise CFG and the cloud is yanked toward the prompt (tighter adherence). Raise temperature and the cloud spreads (more diversity). The paper's chosen point — s=5, T=1.3 — is the balance that felt best in play-testing.

What does increasing the classifier-free guidance weight s do?

Chapter 10: Connections & Cheat Sheet

Magenta RT sits at the intersection of three lineages: neural audio codecs (SoundStream → Encodec → SpectroStream), codec language models for audio (AudioLM → MusicLM → MusicGen), and joint audio-text embeddings (MuLan → CoCa → MusicCoCa). Its novelty is the live reframing: chunked autoregression + coarse context + streaming decoder.

How it relates to its ancestors

ModelWhat it gaveWhat Magenta RT changed
AudioLM / MusicLMCodec LM over audio tokens, joint embedding conditioningReplaced the multi-LM hierarchical cascade with one LM
MusicGenSingle-stage with a "delay pattern" for RVQ tokensTwo-module (temporal/depth) decoder hits RTF≥1×; MusicGen can't live-stream
Moshi / UniAudioBetween-frame / within-frame decoding for speechAdapted the same factorization to full-band music

What the paper doesn't solve (read the fine print)

Cheat sheet — every symbol in one place

SymbolMeaningMagenta RT value
Cchunk length2 s
Hhistory window (chunks)5 (= 10 s)
fkcodec frame rate25 Hz
dc (out / history)RVQ depth generated / remembered16 / 4
|Vc|, |Vm|codec / style codebook size1024 / 1024
encoder inputcoarse history + style tokens1000 + 12 = 1012
style dimMusicCoCa embedding → tokens768-dim → 12 tokens
RTFreal-time factor (T/L)1.8 (H100, T5-Large)
s, T, KCFG weight, temperature, top-K5.0, 1.3, 40
"Music exists in two forms: as a noun, and as a verb."
— The paper's framing of music as a noun (a recording) vs. a verb (a live act)