{"record":{"id":"801c66576eb0d2bd","repo":"invoke-ai/InvokeAI","slug":"missing-class-name-or-architectures-field","errorCode":null,"errorMessage":"missing _class_name or architectures field","messagePattern":"missing _class_name or architectures field","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"invokeai/backend/model_manager/configs/identification_utils.py","lineNumber":104,"sourceCode":"    Returns:\n        The class name from the config file.\n\n    Raises:\n        NotAMatch if the config file is missing or does not contain a valid class name.\n    \"\"\"\n\n    if not isinstance(config, dict):\n        config = get_config_dict_or_raise(config)\n\n    try:\n        if \"_class_name\" in config:\n            # This is a diffusers-style config\n            config_class_name = config[\"_class_name\"]\n        elif \"architectures\" in config:\n            # This is a transformers-style config\n            config_class_name = config[\"architectures\"][0]\n        else:\n            raise ValueError(\"missing _class_name or architectures field\")\n    except Exception as e:\n        raise NotAMatchError(f\"unable to determine class name from config file: {config}\") from e\n\n    if not isinstance(config_class_name, str):\n        raise NotAMatchError(f\"_class_name or architectures field is not a string: {config_class_name}\")\n\n    return config_class_name\n\n\ndef raise_for_class_name(config: Path | set[Path] | dict[str, Any], class_name: str | set[str]) -> None:\n    \"\"\"Get the class name from the config file and raise NotAMatch if it is not in the expected set.\n\n    Args:\n        config_path: The path to the config file, or a set of paths to try.\n        class_name: The expected class name, or a set of expected class names.\n\n    Raises:\n        NotAMatch if the class name is not in the expected set.","sourceCodeStart":86,"sourceCodeEnd":122,"githubUrl":"https://github.com/invoke-ai/InvokeAI/blob/0b6a024f2ff6a86bfb953dcdb9cc504ef7397a06/invokeai/backend/model_manager/configs/identification_utils.py#L86-L122","documentation":"NotAMatchError raised by get_class_name_from_config_dict_or_raise when a successfully loaded config dict contains neither a '_class_name' key (diffusers-style configs) nor an 'architectures' key (transformers-style configs), so no architecture marker can be extracted. This is wrapped into NotAMatchError with the 'unable to determine class name' message (1039), whose cause chain shows this ValueError.","triggerScenarios":"get_class_name_from_config_dict_or_raise / raise_for_class_name / from_model_on_disk receiving a config dict (e.g. model_index.json, custom config.json, or a hand-written JSON) lacking both keys — commonly a bare {\"model_type\": ...}-only transformers config or an empty {} dict.","commonSituations":"Custom model exports that omit _class_name; older or minimal transformers configs without 'architectures'; user-authored placeholder config.json; configs trimmed by download managers that only keep model_type.","solutions":["Add \"architectures\": [\"Gemma2ForCausalLM\"] (or the appropriate class) to config.json, or \"_class_name\" for diffusers-style configs","Re-download config.json from the original HuggingFace repo instead of a hand-made one","Point the importer at the correct config file — you may be reading a secondary config (e.g. tokenizer_config.json-style file) that lacks these keys"],"exampleFix":"// before\n{ \"hidden_size\": 2304, \"model_type\": \"gemma2\" }\n// after\n{ \"architectures\": [\"Gemma2ForCausalLM\"], \"hidden_size\": 2304, \"model_type\": \"gemma2\" }","handlingStrategy":"validation","validationCode":"import json\nfrom pathlib import Path\n\ndef config_has_class_name(model_dir: str | Path) -> bool:\n    p = Path(model_dir) / \"config.json\"\n    try:\n        cfg = json.loads(p.read_text(encoding=\"utf-8\"))\n    except (OSError, json.JSONDecodeError):\n        return False\n    archs = cfg.get(\"architectures\")\n    return isinstance(cfg.get(\"_class_name\"), str) or (\n        isinstance(archs, list) and len(archs) > 0 and isinstance(archs[0], str)\n    )","typeGuard":"def extract_class_name(cfg: dict) -> str | None:\n    if isinstance(cfg.get(\"_class_name\"), str):\n        return cfg[\"_class_name\"]\n    archs = cfg.get(\"architectures\")\n    if isinstance(archs, list) and archs and isinstance(archs[0], str):\n        return archs[0]\n    return None","tryCatchPattern":"try:\n    import_model(model_dir)\nexcept NotAMatchError as e:\n    if \"unable to determine class name\" in str(e):\n        print(\"config.json lacks _class_name/architectures — restore the original from the HF repo\")","preventionTips":["Never hand-write config.json from scratch — copy it from the source repo","Ensure 'architectures' is a non-empty list of strings, not a string or []","Keep both _class_name (diffusers) and architectures (transformers) when converting between formats"],"tags":["config-file","json","model-import"],"backgroundTag":"missing-config-key","analyzedSha":"0b6a024f2ff6a86bfb953dcdb9cc504ef7397a06","analyzedAt":"2026-08-29T04:46:49.967Z","schemaVersion":2},"datasetVersion":"2026-08-29T07:17:48.351Z"}