two QuerySets - merge/join on common foreign key of third model

无人久伴 提交于 2019-12-13 02:48:22

问题


I am now querying - independent of each other - the Models Price and Duration (scroll down for the model definition) through several filters. Finally, I want to merge Price and Duration Querysets so that one price is associated with the specific duration. Example:

Price - in QuerySet _prices:

id | provider | servicelevel | price | currency
1  | 1        | 1            | 10    | 1
2  | 1        | 1            | 20    | 2
3  | 2        | 2            | 15    | 1

Duration - in QuerySet _duration:

id | servicelevel | country_in | country_out | duration | duration_details
1  | 1            | 83         | 236         | 5        | 'only on working days'
2  | 2            | 83         | 236         | 3        | 'Mon-Thu'

What I need to have: Price + Duration joined on Servicelevel

id | provider | servicelevel | price | currency | duration | duration_details
1  | 1        | 1            | 10    | 1        | 5        | 'only on working days'
2  | 1        | 1            | 20    | 2        | 5        | 'only on working days'
3  | 2        | 2            | 15    | 1        | 3        | 'Mon-Thu'

I've played around with annotate(), extra(), but did not find a solution.

Models:

class Price(models.Model):
    ...
    provider = models.ForeignKey(Provider)
    servicelevel = models.ForeignKey(Servicelevel)
    price = models.DecimalField(max_digits=8, decimal_places=2)
    currency = models.ForeignKey('api.Currency')
    ...

class Servicelevel(models.Model):
    name = models.CharField(max_length=200)
    provider = models.ForeignKey(Provider)
    terms = models.TextField(blank=True)
    insurance = models.BooleanField(default=False)
    ...
class Duration(models.Model):
    servicelevel = models.ForeignKey(Servicelevel)
    country_out = models.ForeignKey('Country', related_name='duration_out_country_relation', null=True)
    country_in = models.ForeignKey('Country', related_name='duration_out_country_relation', null=True)
    duration = models.IntegerField()
    duration_details = models.TextField(blank=True)
    ...

KH


回答1:


I have two QuerySets: One of Price, and one of Duration. In the Price QuerySet, there are n prices with one Servicelevel each. In the Duration QuerySet, there are n rows with Servicelevel unique. I want to add the data of the Duration QuerySet to the Price QuerySet

I think as this is for display purposes, you need to restructure your data:

results = {}

for p in price_queryset:
   results.setdefault(p.pk, []).append(p)
   for d in duration_queryset.filter(servicelevel=p.servicelevel):
       results[p.pk].append(d)



回答2:


If Duration and Servicelevel are one-to-one, then you could refactor your data model. If they are not, do you want every permutation in the final report?

Check out the _set "backward" relationship manager:

https://docs.djangoproject.com/en/dev/topics/db/queries/#following-relationships-backward



来源:https://stackoverflow.com/questions/20321137/two-querysets-merge-join-on-common-foreign-key-of-third-model

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!