{"record":{"id":"fd125a3ac6d44019","repo":"deepfakes/faceswap","slug":"extractor-type-is-not-a-valid-plugin-type-selec","errorCode":null,"errorMessage":"{extractor_type} is not a valid plugin type. Select from {list(cls.extract_plugins)}","messagePattern":"(.+?) is not a valid plugin type\\. Select from (.+?)","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"plugins/plugin_loader.py","lineNumber":224,"sourceCode":"        ----------\n        extractor_type\n            The type of extractor to return the plugins for\n        add_none\n            Append \"none\" to the list of returned plugins. Default: False\n        extend_plugin\n            Some plugins have configuration options that mean that multiple 'pseudo-plugins'\n            can be generated based on their settings. An example of this is the bisenet-fp mask\n            which, whilst selected as 'bisenet-fp' can be stored as 'bisenet-fp-face' and\n            'bisenet-fp-head' depending on whether hair has been included in the mask or not.\n            ``True`` will generate each pseudo-plugin, ``False`` will generate the original\n            plugin name. Default: ``False``\n\n        Returns\n        -------\n        A list of the available extractor plugin names for the given type\n        \"\"\"\n        if extractor_type not in cls.extract_plugins:\n            raise ValueError(f\"{extractor_type} is not a valid plugin type. Select from \"\n                             f\"{list(cls.extract_plugins)}\")\n        plugins = [x.split(\".\")[-2].replace(\"_\", \"-\") for x in cls.extract_plugins[extractor_type]]\n        if extend_plugin and extractor_type == \"mask\":\n            extendable = [\"bisenet-fp\", \"custom\"]\n            for plugin in extendable:\n                if plugin not in plugins:\n                    continue\n                plugins.remove(plugin)\n                plugins.extend([f\"{plugin}_face\", f\"{plugin}_head\"])\n        plugins = sorted(plugins)\n        if add_none:\n            plugins.insert(0, \"none\")\n        return plugins\n\n    @staticmethod\n    def get_available_models() -> list[str]:\n        \"\"\"Return a list of available training models\n","sourceCodeStart":206,"sourceCodeEnd":242,"githubUrl":"https://github.com/deepfakes/faceswap/blob/f530cb7508ae670f6474f8a7d9c4df94705cf96b/plugins/plugin_loader.py#L206-L242","documentation":"Raised by PluginLoader.get_available_extract_plugins when the extractor_type argument is not a key of the extract_plugins registry. This is the list-producing API used by the GUI/CLI to populate plugin dropdowns, and it validates the category with the same ValueError as the loader itself.","triggerScenarios":"Calling PluginLoader.get_available_extract_plugins('invalid') — same category typos as error 50 ('alignment', 'masks' plural, etc.) — typically from custom tooling or scripts that enumerate plugins.","commonSituations":"Custom launchers/scripts enumerating plugins with a guessed category name; code drift after a Faceswap upgrade renamed categories.","solutions":["Pass one of the registry keys printed in the message (align, detect, mask, recognition).","Re-use constants or fetch list(cls.extract_plugins) instead of hard-coding the category string.","Prefer letting the GUI/CLI enumerate plugins rather than reimplementing it."],"exampleFix":"# before\nnames = PluginLoader.get_available_extract_plugins('masks')\n\n# after\nnames = PluginLoader.get_available_extract_plugins('mask')","handlingStrategy":"type-guard","validationCode":"from plugins.plugin_loader import PluginLoader\nassert extractor_type in PluginLoader.extract_plugins, \"invalid extractor type\"","typeGuard":"def is_valid_extractor_type(etype: str) -> bool:\n    from plugins.plugin_loader import PluginLoader\n    return etype in PluginLoader.extract_plugins","tryCatchPattern":null,"preventionTips":["Derive category names from list(cls.extract_plugins) instead of hard-coding strings.","Let the GUI/CLI enumerate plugins; don't reimplement plugin discovery."],"tags":["faceswap","plugin-loader","api-misuse","validation"],"backgroundTag":null,"analyzedSha":"f530cb7508ae670f6474f8a7d9c4df94705cf96b","analyzedAt":"2026-08-15T02:59:26.626Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}