Can't run Celery task in Django - I either get "AppRegistryNotReady: Apps aren't loaded yet" or "RuntimeError: populate() isn't reentrant"
Can't run Celery task in Django - I either get "AppRegistryNotReady: Apps aren't loaded yet" or "RuntimeError: populate() isn't reentrant"
我正在尝试在 Django 中使用 Celery 设置一个任务,每天 运行 23:00。
app = Celery('App.tasks', broker='redis://localhost')
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "App.settings")
django.setup() <== PROBLEM
@app.on_after_configure.connect
def setup_periodic_tasks(sender, **kwargs):
sender.add_periodic_task(
crontab(hour=23),
calc_average_rating.s(),
)
@app.task
def calc_average_rating(final_content_id):
问题是,在这个函数中,我有 Rating = apps.get_model(app_label='App', model_name='Rating')
,如果我不调用 django.setup()
,那么我会得到 django.core.exceptions.AppRegistryNotReady: Apps aren't loaded yet.
。
但是,如果我调用 django.setup()
,任务 运行 没问题,但我无法执行 manage.py runserver
,因为我得到 RuntimeError: populate() isn't reentrant
。
有什么解决办法吗?
我不确定如何重现您所处的环境,所以这里是我对环境的一些观察,希望它们对您有所帮助
我有一个 Celery()
对象的唯一地方是在一个独立的文件中,保存在“manage.py startproject”生成的包中,
我认为与大多数 Django 用户相比,我布局 Django 应用程序的方式不同寻常,所以要描述它:
# .git/ # top folder is my vcs
# setup.py # packaging for exampleapp
# env/ # python venv created to this service
# exampleapp/ # package generated from startapp
# exampleapp/tasks.py # package generated from startapp
# exampleproject/ # folder generated from startproject
# exampleproject/exampleproject/ # package generated by startproject
# exampleproject/exampleproject/settings.py # generated
# exampleproject/exampleproject/celery.py # created based on celery docs
# exampleproject/exampleproject/celery.py
import os
from celery import Celery
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'exampleproject.settings')
app = Celery('exampleproject')
app.config_from_object('django.conf:settings', namespace='CELERY')
app.autodiscover_tasks()
@app.task(bind=True)
def debug_task(self):
print('Request: {self.request!r}'.format(self=self))
if __name__ == '__main__':
app.start()
然后我开始 celery 作业,如下所示,其中我的 python 虚拟环境文件夹 'env' 是生成的示例项目包
的同级
(
cd exampleproject
../env/bin/python3 -m celery -A exampleproject worker -l INFO
# or
../env/bin/python3 -m celery -A exampleproject beat -l INFO --scheduler django_celery_beat.schedulers:DatabaseScheduler
)
# and for django
./env/bin/python3 exampleproject/manage.py runserver
可能也有兴趣
# exampleapp/tasks.py
from celery import shared_task
@shared_task
def add(x, y):
return x+y
# exampleproject/exampleproject/settings.py
# suffixed to end of generated file
INSTALLED_APPS.extend([
'django_celery_results',
'django_celery_beat',
])
CELERY_TASK_TRACK_STARTED = True
CELERY_TASK_TIME_LIMIT = 30 * 60
CELERY_RESULT_BACKEND = 'django-db'
#CELERY_RESULT_BACKEND = 'django-cache'
对于这些部分,我没有注意到加载入口点有任何问题
我正在尝试在 Django 中使用 Celery 设置一个任务,每天 运行 23:00。
app = Celery('App.tasks', broker='redis://localhost')
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "App.settings")
django.setup() <== PROBLEM
@app.on_after_configure.connect
def setup_periodic_tasks(sender, **kwargs):
sender.add_periodic_task(
crontab(hour=23),
calc_average_rating.s(),
)
@app.task
def calc_average_rating(final_content_id):
问题是,在这个函数中,我有 Rating = apps.get_model(app_label='App', model_name='Rating')
,如果我不调用 django.setup()
,那么我会得到 django.core.exceptions.AppRegistryNotReady: Apps aren't loaded yet.
。
但是,如果我调用 django.setup()
,任务 运行 没问题,但我无法执行 manage.py runserver
,因为我得到 RuntimeError: populate() isn't reentrant
。
有什么解决办法吗?
我不确定如何重现您所处的环境,所以这里是我对环境的一些观察,希望它们对您有所帮助
我有一个 Celery()
对象的唯一地方是在一个独立的文件中,保存在“manage.py startproject”生成的包中,
我认为与大多数 Django 用户相比,我布局 Django 应用程序的方式不同寻常,所以要描述它:
# .git/ # top folder is my vcs
# setup.py # packaging for exampleapp
# env/ # python venv created to this service
# exampleapp/ # package generated from startapp
# exampleapp/tasks.py # package generated from startapp
# exampleproject/ # folder generated from startproject
# exampleproject/exampleproject/ # package generated by startproject
# exampleproject/exampleproject/settings.py # generated
# exampleproject/exampleproject/celery.py # created based on celery docs
# exampleproject/exampleproject/celery.py
import os
from celery import Celery
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'exampleproject.settings')
app = Celery('exampleproject')
app.config_from_object('django.conf:settings', namespace='CELERY')
app.autodiscover_tasks()
@app.task(bind=True)
def debug_task(self):
print('Request: {self.request!r}'.format(self=self))
if __name__ == '__main__':
app.start()
然后我开始 celery 作业,如下所示,其中我的 python 虚拟环境文件夹 'env' 是生成的示例项目包
的同级(
cd exampleproject
../env/bin/python3 -m celery -A exampleproject worker -l INFO
# or
../env/bin/python3 -m celery -A exampleproject beat -l INFO --scheduler django_celery_beat.schedulers:DatabaseScheduler
)
# and for django
./env/bin/python3 exampleproject/manage.py runserver
可能也有兴趣
# exampleapp/tasks.py
from celery import shared_task
@shared_task
def add(x, y):
return x+y
# exampleproject/exampleproject/settings.py
# suffixed to end of generated file
INSTALLED_APPS.extend([
'django_celery_results',
'django_celery_beat',
])
CELERY_TASK_TRACK_STARTED = True
CELERY_TASK_TIME_LIMIT = 30 * 60
CELERY_RESULT_BACKEND = 'django-db'
#CELERY_RESULT_BACKEND = 'django-cache'
对于这些部分,我没有注意到加载入口点有任何问题