我的api中有两条路由,如下所示:
http://mywebsite/websites/website_1/annonces/http://mywebsite/websites/website_2/annonces/
我需要制作一个合并这2条路由的ListAPIView,但是每个路由都调用自己的数据库。
两个数据库使用相同的Django模型制作。我制作了两个数据库,因为它更适合我的体系结构。
问题是我的数据库中没有列,它指示记录来自的网站。记录仅通过数据库名称来区分。
我想在一条路径中获得所有记录,但也希望能够在json响应中分辨出它们来自哪个数据库。
class Annonce(models.Model):
annonce_type = models.CharField(max_length=200, blank=True, null=True)
annonce_id = models.CharField(unique=True, max_length=200, blank=True, null=True)
url = models.TextField(blank=True, null=True)
region = models.TextField(blank=True, null=True)
class AnnoncesList(generics.ListAPIView):
authentication_classes = ()
permission_classes = ()
serializer_class = AnnonceListSerializer
pagination_class = LargeResultsSetPagination
filter_backends = (DjangoFilterBackend,)
filterset_fields = ('advert_type', 'asset_type', 'sales_type', 'price', 'area', 'department', 'department_id', 'city', 'postal_code')
def get_queryset(self):
queryset = Annonce.objects.using(self.kwargs["website_name"]).all()
return queryset
答案 0 :(得分:1)
为每个数据库创建查询集,然后使用annotate()
为查询集上的每个记录添加一列website_name
。将查询集连接到一个列表中(选中this)(将击中数据库中的所有项目),确保已正确过滤查询集。
from itertools import chain
from rest_framework.generics import ListAPIView
from rest_framework.response import Response
from django.db.models import Value, CharField
class AnnonceMergedList(ListAPIView):
serializer_class = AnnonceMergedListSerializer
queryset = Annonce.objects.all()
def list(self, request, **kwargs):
# Make the querysets for each database
q1 = self.get_queryset().using('website_1').annotate(website_name=Value('website_1', CharField()))
q2 = self.get_queryset().using('website_2').annotate(website_name=Value('website_2', CharField()))
# Filtering the querysets
q1 = self.filter_queryset(q1)
q2 = self.filter_queryset(q2)
# Merge (hit items on database)
data = list(chain(q1, q2))
serializer = self.get_serializer(data, many=True)
return Response(serializer.data)
此视图的序列化程序必须接收website_name
才能显示记录所来自的网站
class AnnonceMergedListSerializer(serializers.ModelSerializer):
class Meta:
model = Annonce
fields = ('website_name', ...)