invoke-ai/InvokeAI · error · ValueError
Qwen-Image PiD decode expected a 16-channel latent, got shap
Error message
Qwen-Image PiD decode expected a 16-channel latent, got shape {tuple(latents.shape)}. What it means
After frame reduction the invocation validates the latent is 4D with 16 channels (Qwen-Image latent channel count). Anything else (SD-style 4-channel, video latent not reduced, wrong ndim) raises ValueError reporting the actual shape, since the VAE denormalization/decode expects exactly this layout.
Source
Thrown at invokeai/app/invocations/qwen_image_pid_decode.py:135
# the Nodes editor wire any PiD decoder into this Qwen-Image-specific node).
assert_pid_decoder_matches_base(
context.models.get_config(self.pid_decoder.decoder).base,
BaseModelType.QwenImage,
node_title="Qwen-Image PiD Decode",
)
latents = context.tensors.load(self.latents.latents_name)
# 1) Reduce the stored 5D (B, C, num_frames, H, W) latent to 2D (B, C, H, W). Qwen's VAE is a video-style
# autoencoder; for a single image num_frames == 1 (mirrors qwen_image_l2i's `img[:, :, 0]`).
if latents.ndim == 5:
if latents.shape[2] != 1:
raise ValueError(
f"Qwen-Image PiD decode expected a single temporal frame, got shape {tuple(latents.shape)}."
)
latents = latents[:, :, 0]
if latents.ndim != 4 or latents.shape[-3] != 16:
raise ValueError(f"Qwen-Image PiD decode expected a 16-channel latent, got shape {tuple(latents.shape)}.")
# 2) Resolve the per-channel latents_mean / latents_std used to denormalise the stored latent.
latents_mean = list(_QWEN_VAE_LATENTS_MEAN_FALLBACK)
latents_std = list(_QWEN_VAE_LATENTS_STD_FALLBACK)
if self.vae is not None:
vae_info = context.models.load(self.vae.vae)
with vae_info.model_on_device() as (_, vae):
config = getattr(vae, "config", None)
cfg_mean = getattr(config, "latents_mean", None) if config is not None else None
cfg_std = getattr(config, "latents_std", None) if config is not None else None
if cfg_mean is not None and cfg_std is not None:
latents_mean = [float(x) for x in cfg_mean]
latents_std = [float(x) for x in cfg_std]
del vae_info
TorchDevice.empty_cache()
if len(latents_mean) != 16 or len(latents_std) != 16:
raise ValueError(
f"Qwen-Image VAE latents_mean/latents_std must have 16 entries, got {len(latents_mean)}/{len(latents_std)}."View on GitHub (pinned to 0b6a024f2f)
Solutions
- Ensure the upstream denoise/latent node is the Qwen-Image pipeline producing 16-channel 4D latents
- Check latents.shape: must be (B, 16, H, W) after any frame reduction
- Use the correct model-specific decode node for non-Qwen latents instead of PiD decode
- Regenerate the latents with the correct pipeline rather than reusing an old latents_name
Example fix
// before latents = latents # (1, 4, 64, 64) SD latent fed to Qwen decode // after latents = qwen_denoise.latents # (1, 16, H, W) Qwen latent
Defensive patterns
Strategy: type-guard
Validate before calling
latents = context.tensors.load(latents_name)
assert latents.ndim == 4 and latents.shape[-3] == 16, f"bad latent: {tuple(latents.shape)}" Type guard
def is_qwen_image_latent(t: "torch.Tensor") -> bool:
return t.ndim == 4 and t.shape[-3] == 16 Try / catch
try:
output = invoke(context)
except ValueError as e:
if "16-channel latent" in str(e):
raise RuntimeError("Wire a Qwen-Image 16-channel latent into this node") from e
raise Prevention
- Match decode nodes to the model family that produced the latents
- Never reuse SD/SDXL 4-channel latents in Qwen nodes
- Verify latent channel count when importing workflows from other versions
When it happens
Trigger: Connecting latents from a non-Qwen model (e.g. SD 4-channel) to the Qwen PiD decode node; passing a 5D latent whose ndim/shape wasn't reduced; loading a stale latents file from another pipeline.
Common situations: Mixing model families in one graph (SDXL denoise -> Qwen decode); upgrading InvokeAI where channel conventions changed; hand-edited workflows with mismatched latent nodes.
Related errors
- Qwen-Image PiD decode expected a single temporal frame, got
- Model '{model_key}' is not a TextLLM model (got {model_confi
- Model '{model_key}' is not a LLaVA OneVision model (got {mod
- No VAE source provided. Standalone safetensors/GGUF models r
- VAE '{vae_config.name}' is not compatible with Krea-2. Selec
AI-assisted analysis of invoke-ai/InvokeAI@0b6a024f2f (2026-08-29).
Data as JSON: /api/errors/b0abdc5751cc02d9.
Report an issue: GitHub.