TL;DR 在我的 django 项目中,我应该把我的“start-a-thread”代码放在哪里,以便在 django 服务器启动后立即运行一个线程?
首先祝大家新年快乐!这是一个新手的问题,所以看起来很愚蠢。感谢您的耐心等待和提前帮助!
背景资料
最近我正在编写一个接收 MQTT 消息的 MQTT 转发程序。我希望用户设置一些规则来处理要转发的消息,所以我选择 django 来构建一个 Web 服务器。用户可以在网页上自行编辑规则。
对于 MQTT 客户端,无论用户是否打开网页,我都需要一个线程来接收 MQTT 消息,因此我无法将其写入 view.py。如果我编写一个 shell 来分别启动 django 服务器和我的脚本,我不确定如何将用户设置从 django 服务器传递到我的 mqtt 客户端脚本。
问题
1.有没有办法一输入python manage.py runserver
就启动后台线程?
2. 用户设置之一是 MQTT 服务器主机,所以一旦用户在网页上更改此条目,后台 MQTT 客户端应该重新启动并连接到新主机。有什么方法可以实现吗?
我做了一些研究,发现一些可能的解决方案是 django-background-tasks
或 Celery
但我不确定这些方法是否正确,而且我认为这个问题太小,无法导入另一个繁重的模块来处理。请给我一些建议!如果您有任何不清楚的地方,请随时问我!
再次感谢你!
最佳答案
我认为您可以做的是在 ready()
中启动线程方法你的AppConfig
在 apps.py
这里是一个简单的例子
# apps.py
from django.apps import AppConfig
from threading import Thread
class TestThread(Thread):
def run(self):
print('Thread running')
class StackConfig(AppConfig):
name = 'stack'
def ready(self):
TestThread().start()
如果您需要应用程序其他部分的代码,请注意您无法在模块级别导入此代码,即,如果您在 apps.py 中尝试类似的操作
#apps.py
from . models import Code
将引发异常:
django.core.exceptions.AppRegistryNotReady: Apps aren't loaded yet
为了避免这种情况,您需要在
ready()
中进行导入。方法:#apps.py
class StackConfig(AppConfig):
name = 'stack'
def ready(self):
from stack.models import Code
TestThread().start()
这在 docs 中有描述.
为了让这一切正常工作,请确保您在 settings.INSTALLED_APPS 中启动您的应用程序,就像这样
'stack.apps.StackConfig',
关于python - django服务器启动时如何启动后台线程?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59541954/