【问题标题】:Django API REST return all objects in a modelDjango API REST 返回模型中的所有对象
【发布时间】:2014-10-31 06:30:39
【问题描述】:

我正在使用 django-rest-framework,我有一个 API 可以通过如下过滤器向我返回信息:

http://example.com/api/products?category=clothing&in_stock=True
--this returns me 10 items

但如果我不放置过滤器,它也会返回整个模型数据,这是默认方式。

http://example.com/api/products/
--this returns me more than 100 (all the Model Table)

我怎样才能禁用这个默认操作,我的意思是,我怎样才能使过滤器成为使这个 api 工作所必需的?甚至更好!如何使最后一个 URL 返回一个空的 json 响应?

更新 这是一些代码:

serializers.py

class OEntradaDetalleSerializer(serializers.HyperlinkedModelSerializer):
    item = serializers.RelatedField(source='producto.item')
    descripcion = serializers.RelatedField(source='producto.descripcion')
    unidad = serializers.RelatedField(source='producto.unidad')
    class Meta:
        model = OEntradaDetalle
        fields = ('url','item','descripcion','unidad','cantidad_ordenada','cantidad_recibida','epc')

views.py

class OEntradaDetalleViewSet(BulkUpdateModelMixin,viewsets.ModelViewSet):
    filter_backends = (filters.DjangoFilterBackend,)
    filter_fields = ('cantidad_ordenada','cantidad_recibida','oentrada__codigo_proveedor','oentrada__folio')
    queryset = OEntradaDetalle.objects.all()
    serializer_class = OEntradaDetalleSerializer

urls.py

router2 = BulkUpdateRouter()
router2.register(r'oentradadetalle', OEntradaDetalleViewSet)

urlpatterns = patterns('',
url(r'^api/',include(router2.urls)),
)

网址示例

http://localhost:8000/api/oentradadetalle/?oentrada__folio=E01
THIS RETURNS ONLY SOME FILTERED VALUES

http://localhost:8000/api/oentradadetalle/
THIS RETURNS EVERYTHING IN THE MODEL (I need to remove this or make it return some empty data)

【问题讨论】:

  • 请给出一些代码。
  • 我不知道你为什么需要一些代码,它有默认的 API 行为,我需要重写它。无论如何......我自己的代码有一个更新,我希望你能帮助我。谢谢

标签: django django-rest-framework


【解决方案1】:

我强烈推荐using pagination,以防止任何人返回所有结果(这可能需要一段时间)。

如果您可以节省额外的查询,您可以随时检查过滤和未过滤的查询集是否匹配,如果是,则只返回一个空的查询集。这将在您视图上的 filter_queryset 方法中完成。

def filter_queryset(self, queryset):
    filtered_queryset = super(ViewSet, self).filter_queryset(queryset)

    if queryset.count() === len(filtered_queryset):
        return queryset.model.objects.none()

    return filtered_queryset

这将对原始查询集的计数进行一次额外的查询,如果与过滤后的查询集相同,则将返回一个空查询集。如果查询集实际上被过滤了,它将被返回,结果将是您所期望的。

【讨论】:

  • 这正是我所需要的!!你太棒了@Kevin Brown。非常感谢!
  • 我这里有一个奇怪的情况......这适用于过滤器中的两个或多个对象,我的意思是,我正在按 oentrada__folio 字段过滤,但如果我只有一个,这不起作用因为查询集总是等于过滤查询集,我怎样才能使这个东西与一个条目一起工作?我可以进行查询以计算 ocompra__folio 的数量,如果它是 1,则返回查询集,但是是否有另一种方法不进行另一个查询?
猜你喜欢
  • 2017-10-14
  • 2019-12-09
  • 1970-01-01
  • 2013-07-02
  • 1970-01-01
  • 1970-01-01
  • 2022-01-19
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多