在 Django 视图中,我生成了一个线程(threading.Thread 类),该线程又创建了一个由 5 个工作人员组成的多处理池。是的,我知道使用像 Celery 这样的任务队列通常是公认的做事方式,但在这种情况下,我们需要线程/多处理。
线程和每个多进程工作人员都访问数据库中的项目。但是,在 Thread 或 Worker 中对 Django 模型进行任何调用都会导致“django.core.exceptions.AppRegistryNotReady:尚未加载模型”异常。
这是完整的堆栈跟踪:
Process SpawnPoolWorker-2:
Traceback (most recent call last):
File "C:\Python34\lib\multiprocessing\process.py", line 254, in _bootstrap
self.run()
File "C:\Python34\lib\multiprocessing\process.py", line 93, in run
self._target(*self._args, **self._kwargs)
File "C:\Python34\lib\multiprocessing\pool.py", line 108, in worker
task = get()
File "C:\Python34\lib\multiprocessing\queues.py", line 357, in get
return ForkingPickler.loads(res)
File "d:\bryan\Documents\Projects\spreadmodel_3.4_venv\lib\site-packages\djang
o\db\models\fields\__init__.py", line 59, in _load_field
return apps.get_model(app_label, model_name)._meta.get_field_by_name(field_n
ame)[0]
File "d:\bryan\Documents\Projects\spreadmodel_3.4_venv\lib\site-packages\djang
o\apps\registry.py", line 199, in get_model
self.check_models_ready()
File "d:\bryan\Documents\Projects\spreadmodel_3.4_venv\lib\site-packages\djang
o\apps\registry.py", line 131, in check_models_ready
raise AppRegistryNotReady("Models aren't loaded yet.")
django.core.exceptions.AppRegistryNotReady: Models aren't loaded yet.
奇怪的是,我在堆栈跟踪中没有看到我的代码的任何部分。
我已经尝试在 Thread init 中执行 django.setup() ,并且在工人开始的方法开始时,仍然没有成功。
在我的模型中,我从未尝试从数据库中读取任何内容,例如对用户模型执行外键的常见问题。
编辑:
我可以通过将 django.setup 放在 Simulation 类下而不是将其放在 init 方法中,从而使数据库查询在 Thread 中工作。但是我仍然对工人中的查询有疑问。
编辑2:
如果我修改 Python 的 queue.Queue 文件并将 django.setup() 调用放在 get 函数中,一切都会很好。但是,这不是一个有效的解决方案。有任何想法吗?
编辑3:
如果我在 PyCharm 中运行测试,那么与这个问题相关的测试就可以工作。在 PyCharm 之外的普通命令行中运行测试(或从服务器 [django 测试服务器或 CherryPy] 运行视图服务器)会导致上述错误。
如果有帮助,这里是 GitHub 上的 views.py 的链接。
供将来参考(在我们修复错误之后),您可以在提交 b4bbbcf7 上看到奇怪的行为(上面链接)。