![](/img/trans.png)
[英]How to add console_script/entry point to setup.py that call a class function python
[英]How to call django.setup() in console_script?
當前的 Django 文檔告訴我:
django.setup() 只能被調用一次。
因此,避免將可重用的應用程序邏輯放在獨立腳本中,以便您必須從應用程序的其他地方的腳本導入。 如果無法避免,請將調用 django.setup() 放在 if 塊中:
if __name__ == '__main__':
import django
django.setup()
來源: “獨立”Django 使用需要調用 django.setup()
我在 setup.py 中使用入口點。 這樣我就沒有__name__ == '__main__'
。
如果使用console_scripts ,如何確保 django.setup() 只被調用一次?
我應該把django.setup()
放在哪里?
我遇到的實際錯誤:Django 掛起。 原因如下: https : //code.djangoproject.com/ticket/27176
我想將我的應用程序移植到當前的 django 版本。 更改為管理命令不是一種選擇,因為其他(第三方應用程序)依賴於我的控制台腳本的存在。
有同樣的問題(或類似的問題)。 我通過執行以下操作解決了它:
[警告:骯臟的解決方案]
if not hasattr(django, 'apps'):
django.setup()
這樣即使多次導入它也只會被調用一次
在這里https://docs.djangoproject.com/en/1.10/_modules/django/#setup我們可以看到django.setup
實際做了什么。
配置設置(這是訪問第一個設置的副作用),配置日志記錄並填充應用程序注冊表。 如果
set_prefix
為 True,則設置線程本地 urlresolvers 腳本前綴。
所以基本上為了確保設置已經完成,我們可以檢查應用程序是否准備就緒並配置了設置
from django.apps import apps
from django.conf import settings
if not apps.ready and not settings.configured:
django.setup()
我在兩個生產 CLI python 包中工作過,在console_scripts
顯式調用django.setup()
。
您應該注意的最重要的事情是env
路徑中的DJANGO_SETTINGS_MODULE
。
你可以在 shell 腳本中設置這個值,甚至可以在你的 python 腳本中加載默認設置。
這是示例:
# setup.py
entry_points={
'my-cli = mypackage.cli:main'
}
.
# cli.py
import logging
from os import environ as env
if not 'DJANGO_SETTINGS_MODULE' in env:
from mypackage import settings
env.setdefault('DJANGO_SETTINGS_MODULE', settings.__name__)
import django
django.setup()
# this line must be after django.setup() for logging configure
logger = logging.getLogger('mypackage')
def main():
# to get configured settings
from django.conf import settings
# do stuffs
if __name__ == '__main__':
main()
因為我喜歡無條件代碼,所以我使用這個解決方案。 就像在 django 文檔中一樣,但是if __name__ == '__pain__'
被避免了。
帶代碼的文件:
# utils/do_good_stuff.py
# This file contains the code
# No `django.setup()` needed
# This code can be used by web apps and console scripts.
from otherlib import othermethod
def say_thank_you():
...
主要文件:
# do_good_stuff_main.py
import django
django.setup()
def say_thank_you_main():
from myapp import do_good_stuff
return do_good_stuff()
設置.py:
'console_scripts': [
'say_thank_you=myapp.do_good_stuff_main:say_thank_you_main',
...
這是我目前的解決方案。 歡迎反饋。 有什么需要改進的嗎?
在 Django 2.2.5(至少)中,設置是在導入時配置的。 django.setup()
配置它們,因為它導入它們。 兩次調用django.setup()
的問題是您將兩次填充settings.INSTALLED_APPS
指定的應用程序,這可能會導致各種問題。
if not apps.ready:
檢查是您應該使用的所有內容:
import django
if not apps.ready:
django.setup()
使用if not (apps.ready or settings.configured):
- 是錯誤的,因為設置可能已在其他地方使用 import 語句進行配置,而應用程序可能仍未填充,因此django.setup()
可能不會在調用時被調用需要。
也就是說,如果你知道你的獨立入口點(例如main.py
),你可以在沒有條件的情況下調用它。 僅當存在實際運行腳本兩次的風險時才需要該條件,也許是通過將您的獨立模塊導入另一個獨立模塊,以便它們都調用 django.setup。 多次導入一個模塊只會運行一次。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.