Python 限制queryset在对数据库的sql调用中查询的django字段

Python 限制queryset在对数据库的sql调用中查询的django字段,python,django,django-rest-framework,django-views,Python,Django,Django Rest Framework,Django Views,我有一个带有blob的表,希望将其排除在对数据库的sql调用中,除非特别要求。开箱即用的django包含queryset中的所有内容。到目前为止,我发现限制该字段的唯一方法是在视图get_queryset()中添加一个函数 并混入序列化程序以限制其检查的字段 class DynamicFieldsMixin(object): def __init__(self, *args, **kwargs): super(DynamicFieldsMixin, self).__ini

我有一个带有blob的表,希望将其排除在对数据库的sql调用中,除非特别要求。开箱即用的django包含queryset中的所有内容。到目前为止,我发现限制该字段的唯一方法是在视图get_queryset()中添加一个函数

并混入序列化程序以限制其检查的字段

class DynamicFieldsMixin(object):
    def __init__(self, *args, **kwargs):
        super(DynamicFieldsMixin, self).__init__(*args, **kwargs)
        if "request" in self.context and self.context['request'] is not None:
            fields = self.context['request'].query_params.get('fields')
            if fields:
                fields = fields.split(',')
                # Drop any fields that are not specified in the `fields` argument.
                allowed = set(fields)
                existing = set(self.fields.keys())
                for field_name in existing - allowed:
                    self.fields.pop(field_name)


class TestSerializer(DynamicFieldsMixin,     rest_serializers.ModelSerializer):
    class Meta:
        model = models.TestData
        fields = '__all__'

这似乎是一个什么做了很多代码。有更简单的方法吗?

Django已经准备好了。使用或

“延迟”将允许您从查询集中排除一组字段:

MyModel.objects.defer('field_i_want_to_exclude')
MyModel.objects.only('field_i_want1', 'field_i_want2')
而仅允许您在queryset上说出所需的字段:

MyModel.objects.defer('field_i_want_to_exclude')
MyModel.objects.only('field_i_want1', 'field_i_want2')
使用:


我会对单个非嵌套对象执行类似操作。对于嵌套属性,您需要更多的逻辑

class DynamicFieldListSerializer(serializers.ListSerializer):

    def to_representation(self, data):
        """
        Code is a copy of the original, with a modification between the
        iterable and the for-loop.
        """
        # Dealing with nested relationships, data can be a Manager,
        # so, first get a queryset from the Manager if needed
        iterable = data.all() if isinstance(data, models.Manager) else data

        fields = list(self.child.get_fields().keys())
        iterable = iterable.only(*fields)

        return [
            self.child.to_representation(item) for item in iterable
        ]


class DynamicSerializerFieldsMixin:

    def get_fields(self):
        fields = super().get_fields()
        raw_fields = set(self.context['request'].GET.get('fields', '').split(','))
        # If querysparams ?fields= doesn't evaluate to anything, default to original
        validated_fields = set(raw_fields) & set(fields.keys()) or set(fields.keys())
        return {key: value for key, value in fields.items() if key in validated_fields}

    @classmethod
    def many_init(cls, *args, **kwargs):
        meta = getattr(cls, 'Meta', None)
        if not hasattr(meta, 'list_serializer_class'):
            meta.list_serializer_class = DynamicFieldListSerializer
        return super().many_init(*args, **kwargs)
有关示例,请参见:


检查此项是否正确。“only”将立即加载您所说的列,并延迟其余的列。Defer将跳过这些字段,而不会从数据库中检索它们。它在文档上。再看一次我的评论。我看了,它没有多大意义。很抱歉如果你不介意澄清的话。啊,延迟是我想要的。谢谢这对于op尝试执行的操作并不理想,因为
values
排除id,除非您显式地传递它。这是最佳答案。