{"record":{"id":"4bd148c9ea514c03","repo":"pypa/pip","slug":"egg-name-is-empty-this-likely-means-no-egg-coul","errorCode":null,"errorMessage":"\"egg_name\" is empty. This likely means no egg could be found from the \"module_path\".","messagePattern":"\"egg_name\" is empty\\. This likely means no egg could be found from the \"module_path\"\\.","errorType":"exception","errorClass":"OSError","httpStatus":null,"severity":"error","filePath":"src/pip/_vendor/pkg_resources/__init__.py","lineNumber":2047,"sourceCode":"        return timestamp, size\n\n    # FIXME: 'ZipProvider._extract_resource' is too complex (12)\n    def _extract_resource(self, manager: ResourceManager, zip_path) -> str:  # noqa: C901\n        if zip_path in self._index():\n            for name in self._index()[zip_path]:\n                last = self._extract_resource(manager, os.path.join(zip_path, name))\n            # return the extracted directory name\n            return os.path.dirname(last)\n\n        timestamp, size = self._get_date_and_size(self.zipinfo[zip_path])\n\n        if not WRITE_SUPPORT:\n            raise OSError(\n                '\"os.rename\" and \"os.unlink\" are not supported on this platform'\n            )\n        try:\n            if not self.egg_name:\n                raise OSError(\n                    '\"egg_name\" is empty. This likely means no egg could be found from the \"module_path\".'\n                )\n            real_path = manager.get_cache_path(self.egg_name, self._parts(zip_path))\n\n            if self._is_current(real_path, zip_path):\n                return real_path\n\n            outf, tmpnam = _mkstemp(\n                \".$extract\",\n                dir=os.path.dirname(real_path),\n            )\n            os.write(outf, self.loader.get_data(zip_path))\n            os.close(outf)\n            utime(tmpnam, (timestamp, timestamp))\n            manager.postprocess(tmpnam, real_path)\n\n            try:\n                rename(tmpnam, real_path)","sourceCodeStart":2029,"sourceCodeEnd":2065,"githubUrl":"https://github.com/pypa/pip/blob/f399c3718970b1b0e2478dac5296eb62679a9b86/src/pip/_vendor/pkg_resources/__init__.py#L2029-L2065","documentation":"Raised by ZipProvider._extract_resource when self.egg_name is empty/falsy. The egg_name is set during _setup_prefix by walking parent paths looking for a directory matching the .egg naming convention; if none is found, egg_name stays empty. This means the zip-backed resource provider cannot construct a cache path for extraction. Extraction from a bare .zip (not an .egg) is fundamentally unsupported.","triggerScenarios":"Calling resource_filename() or get_resource_filename() on a resource that lives inside a plain .zip archive rather than an .egg/whl, or when the module_path does not have a recognizable egg ancestor directory. The check at line 2046 (`if not self.egg_name`) fires inside _extract_resource which is reached via get_resource_filename -> _extract_resource.","commonSituations":"Bundling dependencies as raw .zip files on sys.path instead of .egg or .whl; running on an import hook that registers a zip importer without egg-style naming; legacy packaging tools that produced non-egg zip archives; calling pkg_resources.resource_filename on a module loaded from a zip.","solutions":["Package the resource inside a properly named .egg or wheel (.whl) archive so the egg_name can be derived from the path.","Use an alternative resource access API (e.g. resource_string / resource_stream) that does not require extraction to the filesystem.","Ensure the archive filename matches the convention ProjectName-version-pyX.Y.egg so _is_egg_path returns True during _setup_prefix.","If you control the packaging, switch to wheel format which pkg_resources recognizes via its dist-info/egg-info metadata."],"exampleFix":"// before (resource lives in plain data.zip on sys.path)\nfrom pkg_resources import resource_filename\npath = resource_filename('mypkg', 'data.csv')  # raises OSError\n\n// after (repackage as wheel/egg, or read from stream)\nfrom pkg_resources import resource_string\ndata = resource_string('mypkg', 'data.csv')","handlingStrategy":"validation","validationCode":"from pkg_resources import ZipProvider\nprovider = resource_manager(provider_of_module)\nif isinstance(provider, ZipProvider) and not getattr(provider, 'egg_name', ''):\n    # cannot extract; use stream access instead\n    data = resource_string('mypkg', 'data.csv')\nelse:\n    path = resource_filename('mypkg', 'data.csv')","typeGuard":"import re\ndef is_valid_egg_path(path: str) -> bool:\n    return bool(re.match(r'^[\\w.]+-\\d[^-]+-py\\d', os.path.basename(path)))\n","tryCatchPattern":"from pkg_resources import resource_filename\ntry:\n    path = resource_filename('mypkg', 'data.csv')\nexcept OSError:\n    # fallback: read as string\n    data = resource_string('mypkg', 'data.csv')\n","preventionTips":["Package resources in .whl or .egg archives, not plain .zip files.","Prefer resource_string/resource_stream over resource_filename when extraction isn't strictly needed.","Test resource access in the deployment environment, not just locally."],"tags":["packaging","zip","extraction","egg","pkg-resources"],"backgroundTag":null,"analyzedSha":"f399c3718970b1b0e2478dac5296eb62679a9b86","analyzedAt":"2026-08-08T23:01:42.227Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}