我想要一个完全只读-----END RSA PRIVATE KEY-----
,即只列出/检索方法
最好的方法是什么?
答案 0 :(得分:10)
您确实希望在视图(或视图集)级别执行此操作,您可以使用ReadOnlyModelViewSet执行此操作。
(您在评论中提到了这一点,但我将其留作了更好的知名度的答案)。
答案 1 :(得分:7)
你唯一要做的就是创建一个像这样的序列化器。 serializers.py
class YourdataSerializer(serializers.ModelSerializer):
class Meta:
model = Yourdata
# some data
fields = ('id', 'city', 'pincode', 'created')
read_only_fields = ('id', 'city', 'pincode', 'created')
观看类似这样的内容
class YourdataList(APIView):
def get(self, request, format=None):
yourdata = YourdataList.objects.all()
serializer = YourdataSerializer(yourdata, many=True)
return Response(serializer.data)
详细视图
class YourdataDetail(APIView):
def get_object(self, pk):
try:
return Yourdata.objects.get(pk=pk)
except Yourdata.DoesNotExist:
raise Http404
def get(self, request, pk, format=None):
snippet = self.get_object(pk)
serializer = YourdataSerializer(snippet)
return Response(serializer.data)
这样就可以了。
答案 2 :(得分:2)
如果您使用的是ModelSerializer
,则可以通过以下方法实现:
from rest_framework import serializers
class MyModelSerializer(serializers.ModelSerializer):
...
class Meta:
model = MyModel
fields = ("field_1", "field_2", etc)
read_only_fields = [f.name for f in MyModel._meta.get_fields()]
此解决方案使用django模型的专用_meta
接口,但它相当稳定,并且开发人员已相当广泛地使用它。
在这里,我们只是生成相关模型中所有字段的列表,并将其应用于read_only_fields
中的django-rest-framework
选项。
相对于视图级别,我更喜欢在序列化程序级别执行此操作,因为它不会像mgalgs所建议的那样使您束缚于使用Viewset。
如果您想更进一步,甚至可以将功能包装到mixin中,从而增加类的Meta
选项。诸如此类的东西:
from rest_framework import serializers
from rest_framework.fields import Field
class ReadOnlyMixin(Field):
def __new__(cls, *args, **kwargs):
setattr(
cls.Meta,
"read_only_fields",
[f.name for f in cls.Meta.model._meta.get_fields()],
)
return super(ReadOnlyMixin, cls).__new__(cls, *args, **kwargs)
class MyModelSerializer(ReadOnlyMixin, serializers.ModelSerializer):
...
class Meta:
model = MyModel
fields = ("field_1", "field_2", etc)
答案 3 :(得分:1)
好的亲爱的Mohsen,要使用BaseSerializer类实现只读序列化,我们只需要覆盖.to_representation()方法。让我们看一个使用简单Django模型的例子:
class HighScore(models.Model):
created = models.DateTimeField(auto_now_add=True)
player_name=models.CharField(max_length=10)
score = models.IntegerField()
创建只读序列化程序以将HighScore实例转换为原始数据类型非常简单。
class HighScoreSerializer(serializers.BaseSerializer):
def to_representation(self, obj):
return { 'score': obj.score, 'player_name': obj.player_name }
答案 4 :(得分:1)
如果您确实需要一个序列化器为只读,则覆盖 init 方法的最简洁,最稳定的选择是:
def __init__(self, *args, **kwargs):
super(MySerializer, self).__init__(*args, **kwargs)
setattr(self.Meta, 'read_only_fields', [*self.fields])
与上述相比:
答案 5 :(得分:0)
对此有两种解决方案?
from rest_framework.utils import model_meta
class CustomSerializer(serializers.ModelSerializer):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
model = getattr(self.Meta, 'model')
declared_fields = copy.deepcopy(self._declared_fields)
info = model_meta.get_field_info(model)
field_names = self.get_field_names(declared_fields, info)
_, hidden_fields = self.get_uniqueness_extra_kwargs(
field_names, declared_fields, extra_kwargs)
fields_names.extend(hidden_fields.keys())
setattr(self.Meta, 'read_only_fields', list(field_names))
或
class CustomSerializer(serializers.ModelSerializer):
def __init__(self, *args, **kwargs):
super().__init__()
setattr(self.Meta, 'read_only_fields', list(self.fields))