从兄弟包

时间:2017-07-29 18:51:49

标签: django python-3.x python-import subdirectory siblings

我正在学习django,继续“Tango with Django”

我的项目结构如下:

/django_demo
|-- __init__.py
|-- manage.py
|-- populate.py
|-- settings.py
|.....<other modules>
|
|--/django_demo
|  |-- __init__.py
|  |-- populate_rango.py
|  |...<other modules>
|
|--/rango
|  |-- __init__.py
|  |-- models.py
|  |-- apps.py
|  |....<other modules>

我无法解决两个问题:

查询1 -

populate_rango.py包含以下代码:

import os
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'django_demo.settings')

import django
django.setup()

from django_demo.rango import models

即使我使用了正确的absolute imports符号,models导入也会出现unresolved import错误。关于sibling package imports以及[here] [3]

的文档和类似问题

查询2 -

populate.py包下的/django-demo包含以下代码:

import os
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'django_demo.settings')

import django
django.setup()

from rango import models 

从文档中,必须使用absolute imports点分表示法从子文件夹导入。

上面的代码都没有使用。

,我无法理解
from rango import models

不会抛出未解决的导入错误。

注意1:我已将我的appname包含在INSTALLED_APPS下的\django_demo\settings.py

INSTALLED_APPS = [
    'rango.apps.RangoConfig',
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles', ]

\rango\apps.pyRangoConfig类:

class RangoConfig(AppConfig):
name = 'rango'

注2:  1.我的__init__.py个文件都是空的

  1. 我使用virtualenv和python 3.5.2作为Ubuntu上pydev + eclipse氧气的解释器
  2. UPDATE-1

    如下面的回溯中所示,django.setup()给出了运行时错误:

    Traceback (most recent call last):
      File "/home/sat/coding/python_dev/oxygen_workspace/django_demo/django_demo/populate_rango.py", line 10, in <module>
        django.setup()
      File "/home/sat/coding/flask_dev/venv3/lib/python3.5/site-packages/django/__init__.py", line 22, in setup
        configure_logging(settings.LOGGING_CONFIG, settings.LOGGING)
      File "/home/sat/coding/flask_dev/venv3/lib/python3.5/site-packages/django/conf/__init__.py", line 56, in __getattr__
        self._setup(name)
      File "/home/sat/coding/flask_dev/venv3/lib/python3.5/site-packages/django/conf/__init__.py", line 41, in _setup
        self._wrapped = Settings(settings_module)
      File "/home/sat/coding/flask_dev/venv3/lib/python3.5/site-packages/django/conf/__init__.py", line 110, in __init__
        mod = importlib.import_module(self.SETTINGS_MODULE)
      File "/home/sat/coding/flask_dev/venv3/lib/python3.5/importlib/__init__.py", line 126, in import_module
        return _bootstrap._gcd_import(name[level:], package, level)
      File "<frozen importlib._bootstrap>", line 986, in _gcd_import
      File "<frozen importlib._bootstrap>", line 969, in _find_and_load
      File "<frozen importlib._bootstrap>", line 944, in _find_and_load_unlocked
      File "<frozen importlib._bootstrap>", line 222, in _call_with_frames_removed
      File "<frozen importlib._bootstrap>", line 986, in _gcd_import
      File "<frozen importlib._bootstrap>", line 969, in _find_and_load
      File "<frozen importlib._bootstrap>", line 956, in _find_and_load_unlocked
    ImportError: No module named 'django_demo'
    

    我不明白这个的原因。

    UPDATE-2

    我在类似的行上创建了一个名为 new_django 的新django项目,from rango import models工作正常。

    new_django 结构:

    /new_django
    |-- __init__.py
    |-- manage.py
    |-- populate.py
    |-- settings.py
    |.....<other modules>
    |
    |--/new_django
    |  |-- __init__.py
    |  |-- populate_rango.py
    |  |...<other modules>
    |
    |--/rango
    |  |-- __init__.py
    |  |-- models.py
    |  |-- apps.py
    |  |....<other modules>
    

    populate_rango.py包含以下代码:

    import os
    os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'new_django.settings')
    
    import django
    django.setup()
    
    from rango.models import 
    

    运行时终止,没有任何错误。

    new_django 项目的settings.pyrango/apps.py django_demo 对应的代码相同。

    但是,当我使用像<{1}}这样的绝对导入来引用文档中提到的层次结构from new_django.rango import models时,我会得到以下回溯:

    new_django/rango

    如果相对导入 - Traceback (most recent call last): File "/home/sat/coding/python_dev/oxygen_workspace/new_django/new_django/populate_rango.py", line 12, in <module> from new_django.rango import models ImportError: No module named 'new_django.rango'

    ,也会发生这种情况
    from ..rango import models

    有人可以解释原因:

      UPDATE-1 中,Traceback (most recent call last): File "/home/sat/coding/python_dev/oxygen_workspace/new_django/new_django/populate_rango.py", line 12, in <module> from ..rango import models SystemError: Parent module '' not loaded, cannot perform relative import 出错? UPDATE-2 中,导入django.setup()没有出错,而绝对和相对导入是?

1 个答案:

答案 0 :(得分:0)

由于您正在使用Django版本1.11并且在django_demo项目中有manage.py文件,因此项目目录将加载到此处任何导入的可见路径变量中。

查询2 它运行正常,因为rango模块存在于父django_demo的范围内,即在PATH中加载的项目文件夹。 查询1 它显示导入错误,因为您有2个具有相同名称的模块django_demo导致双重导入问题请参阅here
因此,要解决此问题,请将您的manage.py移到父项目目录django_demo之外。这样,您的相对导入将顺利运行,因为同名模块不会再发生冲突。

|-- manage.py
/django_demo
    |-- __init__.py

    |-- populate.py
    |-- settings.py
    |.....<other modules>
    |
    |--/django_demo
    |  |-- __init__.py
    |  |-- populate_rango.py
    |  |...<other modules>
    |
    |--/rango
    |  |-- __init__.py
    |  |-- models.py
    |  |-- apps.py
    |  |....<other modules>  

现在我们可以从models.py模块导入rango文件,该文件位于populate_rango.py文件中父目录之外的一级

from django_demo.rango import models