2014-02-06 5 views
7

Я хотел создать файл setup.py, который автоматически разрешает зависимость времени сборки от numpy (для компиляции расширений). Моя первая догадка использовать setup_requires и подкласс класса команды, чтобы импортировать модуль Numpy:Почему setup_requires не работает правильно для numpy?

from setuptools import setup, Extension 
from distutils.command.build import build as _build 

class build(_build): 
    def run(self): 
     import numpy 
     print(numpy.get_include()) 
     _build.run(self) 

setup(
    name='test', 
    version='0.0', 
    description='something', 
    cmdclass={'build':build}, 
    setup_requires=['numpy'], 
) 

Теперь работает python setup.py build успешно компилирует NumPy, но затем выходит из строя (внутри build.run) с:

AttributeError: 'module' object has no attribute 'get_include' 

Однако, если повторная работа с той же командой, команда теперь успешно (и не нужно перекомпилировать numpy).

Я тестировал это на python {2.6,2.7,3.3} с и без virtualenv на довольно недавних версиях setuptools.

Я видел workaround using pkg_resources.resource_filename, который, кажется, работает очень хорошо, если все, что мы хотим, это каталог include. EDIT: работает только на python2!

Но все же, мне любопытно. Какие предостережения имеют использование setup_requires? Каковы могут быть причины, по которым он не работает должным образом для numpy? Для некоторых более простых модулей, похоже, проблем нет.

ответ

7

Разобрался, что собственно инициализация модуля Numpy предотвращается проверкой для __NUMPY_SETUP__ внутри numpy/__init__.py:

if __NUMPY_SETUP__: 
    import sys as _sys 
    _sys.stderr.write('Running from numpy source directory.\n') 
    del _sys 
else: 
    # import subodules etc. (main branch) 

Это глобальное состояние не сбрасывается Setuptools после установки. Следующие работы:

... 
def run(self): 
    __builtins__.__NUMPY_SETUP__ = False 
    import numpy 
    ... 
Смежные вопросы