invoke-ai/InvokeAI · error · ValueError

The {model_name} model must be a FLUX.2 Klein pipeline, but

Error message

The {model_name} model must be a FLUX.2 Klein pipeline, but the selected model '{config.name}' is {described}. Its text encoder is incompatible with the Klein transformer. (Its VAE is compatible - this only blocks encoder extraction.)

What it means

_validate_encoder_source raised ValueError because the source pipeline's variant is not one of the FLUX.2 Klein variants mapped in _KLEIN_TO_QWEN3_VARIANT (fails closed for unknown/future variants and for non-Klein pipelines). The text encoder of such a pipeline is incompatible with the Klein transformer; its VAE would be fine, but encoder extraction is blocked.

Source

Thrown at invokeai/app/invocations/flux2_klein_model_loader.py:241

    ) -> None:
        """Validate a Diffusers pipeline used as the *text encoder* source.

        The source's tokenizer + encoder are extracted and paired with *this* model's transformer,
        so they must come from the same Qwen3 family. Mismatched widths produce conditioning that
        only fails as an opaque matmul error deep in denoise, so reject it here where the user still
        gets a clear message. The linear UI (``buildFLUXGraph``) and the standalone-encoder path
        (``_validate_qwen3_encoder_variant``) already enforce the family match; the workflow editor
        lets any FLUX.2 Diffusers pipeline be wired in here, so this is the entry point that closes it.
        """
        config = self._validate_diffusers_format(context, model, model_name)
        source_variant = getattr(config, "variant", None)
        source_qwen3 = _KLEIN_TO_QWEN3_VARIANT.get(source_variant)

        # An allowlist, not "reject [dev]": a future third FLUX.2 variant has to fail closed here
        # the way the [dev] loader's guard already makes it, rather than being silently accepted.
        if source_qwen3 is None:
            described = f"variant '{source_variant.value}'" if source_variant is not None else "not a Klein pipeline"
            raise ValueError(
                f"The {model_name} model must be a FLUX.2 Klein pipeline, "
                f"but the selected model '{config.name}' is {described}. "
                "Its text encoder is incompatible with the Klein transformer. "
                "(Its VAE is compatible - this only blocks encoder extraction.)"
            )

        required_qwen3 = _KLEIN_TO_QWEN3_VARIANT.get(getattr(main_config, "variant", None))
        if required_qwen3 is not None and source_qwen3 != required_qwen3:
            raise ValueError(
                f"Qwen3 encoder variant mismatch: FLUX.2 Klein {main_config.variant.value} requires a "
                f"{required_qwen3.value} encoder, but the {model_name} pipeline '{config.name}' "
                f"({source_variant.value}) carries {source_qwen3.value}. "
                "Select a Klein pipeline from the same family - 4B pairs with 4B, 9B with 9B."
            )

    def _validate_qwen3_encoder_variant(self, context: InvocationContext, main_config: AnyModelConfig) -> None:
        """Validate that the standalone Qwen3 encoder variant matches the FLUX.2 Klein variant.

View on GitHub (pinned to 0b6a024f2f)

Solutions

  1. Choose a FLUX.2 Klein Diffusers pipeline (4B or 9B) as the encoder source
  2. Fix the model's variant metadata in the model manager if it is actually a Klein pipeline but recorded wrong
  3. Extract the text encoder separately and supply it via 'Qwen3 Encoder' instead of pipeline extraction
  4. Catch ValueError and check the variant against _KLEIN_TO_QWEN3_VARIANT before wiring the source

Example fix

// before
loader.qwen3_source_model = flux2_dev_pipeline   # variant not Klein
// after
assert get_variant(context, flux2_klein_pipeline) in KLEIN_VARIANTS
loader.qwen3_source_model = flux2_klein_pipeline
Defensive patterns

Strategy: validation

Validate before calling

cfg = context.models.get_config(source_model)
variant = getattr(cfg, 'variant', None)
if variant not in _KLEIN_TO_QWEN3_VARIANT:
    raise ValueError(f"{cfg.name} is not a Klein pipeline (variant={variant})")

Type guard

def is_klein_pipeline(config) -> bool:
    return getattr(config, 'variant', None) in _KLEIN_TO_QWEN3_VARIANT

Try / catch

try:
    output = loader.invoke(context)
except ValueError as e:
    if 'must be a FLUX.2 Klein pipeline' in str(e):
        loader.qwen3_source_model = select_klein_pipeline(context)
        output = loader.invoke(context)
    else:
        raise

Prevention

When it happens

Trigger: invoke() calls _validate_encoder_source with a model whose main config variant is None (not a Klein pipeline) or a variant with no entry in _KLEIN_TO_QWEN3_VARIANT (e.g. FLUX.2 dev/pro or an unrecognized variant), so source_qwen3 is None.

Common situations: Using a FLUX.2 dev pipeline as the 'Qwen3 Source' for a Klein model; a model record with a missing/unknown variant field; a newly released third FLUX.2 variant not yet in the allowlist.

Related errors


AI-assisted analysis of invoke-ai/InvokeAI@0b6a024f2f (2026-08-29). Data as JSON: /api/errors/efa4515f8c5c1bb1. Report an issue: GitHub.