如何解决如何从views.py中以Popen()开头的脚本中导入Django模型?
当某个请求到达我的 django 服务器时,我想在不同的进程中启动一个 python 脚本。 我可以成功启动它,但它的导入失败。
在我的 Django 应用程序中,我有一个 views.py
。
在这里,我有一个 ViewSet
和一个 update()
方法,看起来像这样(将片段简化为相关代码):
from . import models # notice this import,which works
def update(self,request,pk=None):
dirname = os.path.dirname(__file__)
filename = os.path.join(dirname,'Process.py')
p = subprocess.Popen(["python",filename],stdout=sys.stdout,stdin=subprocess.PIPE)
这按预期工作:当执行导致调用 update()
的适当请求时,它执行 Process.py
,它是与 views.py
位于同一目录中的文件。
在Process.py
中,我想访问django后端的模型,所以我像以前一样:
from . import models
# more code here
但我收到错误:
ImportError: cannot import name 'models'
为什么此导入在 Process.py
中失败,即使它适用于 views.py
?
我试过了
-
互联网上的一个建议,应该为子进程设置相同的环境,如下所示:
p = subprocess.Popen(["python",env = {'PYTHONPATH': os.pathsep.join(sys.path)},# this is new stdout=sys.stdout,stdin=subprocess.PIPE)
但这根本无法启动python:
Fatal Python error: failed to get random numbers to initialize Python
-
以不同的方式在
Process.py
中编写导入语句:from models import stuff
奇怪的是,这确实导入了
models.py
(是的!)但在更深的兔子洞中失败了:ModuleNotFoundError: No module named '<django project name>'
所述兔子洞从
models.py
中的第一个模型类开始,然后深入到 django 代码中,最后在一些引导程序中结束:Traceback (most recent call last): File "<path to django app>\Process.py",line 1,in <module> from models import stuff File "<path to django app>\models.py",line 3,in <module> class <some model class>(models.Model): File "<path to conda environment>\lib\site-packages\django\db\models\base.py",line 108,in __new__ app_config = apps.get_containing_app_config(module) File "<path to conda environment>\lib\site-packages\django\apps\registry.py",line 253,in get_containing_app_config self.check_apps_ready() File "<path to conda environment>\lib\site-packages\django\apps\registry.py",line 135,in check_apps_ready settings.INSTALLED_APPS File "<path to conda environment>\lib\site-packages\django\conf\__init__.py",line 82,in __getattr__ self._setup(name) File "<path to conda environment>\lib\site-packages\django\conf\__init__.py",line 69,in _setup self._wrapped = Settings(settings_module) File "<path to conda environment>\lib\site-packages\django\conf\__init__.py",line 170,in __init__ mod = importlib.import_module(self.SETTINGS_MODULE) File "<path to conda environment>\lib\importlib\__init__.py",line 126,in import_module return _bootstrap._gcd_import(name[level:],package,level)
看起来 django 以某种方式干扰了我的导入,但我不确定如何以及如何纠正它们。
我如何成功导入(和使用)models.py
的 django 应用程序,该脚本以 subprocess.Popen(...)
from views.py
of {{3} 开头}}?
来自评论
Process.py 是常规 Python 脚本,还是编写为 Django 管理命令?
这是一个常规脚本。 我出于调试目的对其进行了修改,如下所示:
import sys
for p in sys.path:
print(p)
from . import models
如果您从 shell 手动运行脚本会发生什么?同样的错误?
来自外壳 | django views.py 通过 Popen()
|
|
---|---|---|
windows cmd: django-project>python manage.py shell 然后 In [1]: from django-app import Process
|
见上 | 通话详情 |
成功 | ImportError: cannot import name 'models' |
结果 |
包括django-project 路径和空路径 |
包括 django-project/django-app
|
sys.path 的差异 |
解决方法
可能您缺少对 Django 应用程序 的引用,要从中导入所有模型,您必须在 python 脚本中执行:
from <django-app-name>.models import *
,
Process.py
应该是一个 Django Management Command,以便 Django 框架被加载并且 model.py
被 Django 使用。
PYTHONPATH
仍然是必需的,以便 Django 知道基目录在哪里。
从 ["python",filename]
开始,进程可以用 ["python","manage.py",filename]
启动。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。