Python 限制queryset在对数据库的sql调用中查询的django字段
我有一个带有blob的表,希望将其排除在对数据库的sql调用中,除非特别要求。开箱即用的django包含queryset中的所有内容。到目前为止,我发现限制该字段的唯一方法是在视图get_queryset()中添加一个函数 并混入序列化程序以限制其检查的字段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
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,除非您显式地传递它。这是最佳答案。