我在正确排序来自数据库的数据时遇到麻烦。

我的设置:我正在广泛使用Django + Django Rest Framework,并使用VueJS作为前端。我有一个数据库表,其中包含带有对用户的ForeignKey引用的消息。这些消息来自不同的联系人(电话号码),我希望能够在对话中对它们进行分组。这样,在前端,我将能够看到一个包含所有带有该phone_number消息的对话盒,在另一个对话盒中具有不同的phone_number等。

我希望它的排列方式是,我希望最新的对话框出现在左上角,第二个最右边,然后继续在右下角显示最近的对话框。

这是Django模型:

class Message(models.Model):
    phone_number = models.CharField(max_length=100, blank=True)
    phone_number_clean = models.CharField(max_length=100, blank=True)
    contact_name = models.CharField(max_length=255, blank=True)
    date_time = models.DateTimeField(null=True)
    body = models.TextField(blank=True)

    user = models.ForeignKey(User)


在我的Django Rest Framework视图文件中,我覆盖了list()方法,如下所示:

queryset = self.filter_queryset(self.get_queryset()).order_by("date_time") # get the data ordered by date_time
serializer = self.get_serializer(queryset, many=True)
data = serializer.data
data.sort(key=itemgetter("phone_number"))
conversation_list = []

for key, group in itertools.groupby(data, lambda item: item["phone_number"]):
    conversation_dict = {}
    messages = [item for item in group][-50:]  # Get only the last 50 messages per phone_number
    conversation_dict["messages"] = messages  # A list of all the messages
    conversation_dict["conversation_key"] = key
    conversation_list.append(conversation_dict)

return Response(conversation_list)


我正在使用itertools.groupby()以便按phone_number对邮件进行分组。因此,我的理解是必须使用data.sort(key=itemgetter("phone_number")),因为如果groupby()记录分散在各处,则phone_number不起作用。不幸的是,正是data.sort()改变了排序方式,我完全失去了原来的order_by("date_time")排序方式。

我已经尝试了很多东西。我尝试在原始呼叫之前和之后都呼叫data.sort(key=itemgger("date_time")。如果我以前叫它,它没有任何作用。如果在之后调用它,则会丢失phone_number排序。我尝试将date_time作为第二个参数传递给data.sort(),但这没有用。我尝试了其他我现在甚至不记得的事情-没有一个产生任何结果。

我已经为此工作了1.5天,但遇到了麻烦。希望您有任何想法,包括如何更好地对数据进行分组以及如何正确进行分组和date_time排序。

万分感谢!

最佳答案

我真的需要开始某种宗教。每次我在SO上发布问题时,我都可以在30分钟内自己回答。

这是我所做的:

QuerySet现在看起来像这样:

queryset = self.filter_queryset(self.get_queryset()).order_by("phone_number_clean", "date_time")


我在conversation_dict循环中添加了另一个groupby()参数:

conversation_dict["last_date"] = messages[-1]["date_time"]


本质上,它只是获取该对话的最后一条消息的日期。

groupby循环之后,我只需执行以下操作:

conversation_list.sort(key=itemgetter("last_date"))


我得到了想要的结果。瞧!

09-11 19:51
查看更多