Django相关字段的正确使用
Correct Usage of Django Related Fields
Django 模型的一个方面是我根本不了解的相关字段,以及如何正确使用它们。我认为这反映出对 SQL 和一般数据库的理解不足 - 所以我怀疑这对许多 django 用户来说是个问题。
在我当前的代码中,我正在构建一个旅游应用程序,因此我将 Accommodation 作为模型。然后我有路线。这一天的路线最终变成了一堆关系领域,但让我感到困惑的是我需要一个开始住宿和一个结束住宿 - 两个独立的关系。
对我来说,按理来说,我应该可以有一个OneToOneField——start_accom来住宿,然后end_accom来住宿。但是这样做会引发错误。
代码:
class Route(models.Model):
start_accom = models.OneToOneField(
Accommodation,
on_delete=models.CASCADE,
primary_key=True,
)
end_accom = models.OneToOneField(
Accommodation,
on_delete=models.CASCADE,
)
mode_of_travel = models.CharField(max_length=50)
description = models.TextField()
以及当我 运行 django 运行server 时的错误信息:
Performing system checks...
Unhandled exception in thread started by <function check_errors.<locals>.wrapper at 0x103ecdd90>
Traceback (most recent call last):
File "/Users/vernonswanepoel/.virtualenvs/tour/lib/python3.6/site-packages/django/utils/autoreload.py", line 226, in wrapper
fn(*args, **kwargs)
File "/Users/vernonswanepoel/.virtualenvs/tour/lib/python3.6/site-packages/django/core/management/commands/runserver.py", line 121, in inner_run
self.check(display_num_errors=True)
File "/Users/vernonswanepoel/.virtualenvs/tour/lib/python3.6/site-packages/django/core/management/base.py", line 431, in check
raise SystemCheckError(msg)
django.core.management.base.SystemCheckError: SystemCheckError: System check identified some issues:
ERRORS:
company.Route.end_accom: (fields.E304) Reverse accessor for 'Route.end_accom' clashes with reverse accessor for 'Route.start_accom'.
HINT: Add or change a related_name argument to the definition for 'Route.end_accom' or 'Route.start_accom'.
company.Route.end_accom: (fields.E305) Reverse query name for 'Route.end_accom' clashes with reverse query name for 'Route.start_accom'.
HINT: Add or change a related_name argument to the definition for 'Route.end_accom' or 'Route.start_accom'.
company.Route.start_accom: (fields.E304) Reverse accessor for 'Route.start_accom' clashes with reverse accessor for 'Route.end_accom'.
HINT: Add or change a related_name argument to the definition for 'Route.start_accom' or 'Route.end_accom'.
company.Route.start_accom: (fields.E305) Reverse query name for 'Route.start_accom' clashes with reverse query name for 'Route.end_accom'.
HINT: Add or change a related_name argument to the definition for 'Route.start_accom' or 'Route.end_accom'.
System check identified 4 issues (0 silenced).
这个问题,正如它提到的那样,是因为反向关系。你需要 add the related_name
attribute
class Route(models.Model):
start_accom = models.OneToOneField(
Accommodation,
on_delete=models.CASCADE,
primary_key=True,
related_name="accommodation_start"
)
end_accom = models.OneToOneField(
Accommodation,
on_delete=models.CASCADE,
related_name="accommodation_end"
)
mode_of_travel = models.CharField(max_length=50)
description = models.TextField()
Django 模型的一个方面是我根本不了解的相关字段,以及如何正确使用它们。我认为这反映出对 SQL 和一般数据库的理解不足 - 所以我怀疑这对许多 django 用户来说是个问题。
在我当前的代码中,我正在构建一个旅游应用程序,因此我将 Accommodation 作为模型。然后我有路线。这一天的路线最终变成了一堆关系领域,但让我感到困惑的是我需要一个开始住宿和一个结束住宿 - 两个独立的关系。
对我来说,按理来说,我应该可以有一个OneToOneField——start_accom来住宿,然后end_accom来住宿。但是这样做会引发错误。
代码:
class Route(models.Model):
start_accom = models.OneToOneField(
Accommodation,
on_delete=models.CASCADE,
primary_key=True,
)
end_accom = models.OneToOneField(
Accommodation,
on_delete=models.CASCADE,
)
mode_of_travel = models.CharField(max_length=50)
description = models.TextField()
以及当我 运行 django 运行server 时的错误信息:
Performing system checks...
Unhandled exception in thread started by <function check_errors.<locals>.wrapper at 0x103ecdd90>
Traceback (most recent call last):
File "/Users/vernonswanepoel/.virtualenvs/tour/lib/python3.6/site-packages/django/utils/autoreload.py", line 226, in wrapper
fn(*args, **kwargs)
File "/Users/vernonswanepoel/.virtualenvs/tour/lib/python3.6/site-packages/django/core/management/commands/runserver.py", line 121, in inner_run
self.check(display_num_errors=True)
File "/Users/vernonswanepoel/.virtualenvs/tour/lib/python3.6/site-packages/django/core/management/base.py", line 431, in check
raise SystemCheckError(msg)
django.core.management.base.SystemCheckError: SystemCheckError: System check identified some issues:
ERRORS:
company.Route.end_accom: (fields.E304) Reverse accessor for 'Route.end_accom' clashes with reverse accessor for 'Route.start_accom'.
HINT: Add or change a related_name argument to the definition for 'Route.end_accom' or 'Route.start_accom'.
company.Route.end_accom: (fields.E305) Reverse query name for 'Route.end_accom' clashes with reverse query name for 'Route.start_accom'.
HINT: Add or change a related_name argument to the definition for 'Route.end_accom' or 'Route.start_accom'.
company.Route.start_accom: (fields.E304) Reverse accessor for 'Route.start_accom' clashes with reverse accessor for 'Route.end_accom'.
HINT: Add or change a related_name argument to the definition for 'Route.start_accom' or 'Route.end_accom'.
company.Route.start_accom: (fields.E305) Reverse query name for 'Route.start_accom' clashes with reverse query name for 'Route.end_accom'.
HINT: Add or change a related_name argument to the definition for 'Route.start_accom' or 'Route.end_accom'.
System check identified 4 issues (0 silenced).
这个问题,正如它提到的那样,是因为反向关系。你需要 add the related_name
attribute
class Route(models.Model):
start_accom = models.OneToOneField(
Accommodation,
on_delete=models.CASCADE,
primary_key=True,
related_name="accommodation_start"
)
end_accom = models.OneToOneField(
Accommodation,
on_delete=models.CASCADE,
related_name="accommodation_end"
)
mode_of_travel = models.CharField(max_length=50)
description = models.TextField()