Где разместить файл конфигурации в Python?
В режиме разработки у меня есть следующее дерево каталогов:
| my_project/
| setup.py
| my_project/
| __init__.py
| main.py
| conf/
| myproject.conf
Я использую ConfigParser для анализа файла myproject.conf
.
В моем коде легко загрузить файл с хорошим путем: my_project/conf/myproject.conf
Проблема: когда я устанавливаю свой проект с помощью setup.py, файл конфигурации находится (благодаря setup.py) в /etc/my_project/myproject.conf
и моем приложении в /usr/lib/python<version>/site-packages/my_project/
.
Как я могу ссылаться на мой файл my_project/conf/myproject.conf
в моем проекте в режиме "производства" и ссылаться на локальный файл (my_project/conf/myproject.conf
) в режиме "devel".
Кроме того, я хотел бы быть портативным, если это возможно (например, работа над окнами).
Какая хорошая практика для этого?
Ответы
Ответ 1
Вы видели, как работают файлы конфигурации? Читайте в файлах "rc", как их иногда называют. "bashrc", "vimrc" и т.д.
Обычно для файла конфигурации используется многоступенчатый поиск.
-
Локальный каталог. ./myproject.conf
.
-
Домашний каталог пользователя (~user/myproject.conf
)
-
Стандартный системный каталог (/etc/myproject/myproject.conf
)
-
Место, присвоенное переменной окружения (MYPROJECT_CONF
)
Установка Python будет последним местом для просмотра.
config= None
for loc in os.curdir, os.path.expanduser("~"), "/etc/myproject", os.environ.get("MYPROJECT_CONF"):
try:
with open(os.path.join(loc,"myproject.conf")) as source:
config.readfp( source )
except IOError:
pass
Ответ 2
Если вы используете setuptools
, см. главу с использованием файлов данных, отличных от пакета. Не пытайтесь самостоятельно искать файлы.
Ответ 3
Пакет appdirs отлично справляется с поиском стандартного места для установленных приложений на разных платформах. Интересно, будет ли смысл расширять его, чтобы обнаружить или разрешить какой-то "удаленный" статус для разработчиков.
Ответ 4
Другой вариант - сохранить все файлы .cfg
и .ini
в домашнем каталоге, например, "boto".
import os.path
config_file = os.path.join(os.path.expanduser("~"), '.myproject')
Ответ 5
Я не думаю, что есть чистый способ справиться с этим. Вы можете просто проверить наличие локального файла, который будет работать в режиме разработки. В противном случае вернитесь к производственному пути:
import os.path
main_base = os.path.dirname(__file__)
config_file = os.path.join(main_base, "conf", "myproject.conf")
if not os.path.exists(config_file):
config_file = PROD_CONFIG_FILE # this could also be different based on the OS