Django ORM在查询中加入子表

时间:2016-02-28 13:01:39

标签: python django django-orm

我想使用Django ORM。我构建了SQL查询:

select itinerary.id, count(users.home_location_id) from itinerary_itinerary as itinerary left join (select to_applicationuser_id as id, users.home_location_id from custom_auth_applicationuser_friends as friends join custom_auth_applicationuser as users on friends.to_applicationuser_id = users.id where from_applicationuser_id = 28)
    as users on itinerary.location_id = users.home_location_id 
    WHERE user_id = 28 
    GROUP BY itinerary.id, users.home_location_id

有人能告诉我如何从子查询中加入表连接吗?
28是当前user_id 我用的是:

Itinerary.object.filter(user_id=28).extra(
            tables=['(select to_applicationuser_id as id, users.home_location_id from custom_auth_applicationuser_friends as friends join custom_auth_applicationuser as users on friends.to_applicationuser_id = users.id where from_applicationuser_id = 28) as users'],
            where=['itinerary.location_id = users.home_location_id']
        )

但我收到了错误

  

ProgrammingError relation"(选择to_applicationuser_id作为id,   users.home_location_id来自"不存在

UPD

模型(这只是简单的方案):

class ApplicationUser(models.Model):
    name = models.CharField(max_length=255)
    home_location = models.ForeignKey(Location)
    friends = models.ManyToManyFieled('self')

class Location(models.Model):
    loc_name = models.CharFiled(max_length=255)

class Itinerary(models.Model):
    user = models.ForeignKey(ApplicationUser)
    location = models.ForeignKey(Location)

1 个答案:

答案 0 :(得分:1)

当您使用extra添加表时,它们会被添加到from列表中,该列表不接受sql语句。 我认为你不需要在这里使用额外的,你可以使用ORM获得类似的查询,而无需加入select语句。使用过滤和注释的以下代码将提供与我能够理解您的查询相同的结果:

ApplicationUser.objects.filter(
    Q(itinerary__location_id = F('friends__home_location_id')) |
    Q(friends__home_location__isnull=True),
    id=28,                                                    
    ).values_list(
        'itinerary__id', 'friends__home_location_id'
    ).annotate(location_count = Count('friends__home_location_id')
    ).values_list('itinerary__id', 'location_count')
相关问题