我正在尝试在命令python manage.py runserver
之后立即调用函数,这可能是简单的打印。我读了一些东西,发现像def ready(self)
这样的有趣话题
Overriding AppConfig.ready()
或Execute code when Django starts ONCE only?我按照说明进行操作,但对于django 2.1.3版本不起作用。我一次没有得到一次准备好的功能,而我又得到了AppRegistryNotReady exceptions
一堆。我认为服务器启动后的调用功能很常见。它不会给您带来太多麻烦,但我仍然找不到合适的解决方案
更新
我尝试了另一种解决方案
我创建这样的中间件类:
import time
class SimpleMiddleware:
def __init__(self, get_response):
self.get_response = get_response
while True:
print("true")
time.sleep(5)
def __call__(self, request):
response = self.get_response(request)
return response
现在我得到正确的输出,如:
Performing system checks...
System check identified no issues (0 silenced).
January 03, 2019 - 14:10:55
Django version 2.1.3, using settings 'CMS.settings'
Starting development server at http://127.0.0.1:8000/
Quit the server with CTRL-BREAK.
true
true
true
true
true
true
true
.
.
.
答案 0 :(得分:0)
您可以仅在manage.py
末尾,在routes.py
之类的支持文件中添加函数调用,依此类推。但!您表示希望在服务器准备好接收请求时调用该函数。
覆盖AppConfig.ready()
适用于您将AppConfig
子类化并将其添加到应用程序注册表中的情况。从您的问题尚不清楚您是否遵循了这一部分。您可以再次检查自己是否遵循了here的说明,以确保正确完成了该操作。
答案 1 :(得分:0)
编辑:
我仍然不确定您要达到的目标,评论者强调了一些重要的问题。首先,AppRegistryNotReady: Apps aren't loaded yet
错误确实令人沮丧,我对此表示赞赏。我不确定您如何组织项目,因此无法提供确切的解决方案。这可能是组织文件以及从中导入应用程序的AppConfig类的方式。您是否在应用程序包级别__init__.py
中放置了它或任何自定义函数或类,以便从那里导入?如果是这样,这似乎会使Django感到困惑,请参阅https://stackoverflow.com/a/34136825/2275482
第二:
我正试图在命令
python manage.py runserver
之后调用函数
我认为我们正在努力了解您要实现的目标以及您是否在将Django应用程序启动时与服务器启动时进行合并。评论者指出,Web服务器完全独立于Django。这是一个独立的过程。
即使与Django捆绑在一起的测试服务器也独立于Django应用。它只是为了方便而放置的简单开发服务器,但这不是必需的,也不应该在生产中使用。 Django的建立符合PEP 333。它可以在AFAIK上与任何与PEP 333兼容的WSGI Web服务器一起使用,无论是Apache和mod_wsgi,gunicorn还是uWSGI等。如果要相对于所使用的服务器执行代码,则需要检查一下服务器文档。
与manage.py
之类的 django-admin
只是一个有助于开发的实用程序,请参见https://docs.djangoproject.com/en/2.1/ref/django-admin/。调用manage.py runserver
时,您正在调用一个实用程序,该实用程序将加载您的应用程序并设置测试服务器。您可以在文件本身中看到执行的流程,正在导入的实用程序等等。该执行流程与使用生产服务器时的执行流程不同。
据我所知,生产服务器从根wsgi.py
文件中加载django应用程序。它甚至不会看manage.py
因此,这又回到了您是否在服务器启动后尝试发布消息的情况,在这种情况下,该消息独立于Django还是当Django应用程序启动时?
如果您要在django应用程序启动,启动并加载到服务器后尝试打印内容,则有很多选择。如果确实愿意,您可以编辑并添加到manage.py
中,但除此之外,我不会篡改Django的核心。当使用其他生产服务器时,这将完全被忽略。
如果要编辑无论使用什么服务器都将加载的入口点,则可以编辑项目的wsgi.py
模块或单独的App AppConfig ready()
方法。
如果您要构建独立于Django并在后台连续运行的东西,则正如@ bruno-desthuilliers指出的那样,您需要构建单独的进程,作为cron作业,或者使用celery或django-carrot希望这样做,尽管后者仍与应用程序启动相关联,但可以作为单独的工作人员工作(我认为)。 Django-carrot仅具有非常简单的功能,适用于小型工作。
很抱歉,如果没有任何帮助,我会尽力提供所提供的信息。
当我希望在我的应用程序AppConfig的ready()
方法中运行某些内容时,我遇到了类似的问题。对我来说,这就是在INSTALLED_APPS
设置变量中安装应用程序的方式。
通常,您会像这样注册您的应用程序:
INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'my_app',
]
但是,这将加载基本的AppConfig类来注册您的应用程序。如果您自定义和覆盖应用程序的AppConfig,以便可以声明自己的ready()
方法,该方法将在实例化应用程序后立即执行,则需要直接在INSTALLED_APPS
中引用覆盖的AppConfig
所以
INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'my_app.apps.MyAPPConfig', # MyAppConfig is the config class that inherits from AppConfig
]
或者,如果您不希望在通过AppConfig加载特定应用程序时执行此操作,则不要通过ready()
方法加载,而是从字面上看,当项目加载到服务器中时,您可以在其中放置一个应用加载后,将项目wsgi.py
模块
即
application = get_wsgi_application()
print('Hello World')
希望有帮助