Содержание страницы
7. Примеры¶Examples
Эта глава содержит несколько базовых примеров, которые помогут начать работу с distutils. Дополнительную информацию об использовании distutils можно найти в Distutils Cookbook.
См. также
- Кулинарная книга Distutils
Сборник рецептов, показывающих, как получить больше контроля над distutils.
7.1. Распространение чистого Python (по модулям)¶Pure Python distribution (by module)
Если вы распространяете всего несколько модулей, особенно если они не находятся
в определённом пакете, вы можете указать их по отдельности с помощью
параметра py_modules в скрипте setup.
В простейшем случае вам понадобится всего два файла: скрипт setup и
единственный модуль, который вы распространяете, foo.py в этом примере:
<root>/
setup.py
foo.py
(На всех схемах в этом разделе <root> обозначает корневой каталог дистрибутива.) Минимальный скрипт setup для описания этой ситуации будет выглядеть так:
from distutils.core import setup
setup(name='foo',
version='1.0',
py_modules=['foo'],
)
Обратите внимание, что имя дистрибутива задаётся независимо с помощью
параметра name, и нет правила, что оно должно совпадать с
именем единственного модуля в дистрибутиве (хотя это, вероятно, хорошее
соглашение). Однако имя дистрибутива используется для генерации
имён файлов, поэтому следует использовать только буквы, цифры, символы подчёркивания и дефисы.
Поскольку py_modules – это список, вы, конечно, можете указать несколько
модулей, например, если вы распространяете модули foo и bar, ваш
setup может выглядеть так:
<root>/
setup.py
foo.py
bar.py
а скрипт setup может быть таким:
from distutils.core import setup
setup(name='foobar',
version='1.0',
py_modules=['foo', 'bar'],
)
Вы можете поместить исходные файлы модулей в другой каталог, но если у вас достаточно модулей для этого, вероятно, проще указывать модули по пакетам, а не перечислять их по отдельности.
7.2. Распространение чистого Python (по пакетам)¶Pure Python distribution (by package)
Если вам нужно распространять больше пары модулей, особенно если они находятся
в нескольких пакетах, вероятно, проще указывать целые пакеты, а не
отдельные модули. Это работает даже если ваши модули не в пакете; вы
можете просто указать Distutils обрабатывать модули из корневого пакета, и это
будет работать так же, как с любым другим пакетом (за исключением того, что вам не нужен
файл __init__.py).
Скрипт setup из предыдущего примера можно также записать как
from distutils.core import setup
setup(name='foobar',
version='1.0',
packages=[''],
)
(Пустая строка обозначает корневой пакет.)
Если эти два файла перемещены в подкаталог, но остаются в корневом пакете, например:
<root>/
setup.py
src/ foo.py
bar.py
тогда вы по-прежнему указываете корневой пакет, но должны сообщить Distutils, где находятся исходные файлы в корневом пакете:
from distutils.core import setup
setup(name='foobar',
version='1.0',
package_dir={'': 'src'},
packages=[''],
)
Однако чаще требуется распространять несколько модулей в одном
пакете (или в подпакетах). Например, если модули foo и bar
принадлежат пакету foobar, один из способов организовать дерево исходников:
<root>/
setup.py
foobar/
__init__.py
foo.py
bar.py
Фактически это стандартная структура, ожидаемая Distutils, и та, что требует наименьших усилий для описания в вашем скрипте setup:
from distutils.core import setup
setup(name='foobar',
version='1.0',
packages=['foobar'],
)
Если модули нужно поместить в каталоги, не названные по имени пакета, то следует снова использовать параметр package_dir. Например, если каталог src содержит модули пакета foobar:
<root>/
setup.py
src/
__init__.py
foo.py
bar.py
соответствующий скрипт setup будет таким:
from distutils.core import setup
setup(name='foobar',
version='1.0',
package_dir={'foobar': 'src'},
packages=['foobar'],
)
Или же можно поместить модули из главного пакета прямо в корневой каталог дистрибутива:
<root>/
setup.py
__init__.py
foo.py
bar.py
в этом случае скрипт setup будет таким:
from distutils.core import setup
setup(name='foobar',
version='1.0',
package_dir={'foobar': ''},
packages=['foobar'],
)
(Пустая строка также обозначает текущий каталог.)
Если есть подпакеты, они должны быть явно перечислены в packages, но все записи в package_dir автоматически распространяются на подпакеты. (Другими словами, Distutils не сканирует дерево исходных файлов, пытаясь выяснить, какие каталоги соответствуют пакетам Python по наличию файлов __init__.py.) Таким образом, если в стандартной структуре появляется подпакет:
<root>/
setup.py
foobar/
__init__.py
foo.py
bar.py
subfoo/
__init__.py
blah.py
тогда соответствующий скрипт setup будет таким:
from distutils.core import setup
setup(name='foobar',
version='1.0',
packages=['foobar', 'foobar.subfoo'],
)
7.3. Один модуль расширения¶Single extension module
Модули расширения задаются с помощью параметра ext_modules. package_dir не влияет на расположение исходных файлов расширения; он влияет только на исходные файлы чистых модулей Python. Самый простой случай – один модуль расширения в одном C-файле:
<root>/
setup.py
foo.c
Если расширение foo принадлежит корневому пакету, скрипт setup для него может быть таким:
from distutils.core import setup
from distutils.extension import Extension
setup(name='foobar',
version='1.0',
ext_modules=[Extension('foo', ['foo.c'])],
)
Если расширение на самом деле принадлежит пакету, например foopkg, то:
При той же структуре дерева исходных файлов это расширение можно поместить в пакет foopkg, просто изменив имя расширения:
from distutils.core import setup
from distutils.extension import Extension
setup(name='foobar',
version='1.0',
ext_modules=[Extension('foopkg.foo', ['foo.c'])],
)