{"id":"1b0e0992a02c901b","repo":"pytest-dev/pytest","slug":"missing-required-plugins","errorCode":null,"errorMessage":"Missing required plugins: {}","messagePattern":"Missing required plugins: (.+?)","errorType":"validation","errorClass":"UsageError","httpStatus":null,"severity":"error","filePath":"src/_pytest/config/__init__.py","lineNumber":1555,"sourceCode":"        plugin_dist_info = {dist.project_name: dist.version for _, dist in plugin_info}\n\n        missing_plugins = []\n        for required_plugin in required_plugins:\n            try:\n                req = Requirement(required_plugin)\n            except InvalidRequirement:\n                missing_plugins.append(required_plugin)\n                continue\n\n            if req.name not in plugin_dist_info:\n                missing_plugins.append(required_plugin)\n            elif not req.specifier.contains(\n                Version(plugin_dist_info[req.name]), prereleases=True\n            ):\n                missing_plugins.append(required_plugin)\n\n        if missing_plugins:\n            raise UsageError(\n                \"Missing required plugins: {}\".format(\", \".join(missing_plugins)),\n            )\n\n    def _warn_or_fail_if_strict(self, message: str) -> None:\n        strict_config = self.getini(\"strict_config\")\n        if strict_config is None:\n            strict_config = self.getini(\"strict\")\n        if strict_config:\n            raise UsageError(message)\n\n        self.issue_config_time_warning(PytestConfigWarning(message), stacklevel=3)\n\n    def _get_unknown_ini_keys(self) -> set[str]:\n        known_keys = self._parser._inidict.keys() | self._parser._ini_aliases.keys()\n        return self._inicfg.keys() - known_keys\n\n    def parse(self, args: list[str], addopts: bool = True) -> None:\n        # Parse given cmdline arguments into this config object.","sourceCodeStart":1537,"sourceCodeEnd":1573,"githubUrl":"https://github.com/pytest-dev/pytest/blob/98b357f69e380da908740a212288d73b2ee06687/src/_pytest/config/__init__.py#L1537-L1573","documentation":"The required_plugins ini option lists plugins that must be installed (with optional version specifiers) for the test suite to run. During _validate_plugins(), pytest parses each requirement with packaging.Requirement and checks it against installed plugin distributions. If any are missing or fail the version constraint, pytest raises UsageError listing all missing plugins.","triggerScenarios":"Setting required_plugins in pyproject.toml/pytest.ini (e.g., required_plugins = pytest-xdist>=3.0) when the plugin is not installed or the installed version doesn't satisfy the specifier. The requirement name is not found in plugin_dist_info or fails req.specifier.contains().","commonSituations":"Fresh clone without installing dev dependencies, CI matrix running an older plugin version, or a version specifier tightened beyond what's installed. Also, a typo in the requirement string causing InvalidRequirement.","solutions":["Install the missing plugins: pip install <plugin_name><specifier>.","Update the specifier in required_plugins to match the installed version.","Verify installed plugin versions with pip list | grep pytest-<name>.","If the requirement string is malformed, correct it to PEP 508 format."],"exampleFix":"# before (pytest.ini)\n[pytest]\nrequired_plugins = pytest-xdist>=4.0\n# but pytest-xdist 3.x installed\n\n# after (pytest.ini)\n[pytest]\nrequired_plugins = pytest-xdist>=3.0","handlingStrategy":"validation","validationCode":"from packaging.requirements import Requirement, InvalidRequirement\nfrom importlib.metadata import distributions\n\ndef validate_required_plugins(required: list[str]) -> None:\n    installed = {dist.metadata['Name'].lower(): dist.version for dist in distributions()}\n    missing = []\n    for req_str in required:\n        try:\n            req = Requirement(req_str)\n        except InvalidRequirement:\n            missing.append(req_str)\n            continue\n        name = req.name.lower()\n        if name not in installed or not req.specifier.contains(installed[name], prereleases=True):\n            missing.append(req_str)\n    if missing:\n        raise EnvironmentError(f'Missing required plugins: {\", \".join(missing)}')","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Install all required_plugins in CI before running pytest: pip install -r requirements-test.txt.","Keep required_plugins specifiers loose enough to allow patch updates unless a specific feature is needed.","Run pip list and verify versions match specifiers during environment setup."],"tags":["config","plugins","dependency","version-mismatch","usage-error"],"analyzedSha":"98b357f69e380da908740a212288d73b2ee06687","analyzedAt":"2026-08-04T20:26:34.442Z","schemaVersion":2}