gpt4 book ai didi

python - 使用来自多个相关模型的值创建上下文对象

转载 作者:行者123 更新时间:2023-12-01 01:39:43 25 4
gpt4 key购买 nike

我似乎无法弄清楚这一点。我的 View 采用 Team.id 参数,并且我想返回一个上下文对象,其中每个 User 对象在 User.profile.team< 中具有特定值 以及报告 中的相关日期。我觉得我开始走在正确的轨道上,但缺少一些东西。我的模板的输出包含我试图获取的所有数据,但不是以可以逻辑显示的方式。

基本上,我使用的模型类似于以下内容:

class Reports(models.Model):
user = models.ForeignKey(User, null=True, on_delete=models.PROTECT)
product = models.CharField(max_length=15)
apps_activated = models.IntegerField(blank=True, null=True)
prem_submitted = models.DecimalField(max_digits=30, decimal_places=2)

class Team(models.Model):
name = models.CharField(max_length=255)
leader = models.ForeignKey(User,on_delete=models.PROTECT)

扩展用户配置文件:

class Profile(models.Model):
COORDINATOR = 1
LEADER = 2
ADMIN = 3
ROLE_CHOICES = (
(COORDINATOR, 'Coordinator'),
(LEADER, 'Leader'),
(ADMIN, 'Admin'),
)
user = models.OneToOneField(User, on_delete=models.CASCADE)
team = models.ForeignKey(Team, on_delete=models.PROTECT,null=True)
role = models.PositiveSmallIntegerField(choices=ROLE_CHOICES, null=True, blank=True)

我认为最接近返回所需数据的是以下内容:

team = 1
team_name = Team.objects.get(id=team)
team_users = User.objects.filter(profile__team=team).all()
team_stats = []

for user in team_users:
team_stats.append(Reports.objects.filter(user_id=user.id))

使用如下所示的模板:

{% block content %}
<h1>{{ team }}</h1>
<ul>
{% for user in team_users %}
<li><a href="/reports/user/{{ user.id }}">{{ user.first_name }} {{ user.last_name }}</a></li>
{% endfor %}
</ul>

<ul>
{% for stat in team_stats %}
<li>
{% for line in stat %}
{{ line.product }} {{ line.type }} #etc #etc
{% endfor %}
</li>
{% endfor %}
</ul>

{% endblock %}

我以为我对 prefetch_lated() 有所了解,但无法弄清楚。理想情况下,我只需将一个上下文对象返回到我的模板。

编辑:

如果更清楚的话,此查询返回我尝试传递给模板的结果:

select auth_user.first_name, auth_user.last_name, r.product, r.apps_activated, r.prem_submitted, r.conversion_percentage, r.type
from auth_user
join home_profile
on auth_user.id = home_profile.user_id
join reports_reports as r
on auth_user.id = r.user_id
where home_profile.team_id = 1

它返回如下所示的行:

first_name-last_name-product-apps_activated-prem_submitted-conversion_rate-type    
user_1-user_1_last-product_1-693-139764.00-53.86-type1
user_1-user_1_last-product_2-74-27400.10-0.00-type1
user_1-user_1_last-product_3-102-19782.00-47.00-type2
user_2-user_2_last-product_1-7-2437.70-0.00-type2
user_2-user_2_last-product_2-52-10608.00-42.54-type3
user_2-user_2_last-product_3-260.40-0.00-type3

最佳答案

潜在解决方案 1:

所以,我会执行以下操作。更改 Reports 模型中的 user 以显式链接到 Profile(后者又链接到用户)

class Reports(models.Model):
profile = models.ForeignKey(Profile, null=True, on_delete=models.PROTECT)
product = models.CharField(max_length=15)
apps_activated = models.IntegerField(blank=True, null=True)
prem_submitted = models.DecimalField(max_digits=30, decimal_places=2)

您似乎正在寻找类似 select_related() 的东西。查询,为配置文件添加额外的 ForeignKey 字段:

reports = Reports.objects.select_related('profile')

您可以通过 str(reports.query) 检查生成的 SQL,这应该会产生与您在问题中概述的内容相符的结果。

返回的游标值随后会转换为适当的 ORM 模型实例,以便当您循环这些报告时,您可以通过相关表自己的对象访问相关表的值。然而,这些沿着预先选择的前向关系的访问不会导致额外的数据库命中:

{% for report in reports %}
{{ report.profile.user.username }}
{{ report.product }}
# ...
{% endfor %}

请告诉我您的进展情况,以及我们能否集体讨论出一个更合适的解决方案(如果这个不合适)。

潜在解决方案 2:

也许另一种解决方案,也可能是两种解决方案中最简单的一种,是在您的 Profile 模型与 Reports 之间建立 ManyToMany 关系:

class Profile(models.Model):
COORDINATOR = 1
LEADER = 2
ADMIN = 3
ROLE_CHOICES = (
(COORDINATOR, 'Coordinator'),
(LEADER, 'Leader'),
(ADMIN, 'Admin'),
)
user = models.OneToOneField(User, on_delete=models.CASCADE)
team = models.ForeignKey(Team, on_delete=models.PROTECT,null=True)
role = models.PositiveSmallIntegerField(choices=ROLE_CHOICES, null=True, blank=True)
reports = models.ManyToManyField(Reports, ...)

然后您应该能够在模板中循环用户:

{% for user in users %}
{% for report in user.reports.all %}
{{ report.product }}
{% endfor %}
{% endfor %}

关于python - 使用来自多个相关模型的值创建上下文对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52014056/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com