我有两个基本型号SiteData和Showoroom Service,它们具有如下所示的模型结构。
我需要SiteData信息,但如果有匹配的ID,我也想从展示厅服务模型中获取link_type。
到目前为止,我已经尝试了一些事情,没有人得到我需要的东西,实现这个目标的最佳途径是什么?由于
选择相关的
>>> nd = ShowroomService.objects.select_related('site').all()
>>> nd
Traceback (most recent call last):
File "<console>", line 1, in <module>
File "/usr/local/lib/python3.6/site-packages/django/db/models/query.py", line 229, in __repr__
return '<%s %r>' % (self.__class__.__name__, data)
File "/usr/local/lib/python3.6/site-packages/django/db/models/base.py", line 590, in __repr__
u = six.text_type(self)
TypeError: __str__ returned non-string (type SiteData)
结合:
>>> complete_data = site_data | monitoring_data
Traceback (most recent call last):
File "<console>", line 1, in <module>
File "/usr/local/lib/python3.6/site-packages/django/db/models/query.py", line 310, in __or__
combined.query.combine(other.query, sql.OR)
File "/usr/local/lib/python3.6/site-packages/django/db/models/sql/query.py", line 529, in combine
"Cannot combine queries on two different base models."
AssertionError: Cannot combine queries on two different base models.
链接
>>> final_data = chain(monitoring_data, site_data)
>>> for i in final_data:
... '{} {}'.format(i.location,i.link_Type)
...
Traceback (most recent call last):
File "<console>", line 2, in <module>
AttributeError: 'ShowroomService' object has no attribute 'location'
sites.models.py
class SiteData(models.Model):
location = models.CharField(max_length=50)
site_type = models.ForeignKey(SiteTypes, verbose_name="Site Type", \
on_delete=models.PROTECT)
subnet = models.GenericIPAddressField(protocol='IPv4')
routed_subnet = models.GenericIPAddressField(protocol='IPv4', \
verbose_name="Routed Link Subnet", blank=True, null=True)
bgp_as = models.CharField(max_length=6, verbose_name="BGP AS Number")
opening_date = models.DateField(verbose_name="Showroom opening date")
last_hw_refresh_date = models.DateField(verbose_name="Date of latest hardware refresh", \
blank=True, null=True)
is_live = models.BooleanField(default=False, verbose_name="Is this a live site?")
tel = models.CharField(max_length=20, blank=True, null=True)
address = models.CharField(max_length=255, blank=True, null=True)
town = models.CharField(max_length=255, blank=True, null=True)
...
class Meta:
verbose_name = "Site Data"
verbose_name_plural = "Site Data"
ordering = ('location',)
permissions = (
("can_view", "Can View"),
("can_view_mgmt", "Can View Management"),
)
def __str__(self):
return self.location
monitoring.models.py
from sites.models import SiteData
class ShowroomService(models.Model):
site = models.ForeignKey(SiteData, verbose_name="Site", \
on_delete=models.PROTECT)
link_type = models.CharField(max_length=200, blank=True, null=True)
preference = models.CharField(max_length=200, blank=True, null=True)
timestamp = models.DateTimeField(auto_now_add=True, blank=True, null=True)
dashboard = models.BooleanField(default=True, verbose_name="display on monitoring dashboard?")
class Meta:
verbose_name = "Showroom Service Data"
verbose_name_plural = "Showroom Service Data"
def __str__(self):
return self.site
答案 0 :(得分:2)
您可以使用django&#34; s&#34;相关经理&#34;来提取所有相关对象。文档可在此处获取:https://docs.djangoproject.com/en/2.0/ref/models/relations/#related-objects-reference
通过在showroom_service_set
模型上调用SiteData
,您可以获取每个SiteData
的子记录集。
只是为了解释列出的尝试失败的原因:
__str__
方法需要才能返回字符串。如果他们不这样做,你就会得到那个例外。|
用于OR
django中的查询。这段代码试图将查询组合成两种不同类型的模型。location
属性。这是获取附加到SiteData模型的所有ShowroomService模型的链接类型的一大块代码:
for site_data in SiteData.objects.all():
for showroom in site_data.showroom_service_set.all():
print showroom.link_type
我不确定django如何使用相关对象处理骆驼套管,所以showroom_service_set
是我最好的猜测。您可能需要对此进行一些小工作以确定实际集合的调用方式。
编辑:有一些名为prefetch_related的东西。这是一个关于它的SO答案;我认为它会让你找到你想要的东西:https://stackoverflow.com/a/13096423/769971