Подтвердить что ты не робот

Способ доступа к файлам ресурсов в python

Каков правильный способ доступа к ресурсам в программах python.

В основном во многих моих модулях python я в конечном итоге пишу код:

  DIRNAME = os.path.split(__file__)[0]

  (...) 

  template_file = os.path.join(DIRNAME, "template.foo")

Что хорошо, но:

  • Он сломается, если я начну использовать пакеты zip python
  • Это шаблонный код.

В Java у меня была функция, которая делала точно то же самое --- но работала, когда код лежал в связке папок и когда он был упакован в файл .jar.

Есть ли такая функция в Python, или есть какой-либо другой шаблон, который я мог бы использовать.

4b9b3361

Ответ 1

Вы хотите посмотреть на использование get_data в stdlib или pkg_resources из setuptools/distribute. Какой из них вы используете, вероятно, зависит от того, используете ли вы дистрибутив для упаковки своего кода в виде яйца.

Ответ 2

Попытка понять, как мы могли бы объединить два аспекта togather

  • Загрузка ресурсов в встроенную файловую систему
  • Упакованные в сжатые файлы

Чтение через быстрый учебник по zipimport: http://www.doughellmann.com/PyMOTW/zipimport/

Я вижу следующий пример:

import sys
sys.path.insert(0, 'zipimport_example.zip')
import os
import zipimport
importer = zipimport.zipimporter('zipimport_example.zip')
module = importer.load_module('example_package')
print module.__file__
print module.__loader__.get_data('example_package/README.txt')

Я думаю, что вывод __file__ является "zipimport_example.zip/example_package/__init__.pyc"

Вам нужно проверить, как он выглядит изнутри.

Но тогда мы всегда могли бы сделать что-то вроде этого:

if ".zip" in example_package.__file__:
    ... 
    load using get_data
else:
    load by building the correct file path

[Edit:] Я попытался немного улучшить пример.

Если пакет импортируется как zip файл, то происходит две вещи:

  • __ file__ содержит ".zip" в этом пути.
  • __ loader__ доступен в пространстве имен

Если эти два условия выполнены, то внутри пакета вы можете сделать:

print __loader__.get_data(os.path.join('package_name','README.txt'))

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

Ответ 3

Я предполагаю, что zipimport стандартный модуль python может быть ответом...

EDIT: ну, а не использование модуля напрямую, но использование sys.path, как показано в примере, может быть хорошим способом:

  • У меня есть zip файл test.zip с одним модулем python test и файлом test.foo внутри
  • проверить, что для модуля zipped python test может быть известно о test.foo, он содержит этот код:

c

import os
DIRNAME = os.path.dirname(__file__)
if os.path.exists(os.path.join(DIRNAME, 'test.foo')):
    print 'OK'
else:
    print 'KO'

Тест выглядит нормально:

>>> import sys
>>> sys.path.insert(0, r'D:\DATA\FP12210\My Documents\Outils\SVN\05_impl\2_tools\test.zip')
>>> import test
OK
>>> 

Таким образом, решение может состоять в том, чтобы зацикливать ваш zip файл для извлечения всех модулей python и добавить их в sys.path; эта часть кода была бы идеально первой, загруженной вашим приложением.