Как соединить две таблицы с помощью Django без использования необработанного SQL?

Возможно ли программно соединить две таблицы с помощью Django ORM? У меня есть две модели: Темы и Голоса. В моем шаблоне есть список тем, за которые пользователи могут голосовать за/против, как Reddit. Все работает как надо кроме сортировки результатов. Я не могу понять, как сортировать список объектов на основе оценки, которая представляет собой сумму количества голосов каждого объекта. Я могу получить нужные данные из postgres без каких-либо проблем:

select i.id, i.title, i.date_created, s.object_id, s.vote, Sum(vote) 
from topic_topic i, votes s 
where i.id = s.object_id 
group by 1, 2, 3, 4, 5 
order by sum DESC;

Он возвращает желаемые результаты:

id | title  |         date_created          | object_id | vote | sum 

11 | sdfg   | 2012-06-04 23:30:17.805671-07 |        11 |    1 |   2

 1 | test   | 2012-05-13 17:03:24.206092-07 |         1 |    1 |   2

 3 | asdf   | 2012-05-13 19:23:15.059135-07 |         3 |    1 |   2

 2 | adsf   | 2012-05-13 19:21:34.180905-07 |         2 |    1 |   2

12 | 11     | 2012-06-04 23:30:54.759158-07 |        12 |    1 |   2

 9 | asfd   | 2012-05-24 00:26:26.705843-07 |         9 |   -1 |  -1

 4 | asdf   | 2012-05-14 19:59:52.450693-07 |         4 |   -1 |  -2

Проблема в том, что я не уверен, как получить это как набор запросов. На данный момент я использую для отображения объектов следующее:

topic_list = Topic.objects.all()

Все отображается так, как я хотел бы, за исключением порядка сортировки. Я хотел бы, чтобы наивысший балл отображался первым.

Ресурсы, которые я уже просматривал: https://docs.djangoproject.com/en/dev/topics/db/managers/#adding-extra-manager-methods
Как сделать запрос как GROUP BY в django?

И многое другое, но мне как новому пользователю антиспам не позволяет их добавлять.

Что я пробовал:

Цепочка:

listed_links = list(chain(topic, score))

К сожалению, если я попытался добавить отсортированное значение, это сломалось.

Объединение списков объектов:

topic = Topic.objects.all().values_list('user','id', 'title','slug', 'date_created', 'date_updated',)

score = Vote.objects.values('object_id').annotate(total=Sum('vote')).order_by('-total')

results = []

for topic in topic:
results.append(topic)

for score in score:
results.append(topic)

В результате все объекты, которые я хотел, были объединены в один список, но я не мог понять, как связать theme.idс score.object_id. .

Я также пытался вставить необработанный SQL, но мне кажется, что я делаю это неправильно, и это может привести к внедрению SQL третьей стороной.

Я хотел бы поделиться результатами этого с проектом django-voting. Как я уже сказал, все работает как надо, за исключением того, что я не могу понять, как сортировать по счету desc.

============= Голосование========================

from django.contrib.contenttypes import generic

from django.contrib.contenttypes.models import ContentType

from django.contrib.auth.models import User

from django.db import models

from voting.managers import VoteManager

from voting.VotedObjectsManager import VotedObjectsManager

    SCORES = (
    (+1, u'+1'),
    (-1, u'-1'),
)

class Vote(models.Model):

    """
    A vote on an object by a User.
    """

    user         = models.ForeignKey(User)

    content_type = models.ForeignKey(ContentType)

    object_id    = models.PositiveIntegerField()

    object       = generic.GenericForeignKey('content_type', 'object_id')

    vote         = models.SmallIntegerField(choices=SCORES)

    objects      = VoteManager()


    class Meta:
        db_table = 'votes'
        # One vote per user per object
        unique_together = (('user', 'content_type', 'object_id'),)

    def __unicode__(self):
        return u'%s: %s on %s' % (self.user, self.vote, self.object)

    def is_upvote(self):
        return self.vote == 1

    def is_downvote(self):
        return self.vote == -1

============= Тематическая модель========================

from django.db import models

from datetime import datetime

from tinymce import models as tinymce_models

from django.forms import ModelForm

from django.template.defaultfilters import slugify

from tagging.fields import TagField

from tagging.models import Tag

from django.contrib.auth.models import User

from django.utils.translation import ugettext_lazy as _

from django.contrib.contenttypes.models import ContentType

from django.contrib.contenttypes import generic

from django.core import urlresolvers

    class Topic(models.Model):

    title           = models.CharField(max_length=50)

    slug            = models.SlugField(max_length=50, editable=False)

    topic         = tinymce_models.HTMLField()

    date_created    = models.DateTimeField(editable=False)

    date_updated    = models.DateTimeField(editable=False)

    tags            = TagField()


    def set_tags(self, tags):
        Tag.objects.update_tags(self, tags)    

    def __unicode__(self):
        return self.tags

    def __unicode__(self):
        return self.id

    def __unicode__(self):
        return self.title

5
задан Community 23 May 2017 в 10:28
поделиться