Python 打包:数据文件已正确放入 tar.gz 文件中,但未安装到虚拟环境中
Posted
技术标签:
【中文标题】Python 打包:数据文件已正确放入 tar.gz 文件中,但未安装到虚拟环境中【英文标题】:Python Packaging: Data files are put properly in tar.gz file but are not installed to virtual environment 【发布时间】:2012-10-29 17:36:29 【问题描述】:我无法将项目package_fiddler
正确安装到我的虚拟环境中。
我发现MANIFEST.in
负责将非.py文件放入Package_fiddler-0.0.0.tar.gz
,这是在执行python setup.py sdist
时生成的。
然后我做了:
(virt_envir)$ pip install dist/Package_fiddler-0.0.0.tar.gz
但这并没有将数据文件和包安装到/home/username/.virtualenvs/virt_envir/local/lib/python2.7/site-packages
。
我尝试了许多设置参数package_data
、include_package_data
和data_files
的配置,但我似乎每次都使用了错误的配置。
package_data
和/或include_package_data
和/或data_files
的哪种配置可以正确地将package_fiddler
安装到我的虚拟环境中?
项目树
.
├── MANIFEST.in
├── package_fiddler
│ ├── data
│ │ ├── example.html
│ │ └── stylesheets
│ │ └── example.css
│ └── __init__.py
├── README.rst
└── setup.py
setup.py
from setuptools import setup
setup(
name='Package_fiddler',
entry_points=
'console_scripts': ['package_fiddler = package_fiddler:main', ],,
long_description=open('README.rst').read(),
packages=['package_fiddler',])
MANIFEST.in
include README.rst
recursive-include package_fiddler/data *
我尝试过 setup.py 的哪些配置(上面有代码库)?
配置1
添加:
package_data="": ['package_fiddler/data/*',]
配置2
添加:
package_data="": ['*.html', '*.css', '*.rst']
配置3
添加:
include_package_data=True
配置4
添加:
package_data="": ['package_fiddler/data',]
删除:
packages=['package_fiddler',]
配置5(克里斯的建议)
添加:
package_data="data": ['package_fiddler/data',]
删除:
packages=['package_fiddler',]
配置6
添加:
package_data="": ['package_fiddler/data/*',]
删除:
packages=['package_fiddler',]
这些配置都导致/home/username/.virtualenvs/virt_envir/local/lib/python2.7/site-packages
上根本没有安装任何文件。
编辑
仓富敏夫的注意事项:
在我原来的帖子中,为了清楚起见,我使用了最简单的树结构,但实际上我的树看起来更像下面的树。对于那棵树,奇怪的是,如果我只在stylesheets
中放一个__init__.py
,那么texts
文件夹中的所有数据文件也都安装正确!!!这让我很困惑。
树 2(这会以某种方式正确安装所有数据文件!!)
.
├── MANIFEST.in
├── package_fiddler
│ │── stylesheets
| | ├── __init__.py
| | ├── example.css
| | └── other
| | └── example2.css
| |__ texts
| | ├── example.txt
| | └── other
| | └── example2.txt
│ └── __init__.py
├── README.rst
└── setup.py
【问题讨论】:
【参考方案1】:找到了适合我的解决方案here。
使用setuptools==2.0.2
我做了:
setuptools.setup(
...
packages=setuptools.find_packages(),
include_package_data=True, # use MANIFEST.in during install
...
)
【讨论】:
不错!该功能几乎解决了所有问题,我很惊讶这是我第一次听说它。我认为这应该是公认的答案,而不是__init__.py
hack。
这确实是正确的答案,这解决了我所有的问题。 __init__.py
hack 对我不起作用,因为我已经在树中的任何地方放置了 init 文件!此外,init 技巧对于非 python 数据文件也无济于事。
这行得通。注意:答案中没有明确提及,但在 setup.py 中删除 package_data=...
并从数据子目录中删除 __init__.py
文件:此方法不需要它们。 -- 只需使用 MANIFEST.in 并设置 include_package_data=True。我经历的另一件事是来自 MANIFEST.in 的数据文件需要位于 python 代码子树(至少一个检测到的包)下,否则它们不会被安装。
另外请注意,如果您打算稍后在运行时使用os.path.dirname(__file__)
路径算法从 MANIFEST.in 加载文件,添加 zip_safe=False 可能有助于确保正确性(省略 zip_false 将使 bdist_egg 推断它是否通过文件检查安全)docs。见other answer。【参考方案2】:
我个人不喜欢 setuptools 在概念上和实现上混合代码和数据的方式。我认为正是这种实现让你陷入了困境。为了让 setuptools 找到和使用 package_data,它需要将数据驻留在 python 包中。 python包可以是一个目录,但目录中需要有一个__init__.py
文件。所以看起来你需要以下(空的很好)文件:
./package_fiddler/data/__init__.py
./package_fiddler/data/stylesheets/__init__.py
【讨论】:
我之前也遇到过类似的问题,确实需要init.py。 ***.com/questions/3760970 我同意。奇怪的是,嵌套数据文件中只需要一个__init__.py
文件即可在我的帖子的编辑部分中正确安装带有tree2
的项目!
__init__.py
用于使目录可作为模块导入——这对于数据目录来说不是必需的。见my answer here。
@Leo 是的,__init__.py
很糟糕,但是package_data
是 distutils
的功能,setuptools
忽略了它。此外,package_data
在运送sdists
时不起作用。一般来说,python 中的包装是可怕的;人们更喜欢 hacky __init__.py
解决方案而不是不一致的 package_data
解决方案,请让他们。
直到今天我仍然遇到 package_data 未包含在生成的车轮包中的问题。我必须将 manifest.in 与正确的包含一起使用,我必须将空的 __init__.py
文件放在数据文件夹中,并且我需要另外使用 packages 参数显式添加数据文件夹进行设置。否则,我只使用了 ext_modules。圣诞节后的噩梦。【参考方案3】:
在“setup.py”中包含包数据的最简单方法如下:
package_data = '<package name>': ['<path to data file within package dir>']
所以在你的例子中:
package_data = 'package_fiddler': ['data/*', 'data/stylesheets/*']
package_data
是一个字典,其中的键是安装程序中包含的包的名称。这些键下的值应该是包目录中特定文件路径或全局/通配符的列表。
您还需要包含标志:
zip_safe=False
如果您希望能够解析数据的文件系统路径,请在setup(...)
中。否则,您可以使用pkg_resources
执行此操作:http://peak.telecommunity.com/DevCenter/PythonEggs#accessing-package-resources
您绝对不需要“数据”目录中的__init__.py
文件 - 此目录不是模块,也不打算导入。
【讨论】:
是的,这行得通。但是您必须复制MANIFEST.in
和setup.py
中的路径并保持同步。
这,这,这!最糟糕的是,文档让人们相信 MANIFEST.in 是 NOT 需要的,而我还没有找到一种方法让它在没有它的情况下工作。 :(【参考方案4】:
使用
package_data="data": ['package_fiddler/data',]
而不是
packages=['package_fiddler',]
【讨论】:
它没有改变任何东西。当我重新打包后 pip install 项目时,在虚拟环境中仍然找不到任何东西。 您在setup.py
中使用了from setuptools import setup
还是from distutils.core import setup
?【参考方案5】:
这对我有用。希望能帮助到你。
package_data=
"package_fiddler": [
'\*.\*',
'\*/\*.\*',
'\*/\*/\*.\*',
],
,
【讨论】:
我还以为是一种ASCII图形=)以上是关于Python 打包:数据文件已正确放入 tar.gz 文件中,但未安装到虚拟环境中的主要内容,如果未能解决你的问题,请参考以下文章
run build打包之后axios能连上,websocket连不上问题已解决
run build打包之后axios能连上,websocket连不上问题已解决
run build打包之后axios能连上,websocket连不上问题已解决