{"record":{"id":"df2a71e14732f618","repo":"invoke-ai/InvokeAI","slug":"node-title-requires-a-node-base-value-pid-deco","errorCode":null,"errorMessage":"{node_title} requires a {node_base.value} PiD decoder, but the selected decoder is configured for {decoder_base.value}. Connect a PiD decoder whose base matches this node.","messagePattern":"(.+?) requires a (.+?) PiD decoder, but the selected decoder is configured for (.+?)\\. Connect a PiD decoder whose base matches this node\\.","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"invokeai/backend/pid/decode.py","lineNumber":645,"sourceCode":"    caption_mask = toks.attention_mask[:, select_idx].to(torch.bool)\n    return caption_embs, caption_mask\n\n\ndef assert_pid_decoder_matches_base(decoder_base: BaseModelType, node_base: BaseModelType, *, node_title: str) -> None:\n    \"\"\"Guard a base-specific PiD decode node against an incompatible decoder.\n\n    The generic ``pid_decoder_loader`` exposes every PiD decoder through one base-agnostic\n    field, so in the Nodes editor a decoder for the wrong backbone can be connected to a\n    decode node. The decoders share tensor names across backbones, so a mismatch would either\n    silently produce garbage (compatible shapes) or fail deep inside inference (incompatible\n    shapes). Validate up front instead.\n\n    ``node_base`` is the backbone the node feeds to ``PidNet`` — e.g. the Z-Image decode node\n    reuses the FLUX decoder and therefore passes ``BaseModelType.Flux`` here, so a FLUX decoder\n    is accepted for Z-Image while every other pairing must match exactly.\n    \"\"\"\n    if decoder_base != node_base:\n        raise ValueError(\n            f\"{node_title} requires a {node_base.value} PiD decoder, but the selected decoder is \"\n            f\"configured for {decoder_base.value}. Connect a PiD decoder whose base matches this node.\"\n        )\n\n\n__all__ = [\n    \"BACKBONE_DISCRIMINATOR_KEY\",\n    \"PID_CHI_PROMPT\",\n    \"PID_MODEL_MAX_LENGTH\",\n    \"PID_NEGATIVE_PROMPT\",\n    \"PiDDecodeConfig\",\n    \"PiDDecoder\",\n    \"assert_pid_decoder_matches_base\",\n    \"build_pid_net\",\n    \"encode_caption_for_pid\",\n    \"load_pid_decoder\",\n    \"required_pid_net_shapes\",\n]","sourceCodeStart":627,"sourceCodeEnd":663,"githubUrl":"https://github.com/invoke-ai/InvokeAI/blob/0b6a024f2ff6a86bfb953dcdb9cc504ef7397a06/invokeai/backend/pid/decode.py#L627-L663","documentation":"assert_pid_decoder_matches_base enforces that the PiD decoder's backbone base matches the consuming node's required base. Some nodes (e.g. Z-Image decode) deliberately accept FLUX decoders; otherwise the bases must match exactly, otherwise ValueError is raised.","triggerScenarios":"Connecting a PiD decoder whose decoder_base differs from node_base in a node's invoke() — e.g. a Z-Image node wired to an SDXL-configured decoder, or any node receiving a decoder built with a mismatched BaseModelType.","commonSituations":"Selecting the wrong PiD decoder model in the workflow UI; a decoder saved under one base and reused for another; copy-pasting workflows after switching base models.","solutions":["Connect a PiD decoder model whose configured base matches the node's requirement (FLUX decoders also satisfy Z-Image nodes)","Check the decoder's base model metadata and re-select/download the correct variant","Update the node's declared base only if the decoder genuinely supports it"],"exampleFix":"// before\nassert_pid_decoder_matches_base(decoder_base=BaseModelType.SDXL, node_base=BaseModelType.ZImage, node_title=\"Z-Image Decode\")\n// after\nassert_pid_decoder_matches_base(decoder_base=BaseModelType.Flux, node_base=BaseModelType.ZImage, node_title=\"Z-Image Decode\")","handlingStrategy":"validation","validationCode":"from invokeai.backend.util.base_types import BaseModelType\ndecoder_base = pid_decoder.backbone\nallowed = {node_base, BaseModelType.Flux} if node_is_z_image else {node_base}\nassert decoder_base in allowed, f\"decoder base {decoder_base} unusable for {node_title}\"","typeGuard":"def decoder_matches_node(decoder, node_base: BaseModelType) -> bool:\n    if decoder.backbone == node_base:\n        return True\n    return node_base == BaseModelType.ZImage and decoder.backbone == BaseModelType.Flux","tryCatchPattern":"try:\n    assert_pid_decoder_matches_base(decoder_base, node_base, node_title)\nexcept ValueError as e:\n    raise RuntimeError(f\"Workflow misconfigured: {e}\") from e","preventionTips":["Store the decoder's base in model config and display it in workflow UI selection","Validate decoder-base vs node-base at workflow load time, not just at invoke","Document that Z-Image accepts FLUX decoders; all others match exactly"],"tags":["valueerror","model-mismatch","workflow"],"backgroundTag":"model-base-mismatch","analyzedSha":"0b6a024f2ff6a86bfb953dcdb9cc504ef7397a06","analyzedAt":"2026-08-29T04:46:49.967Z","schemaVersion":2},"datasetVersion":"2026-08-29T07:17:48.351Z"}