是否可以将来自多个数据库的多个Django查询集合并为一个查询集?

时间:2019-03-26 14:55:51

标签: django django-models django-rest-framework

我想用django-rest创建一个api来获取事件。例如:我在多个数据库中有一个表事件。对/ events的get请求应该从所有已配置的数据库中读取所有事件,并将所有结果聚合到一个查询集中。然后,我想序列化queryset并将json返回给用户。

在settings.py中的

中,我创建了具有事件表的数据库列表。 我可以通过一次查询从DATABASE_1和DATABASE_2中查询事件。但是,当我尝试将结果汇总到一个循环中时,则只能从DATABASE_2获取事件。因此聚合无法正常工作。

如何将这些查询集聚合为一个?还是有更好的查询多个数据库的解决方案?

settings.py

DATABASES = {
    'default': env.db(),
    'DATABASE_1': env.db('DATABASE_1'),
    'DATABASE_2': env.db('DATABASE_2'),
}

EVENT_DATABASES = [
    'DATABASE_1',
    'DATABASE_2',
]

urls.py

urlpatterns = [
    path('events/', EventView.as_view())
]

event_view.py

class EventView(APIView):
    serializer_class = EventSerializer

    def get_queryset(self):
        last_24_hours = datetime.datetime.today() - datetime.timedelta(1)
        events = Event.objects.none()
        for database in settings.EVENT_DATABASES:
            events |= Event.objects.using(database).filter(updated_at__gte=last_24_hours).exclude(code='OK')
        return events

    def get(self, request, format=None):
        queryset = self.get_queryset()
        serializer = EventSerializer(queryset, many=True)
        return Response(serializer.data)

2 个答案:

答案 0 :(得分:1)

您将要使用itertools.chain

答案 1 :(得分:0)

如果您尝试合并同一模型的查询集,则可以使用|运算符。

merged_queryset = queryset_1 | queryset_2

否则,您最好的朋友是itertools.chain(如上一个答案所述)。链的结果是一个链对象,您可以执行以下操作将其变成列表:

merged_queryset = list(chain(queryset_1, queryset_2))

希望这项帮助!