Django REST;在多字段上使用queryset来过滤相关字段

时间:2019-05-09 21:02:27

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

我使用的是Django REST框架,无法弄清楚如何过滤查询参考模型/视图时返回的子字段(多字段)的结果。

我有一个Tag模型,该模型通过多方域与Book模型相关。查询标签时,它会返回与其关联的所有书籍。但是,我需要过滤书籍以仅包括当前用户有权访问的书籍。

可以在“书本”视图中对其进行正确过滤,但是我无法弄清楚如何在标签视图中使用它

// Book model:
class BookQuerySet(models.QuerySet):
    def visible_to(self, user):
        if user.can_see_secrets:
            return self
        return self.exclude(secret_book=True)


class Book(models.Model):
    id = models.AutoField(db_column='Id', primary_key=True)
    name = models.CharField(db_column='CatalogNumber', unique=True, max_length=50)
    secret_book = models.IntegerField(db_column='secret', default=False)
    objects = BookQuerySet.as_manager()

    class Meta:
        managed = False
        db_table = 'book'
        app_label = 'core'


// Book view:
class BooksFilteringBackend(filters.BaseFilterBackend):
    def filter_queryset(self, request, queryset, view):
        current_user = request.user
        queryset = queryset.visible_to(current_user)
        return queryset

class BookViewSet(viewsets.ReadOnlyModelViewSet):
    authentication_classes = (TokenAuthentication,)
    permission_classes = (IsAuthenticated,)
    queryset = Book.objects.all()
    filter_backends = (BooksFilteringBackend,)
    serializer_class = BookSerializer

There is a BookSerializer that doesnt do anything interesting

现在上面的方法有效,如果用户查询书本视图,他们只会得到他们应该能够看到的书本。

这是我的问题:

// Tag model
class Tag(models.Model):
    id = models.AutoField(db_column='Id', primary_key=True)
    description = models.CharField(db_column='Description', unique=True, max_length=255)
    books = models.ManyToManyField('core.Book', through='BookTag', related_name='tags')

    class Meta:
        managed = False
        db_table = 'tag'
        app_label = 'tags'

// Tag viewset
class TagViewSet(viewsets.ReadOnlyModelViewSet):
    authentication_classes = (TokenAuthentication,)
    permission_classes = (IsAuthenticated,)
    queryset = Tag.objects.all()
    serializer_class = TagSerializer

// Tag serializer
class TagSerializer(serializers.ModelSerializer):
    id = serializers.ReadOnlyField()
    description = serializers.CharField(max_length=255)
    books = BookSerializer(many=True, read_only=True)

    class Meta:
        model = Tag
        fields = ('id',
                  'description',
                  'books',)

如果我点击标签视图集,则会得到与该标签相关联的所有图书,因为我没有根据上述相同的逻辑将这些图书过滤掉。 如何提取标签时可以使用BookQuerySet或类似的东西。

赞赏任何见解!

1 个答案:

答案 0 :(得分:0)

找到答案:How do you filter a nested serializer in Django Rest Framework?

诀窍是在串行器级别执行此操作。显然,标签序列化程序引用了书籍序列化程序,因此书籍的查询为all(),因此您可以覆盖以下内容:

在我无关紧要的书序列化文件中:

#ADD / Eventually add data

$counter = 2
$endcounter = 11
Write-Host "counter:" $counter

while ($counter -le $endcounter)
{
$countertwo = $counter
$formula = ("=" + "B" + $countertwo + "&" + "" / "")
Write-Host "formula:" $formula
#$counter++
Write-Host "Counter:" $counter
$countertwo = $counter
Write-Host "countertwo:" $countertwo
$WorkSheet.Cells.Item($countertwo,19).Formula = $formula
$counter++
Write-Host "Counter:" $counter
}

现在,当我查询标签端点并将其加载到作品中时,标签会使用此过滤系统。