什么是 Python 鸡蛋缓存 (PYTHON_EGG_CACHE)?

Posted

技术标签:

【中文标题】什么是 Python 鸡蛋缓存 (PYTHON_EGG_CACHE)?【英文标题】:What is the Python egg cache (PYTHON_EGG_CACHE)? 【发布时间】:2011-01-12 15:14:15 【问题描述】:

我刚刚在我的开发机器上从 Python 2.6.1 升级到 2.6.4,在启动 python 脚本时出现以下消息:

无法将文件提取到 egg 缓存

以下错误发生在 试图将文件提取到 Python 鸡蛋缓存:

[Errno 13] 权限被拒绝: '/var/www/.python-eggs'

Python egg 缓存目录是 当前设置为:

/var/www/.python-eggs

也许您的帐户没有 对该目录的写权限?你 可以通过改变缓存目录 设置 PYTHON_EGG_CACHE 环境变量指向一个 可访问的目录。

python docs 中没有任何内容,因此我对放置此目录及其用途的最佳实践感到有些茫然。

谁能解释一下 Python 的鸡蛋缓存是什么?

另外,您能否解释一下它与 Python 用来存储鸡蛋的 site-packages 目录为什么/有何不同(据我所知)?

【问题讨论】:

【参考方案1】:

python egg 缓存只是 setuptools 用来存储符合egg specification 的安装包的目录。你可以read more about setuptools here。

此外,如错误消息所述,您可以通过设置 PYTHON_EGG_CACHE=/some/other/dir 在您的环境中指定不同的 egg 缓存目录。最简单的方法是在 ~/.bash_profile 中设置它(假设您使用的是 bash),如下所示:

export PYTHON_EGG_CACHE=/some/other/dir

如果您使用的是 Web 应用程序,您可能需要在 Apache 环境中进行设置。

【讨论】:

我通过编辑 app.yaml 解决了 Google App Engine 的网络服务器中缺少的环境变量,如下所示: env_variables: PYTHON_EGG_CACHE: 'C:\Python27\Lib\site-packages' ***.com/questions/31122337/…【参考方案2】:

Python 鸡蛋是包含 Python 模块和元数据的 zip 压缩包。鸡蛋缓存是存储提取的鸡蛋内容的地方,以便其中包含的 Python 模块可用。

【讨论】:

【参考方案3】:

根据我的调查发现,一些鸡蛋被打包为 zip 文件,并保存在 Python 的 site-packages 目录中。

这些压缩的鸡蛋需要在执行之前解压缩,所以会展开到PYTHON_EGG_CACHE 目录,默认为~/.python-eggs(位于用户的主目录中)。如果这不存在,则会在尝试运行应用程序时导致问题。

有许多修复:

    在用户的主目录中创建一个.python-eggs 目录,并使其对用户可写。 创建一个用于解压的全局目录(例如/tmp/python-eggs)并将环境变量PYTHON_EGG_CACHE设置为该目录。 安装时使用easy_install解压包时使用-Z开关。

【讨论】:

Python 可以访问 .zip 文件中的文件。唯一需要提取它们的时候是当应用程序想要一个文件名而不是一个类似文件的对象时,它可以用于鸡蛋内的资源(或目录)。这通常发生在 Web 服务器等上。 还值得一提的是 .python-eggs 无需在目录中添加执行权限即可获取您的 umask。没有执行权限就无法访问目录,因此您会遇到与上述相同的错误。 我想知道为什么它会默认设置为/var/www/.python-eggs,而不是更标准的地方...... +1 表示选项 3。今天这让我困扰了好几个小时。使用带有 -Z 选项的 easy_install 可以在几秒钟内解决我的问题。 Easy_install,没那么容易。【参考方案4】:

您还可以在安装 .egg 后禁用它。您需要进入站点包目录,提取 .egg,然后将其移动到隐藏文件(或删除它,或其他)。

这是我禁用 mysqldb 模块 .egg 文件的示例,当从 Zabbix 运行 python 脚本时,该文件会导致此错误。

cd /usr/local/lib/python2.7/site-packages 解压 MySQL_python-1.2.3-py2.7-linux-x86_64.egg mv MySQL_python-1.2.3-py2.7-linux-x86_64.egg .MySQL_python-1.2.3-py2.7-linux-x86_64.egg

【讨论】:

我认为您不会通过 PyODBC 获得 .egg,而只是获得 .egg-info.so 如果不是将MySQL_python-1.2.3-py2.7-linux-x86_64.egg移动到.MySQL_python-1.2.3-py2.7-linux-x86_64.egg,而是将解压缩的EGG-INFO文件移动到MySQL_python-1.2.3-py2.7-linux-x86_64.egg-info,这对我有用【参考方案5】:

这是使用其他不错的鸡蛋机制的负面影响。

Eggs 是打包到一个.egg 文件中的包(一个充满文件的目录),以简化分解。

它们存储在/site-packages/ 目录中。

只要 Egg 中存储的文件是 .py 文件,它就可以很好地工作。 Python import 可以从任何类似文件的对象中导入东西,就像它是一个普通文件一样。

但是当像.so 这样的东西碰巧出现在那里时,python 无法向底层操作系统解释它想要加载一个没有物理名称的库。 distutils 作者想到的唯一解决方法是将其解压缩到临时目录中。自然不是/site-packages/,因为/site-packages/对于普通用户是不可写的。

所以你可以

PYTHON_EGG_DIR 设置为/tmp

授予用户www/var/www/.python-eggs的写入权限 (这样文件就不会在每次清理 /tmp 时都被解压缩)或者更好

按照@shalley303的建议解压缩鸡蛋 (并完全避免在运行时解压缩鸡蛋)。

【讨论】:

【参考方案6】:

菲利普 B 奥尔德姆是对的。您可以在代码中添加这些行:

import os  
os.environ['PYTHON_EGG_CACHE'] = '/tmp' # a writable directory 

【讨论】:

【参考方案7】:

一个简单的解决方法是创建目录并提供www-data 访问它。

$ mkdir /var/www/.python-eggs
$ chown www-data:www-data /var/www/.python-eggs

【讨论】:

【参考方案8】:

第一次运行以下命令时,我在 Django 中遇到此错误。

python manage.py sql myproject

我让它像这样工作:

1. In Explorer, view the folder that the error says egg cache directory is set to
2. Delete (or rename) the file mysql_python-1.2.5-py2.7-win32.egg-tmp
3. That's it. The command now works and creates a new file in there. (Haven't tested if I need to do this every time.)

【讨论】:

【参考方案9】:

在任何导入工作之前将其添加到我的源文件的开头

import os
xyz = os.path.join('~', 'Documents', '.cache')
os.environ['PYTHON_EGG_CACHE'] = os.path.expanduser(xyz)

【讨论】:

以上是关于什么是 Python 鸡蛋缓存 (PYTHON_EGG_CACHE)?的主要内容,如果未能解决你的问题,请参考以下文章

Python:为啥有些包作为鸡蛋安装,有些作为“鸡蛋文件夹”安装?

为啥easy_install会提取一些python鸡蛋而不是其他的?

如何创建 Python 鸡蛋文件

从文件而不是鸡蛋运行 Python 包

为 python 项目构建一个***/鸡蛋和所有依赖项

把4个鸡蛋放进两个蓝子里(有一个蓝子可以不放)有几种放法 可以怎么放?