Что настраивает sys.path с Python и когда?

Когда я бегу

import sys 
print sys.path

на моем Mac (Mac OS X 10.6.5, Python 2.6.1) я получаю следующие результаты.

/Library/Python/2.6/site-packages/ply-3.3-py2.6.egg...
/Library/Python/2.6/site-packages/ipython-0.10.1-py2.6.egg
/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python26.zip
/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6
/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/plat-darwin
/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/plat-mac
/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/plat-mac/lib-scriptpackages

/System/Library/Frameworks/Python.framework/Versions/2.6/Extras/lib/python
/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/lib-tk
/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/lib-old
/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/lib-dynload
/Library/Python/2.6/site-packages
/System/Library/Frameworks/Python.framework/Versions/2.6/Extras/lib/python/PyObjC
/System/Library/Frameworks/Python.framework/Versions/2.6/Extras/lib/python/wx-2.8-mac-unicode

Они сгруппированы в 5 категорий.

  • /Library/Python/2.6/site-packages/*.egg
  • /Library/Python/2.6/site-packages
  • Каркасы / Python.framework / Версии / 2.6 / Библиотека / python2.6
  • Каркасы / Python.framework / Версии / 2,6 / Дополнительно / Библиотека / питон
  • PATH из переменной среды PYTHONPATH.

И я могу добавить больше путей, используя код

sys.path.insert(0, MORE_PATH)
  • Какие процедуры устанавливают эти пути и когда?
  • Являются ли некоторые пути встроены в исходный код Python?
  • Возможно ли, что пути, вставленные с sys.path.insert, игнорируются? Мне любопытно, так как с mod_wsgi я обнаружил, что пути не найдены в sys.path.insert. Я попросил еще один пост на этот вопрос.

ADDED

Основываясь на ответе Майкла, я посмотрел на site.py и получил следующий код.

def addsitepackages(known_paths):
    """Add site-packages (and possibly site-python) to sys.path"""
    sitedirs = []
    seen = []

    for prefix in PREFIXES:
        if not prefix or prefix in seen:
            continue
        seen.append(prefix)

        if sys.platform in ('os2emx', 'riscos'):
            sitedirs.append(os.path.join(prefix, "Lib", "site-packages"))
        elif sys.platform == 'darwin' and prefix == sys.prefix:
            sitedirs.append(os.path.join("/Library/Python", sys.version[:3], "site-packages"))

Я также считаю, что имя каталога, в котором есть site.py (/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6 для моего Mac), должно быть встроено в исходный код Python.

7 ответов

Решение

Большая часть материала настроена в Python site.py который автоматически импортируется при запуске интерпретатора (если вы не запустите его с -S опция). Во время инициализации в самом интерпретаторе задается несколько путей (вы можете выяснить, какой из них, запустив python с -S).

Кроме того, некоторые фреймворки (вроде Django, я думаю) модифицируют sys.path при запуске, чтобы удовлетворить их требования.

site Модуль имеет довольно хорошую документацию, закомментированный исходный код и выводит некоторую информацию, если вы запускаете его через python -m site,

Из изучения Python:

sys.path - это путь поиска модуля. Python настраивает его при запуске программы, автоматически объединяя домашний каталог файла верхнего уровня (или пустую строку для обозначения текущего рабочего каталога), любые каталоги PYTHONPATH, содержимое любых путей файлов .pth, которые вы создали, и каталоги стандартной библиотеки. В результате получается список строк с именами каталогов, которые Python ищет при каждом импорте нового файла.

site.py действительно ответы. Я хотел удалить все зависимости от старого Python, который по умолчанию установлен на моем Mac. Это работает довольно хорошо, так как site.py вызывается каждый раз, когда запускается интерпретатор python.

Для Mac я вручную добавил следующую строку в конец main() в /System/Library/Frameworks/Python.framework/Versions/2.7/Extras/lib/python/site.py:

    sys.path =  filter (lambda a: not a.startswith('/System'), sys.path)

Путь имеет следующие части:

  • Пути к ОС, в которых находятся ваши системные библиотеки
  • текущий каталог python начался с
  • переменная среды $PYTHONPATH
  • Вы можете добавить пути во время выполнения.

Пути не игнорируются. Но они не могут быть найдены, и это не вызовет ошибки. sys.path также должен быть добавлен, а не вычитаться из. Джанго не будет удалять пути.

Вы используете системный питон /usr/bin/python,

sys.path устанавливается из системных файлов при запуске Python.

Не трогайте эти файлы, в частности site.py, потому что это может привести к нарушению работы системы.

Однако вы можете изменить sys.path внутри Python, в частности, при запуске:

в ~/.bashrc или ~/.zshrc:

export PYTHONSTARTUP=~/.pythonrc

в ~/.pythonrc:

запишите свои изменения в sys.path.

Эти изменения будут только для вас в интерактивных оболочках.

Для взлома с небольшим риском для системы, установите собственную и более позднюю версию Python.

Также обратите внимание: если PYTHONHOME env var установлен, стандартные библиотеки будут загружаться по этому пути вместо пути по умолчанию, как задокументировано.

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

Добавление к принятому ответу и обращение к комментариям о том, что модуль не должен удалять записи из sys.path:

Это в целом верно, но есть обстоятельства, когда вы можете изменить sys.path удалив записи. Например - и это зависит от Mac; * Следствия nix/Windows могут существовать - если вы создаете Python.framework для включения в ваш собственный проект вы можете игнорировать настройки по умолчанию sys.path записи, которые указывают на систему Python.framework,

У вас есть несколько вариантов:

  1. Взломать site.py как указывает @damirv, или

  2. Добавьте свой собственный sitecustomize модуль (или пакет) для пользовательской платформы, которая достигает того же конечного результата. Как указано в site.py комментарии (для 2.7.6, в любом случае):

    После этих манипуляций с путями делается попытка импортировать модуль с именем sitecustomize, который может выполнять произвольные дополнительные специфичные для сайта настройки. Если этот импорт завершается с ошибкой ImportError, он игнорируется.

Другие вопросы по тегам