如何向控制盘添加其他文件?

2024-05-15 05:22:30 发布

您现在位置:Python中文网/ 问答频道 /正文

如何控制轮子中包含的文件?似乎MANIFEST.in没有被python setup.py bdist_wheel使用。

更新

我错了从源头安装tarball和从轮子安装tarball的区别。源发行版包含在MANIFEST.in中指定的文件,但安装的包只有python文件。无论安装是通过源代码分发、egg还是wheel,都需要执行步骤来标识应安装的其他文件。也就是说,package_data对于附加的包文件是必需的,而data_files对于包之外的文件,比如命令行脚本或系统配置文件。

原题

我在a project中使用python setup.py sdist来构建我的包,MANIFEST.in来控制包含和排除的文件,以及pyromacheck-manifest来确认我的设置。

我最近将其转换为双Python 2/3代码,并添加了一个setup.cfg

[bdist_wheel]
universal = 1

我可以用python setup.py bdist_wheel构建一个轮子,它看起来是一个通用的轮子。但是,它不包括MANIFEST.in中指定的所有文件。

安装了什么?

我挖得更深,现在知道更多关于包装和车轮。以下是我学到的:

我将两个包文件上载到multigtfs project on PyPi

  • multigtfs-0.4.2.tar.gz-源tar球,它包含MANIFEST.in中的所有文件。
  • multigtfs-0.4.2-py2.py3-none-any.whl-所讨论的二进制分布。

我用Python 2.7.5创建了两个新的虚拟环境,并安装了每个包(pip install multigtfs-0.4.2.tar.gz)。这两种环境几乎相同。它们有不同的.pyc文件,它们是“编译”的Python文件。有记录磁盘上不同路径的日志文件。从源tar ball安装包括一个文件夹multigtfs-0.4.2-py27.egg-info,其中详细介绍了安装过程,而wheel安装有一个文件夹multigtfs-0.4.2.dist-info,其中包含了该过程的详细信息。但是,从使用multigtfs项目的代码来看,这两种安装方法没有区别。

显然,我的测试也没有使用.zip文件,因此测试套件将失败:

$ django-admin startproject demo
$ cd demo
$ pip install psycopg2  # DB driver for PostGIS project
$ createdb demo         # Create PostgreSQL database
$ psql -d demo -c "CREATE EXTENSION postgis" # Make it a PostGIS database 
$ vi demo/settings.py   # Add multigtfs to INSTALLED_APPS,
                        # Update DATABASE to set ENGINE to django.contrib.gis.db.backends.postgis
                        # Update DATABASE to set NAME to test
$ ./manage.py test multigtfs.tests  # Run the tests
...
IOError: [Errno 2] No such file or directory: u'/Users/john/.virtualenvs/test/lib/python2.7/site-packages/multigtfs/tests/fixtures/test3.zip'

指定其他文件

根据答案中的建议,我向setup.py添加了一些附加指令:

from __future__ import unicode_literals
# setup.py now requires some funky binary strings
...
setup(
    name='multigtfs',
    packages=find_packages(),
    package_data={b'multigtfs': ['test/fixtures/*.zip']},
    include_package_data=True,
    ...
)

这会将zip文件(以及自述文件)安装到文件夹中,并且测试现在可以正确运行。谢谢你的建议!


Tags: 文件toinpytestdatademosetup
3条回答

可以在setup.py中使用package_datadata_files来指定其他文件,但它们是ridiculously hard to get right (and buggy)

另一种方法是使用MANIFEST.in,并在setup.pysetup()中添加include_package_data=True作为indicated here

使用此指令,MANIFEST.in将用于指定文件,这些文件不仅包括在源tarball/zip中,还包括在wheel和win32安装程序中。这也适用于任何python版本(我在一个从py2.6到py3.6的项目中进行了测试)。

你试过在你的setup.py中使用package_data吗?MANIFEST.in似乎是针对python版本的<;=2.6,我不确定更高版本是否会考虑它。

在探索了https://github.com/pypa/sampleproject之后,他们的MANIFEST.in说:

# If using Python 2.6 or less, then have to include package data, even though
# it's already declared in setup.py
include sample/*.dat

这似乎意味着这种方法已经过时了。同时,在setup.py中声明:

setup(
    name='sample',
    ...
    # If there are data files included in your packages that need to be
    # installed, specify them here.  If using Python 2.6 or less, then these
    # have to be included in MANIFEST.in as well.
    package_data={
        'sample': ['package_data.dat'],
    },
    ...
)

(我不知道他们为什么选择MANIFEST.in中的通配符和setup.py中的文件名。它们引用同一个文件)

这一点,再加上更简单,似乎再次表明package_data路由优于MANIFEST.in方法。好吧,除非你必须支持2.6,也就是说,在这种情况下,我向你祈祷。

MANIFEST.insetup.py中进行任何更改之前,必须删除旧的输出目录。Setuptools正在缓存一些数据,这可能会导致意外的结果。

rm -rf build *.egg-info

如果不这样做,就不指望任何东西能正常工作。

现在这已经不可能了。

  1. 如果您正在构建一个源分发版sdist),那么您可以使用下面的任何方法。

  2. 如果您正在构建一个轮子bdist_wheel),那么include_package_dataMANIFEST.in将被忽略,您必须使用package_datadata_files

包含软件包数据

这是一个很好的选择,但是bdist_wheel并不尊重它。

setup(
    ...
    include_package_data=True
)

# MANIFEST.in
include package/data.json

非包数据的数据文件

这是最灵活的选择,因为您可以将回购中的任何文件添加到sdistbdist_wheel

setup(
    ....
    data_files=[
        ('output_dir',['conf/data.json']),
    ]
    # For sdist, output_dir is ignored!
    #
    # For bdist_wheel, data.json from conf dir in root of your repo 
    # and stored at `output_dir/` inside of the sdist package.
)

包中非python文件的包数据

与上面类似,但是对于bdist_wheel,让我们将数据文件放在包中。它对于sdist是相同的,但是比data_files有更多的限制,因为文件只能从包subdir中获得。

setup(
    ...
    package_data={'package':'data.json'},
    # data.json must be inside of your actual package
)

相关问题 更多 >

    热门问题