2016-11-10 23 views
3

我的Python應用程序可以與pip是安裝正常的方式,或在開發/編輯模式,就像這樣:檢查我的應用程序開發/編輯模式下運行

virtualenv my_app 
source my_app/bin/activate 
pip install -e my_app 

我怎樣才能讓一個函數來反思我的virtualenv並檢查我的應用程序是否在開發/可編輯模式下運行?

sys模塊中有沒有「標誌」?

動機:在開發模式和生產中有不同的配置。

編輯:我比較的virtualenv目錄。

import os 
import sys 

import pkg_resources 

main_pkg = 'my_app' 
package_dir = pkg_resources.resource_filename(main_pkg, '__init__.py') 
virtualenv_dir = os.path.dirname(os.path.dirname(sys.executable)) 
common_path = os.path.commonprefix([package_dir, virtualenv_dir]) 
is_dev_mode = not common_path.startswith(virtualenv_dir) 

我測試,如果package_dir是的virtualenv_dir子目錄:如果它不是一個子目錄,然後我對發展模式。

EDIT2:

有沒有更可靠的解決方案?

我想知道在環境中是否沒有數據/標誌會明確指示我的應用程序正在運行開發模式。

如果另一個依賴關係在開發模式下會發生什麼?

回答

3

pip使用代碼,我們可以判斷這一點:

import pip 
import pkg_resources 

# I've done `pip install -e .` for a git repo I'm working in inside 
# a virtualenv 
distributions = {v.key: v for v in pkg_resources.working_set} 
# >>> distribution 
# pre-commit 0.9.3 (/home/asottile/workspace/pre-commit) 
distribution = distributions['pre-commit'] 

# Below is approximately how `pip freeze` works, see the end of 
# the answer for a simpler approach, still using pip 

# Turn into a pip FrozenRequirement (I'm using pip 9.0.1, it may 
# be different for your version) 
# I've passed an empty list for the second argument (dependency_links) 
# I don't think it's necessary? 
frozen_requirement = pip.FrozenRequirement.from_dist(distribution, []) 

# Query whether the requirement is installed editably: 
print(frozen_requirement.editable) 

這樣做的魔力來自內部PIP一個小功能(pip.utils):

def dist_is_editable(dist): 
    """Is distribution an editable install?""" 
    for path_item in sys.path: 
     egg_link = os.path.join(path_item, dist.project_name + '.egg-link') 
     if os.path.isfile(egg_link): 
      return True 
    return False 

在此的dist是一個pkg_resources分佈(正如我們上面獲得的)。當然,你可以直接使用dist_is_editable功能,而不是通過FrozenRequirement打算:

# With `distribution` as above: 
from pip.utils import dist_is_editable 
print(dist_is_editable(distribution)) # True in my case ;) 
+0

聽起來不錯;-)'pkg_resources.working_set'軟件包的名稱('import pkg_name')或庫名稱(如setup.py中的'name =「lib_name」)的密鑰? –

+0

這些鍵最終會成爲「規範化」的軟件包名稱(所以對於'yaml'你會尋找'pyyaml',對於'pre_commit'你會尋找'pre-commit')。規範化規則遵循https://www.python.org/dev/peps/pep-0440/(PEP440)(儘管通常它最終是'.replace('_',' - ')。lower()') –

+0

@LaurentLAPORTE你對這個問題還有其他問題嗎? –

0

我不確定是否有可靠的方法來確定這一點。事實上,我會建議你不要這樣測試路徑,因爲你可能遇到不同的操作系統或環境中的特殊情況。

有幾個備選方案,我建議改爲:

1)如果這是一個命令行工具,我建議允許通過一個命令行標誌,自定義配置文件配置的加載:

from argparse import ArgumentParser 
import sys 
import json 

parser = ArgumentParser(description='...') 
parser.add_argument('-c', '--config', default='config.json') 

def main(argv): 
    args = parser.parse_args(argv) 
    print('loading config file:', args.config) 
    with open(args.config, 'r') as config: 
     config = json.loads(config.read()) 
    print('loaded config', config) 
    # TODO do something with the config 

if __name__ == '__main__': 
    main(sys.argv[1:]) 

運行帶:python3 test1.py -c config-dev.json

2)如果這不是一個CLI應用程序,你可以實現通過USI類似的事情NG環境變量:

import os 
import json 

os.environ.get('CONFIG', 'config.json') 

def main(): 
    config_file = os.environ.get('CONFIG', 'config.json') 
    print('loading config file:', config_file) 
    with open(config_file, 'r') as config: 
     config = json.loads(config.read()) 
    print('loaded config', config) 
    # TODO do something with the config 

if __name__ == '__main__': 
    main() 

運行:CONFIG=config-dev.json python3 test2.py,或:

export CONFIG=config-dev.json 
python3 test2.py 

你也可以做一個shell腳本,以幫助設置你的開發環境,我們稱之爲customenv

source env/bin/activate 
export CONFIG=config-dev.json 

然後你可以使用這個文件來激活開發環境:

source customenv 

3)如果你真的想在你的開發環境代碼的特殊情況下,可以通過環境變量也指定此:

import os 
is_dev_mode = 'MY_APP_DEV' in os.environ and os.environ['MY_APP_DEV'] == '1' 
if is_dev_mode: 
    print('dev mode!') 

運行與MY_APP_DEV=1 python3 test3.py,或:

export MY_APP_DEV=1 
python3 -m test3.py 

4)更多定製:

import os 
app_mode = os.environ.get('MY_APP_MODE', 'prod') 
print(app_mode) 
+0

我同意你的觀點,但是這不是我想要的。對不起,但是,我真的需要檢查我是否處於*開發*模式。 –

相關問題