标签: django-serializer

如何为“列表”(玩家/)和“详细信息”(玩家/{id})获得不同的结果?

这是情况。我的 Django REST API 上有一个列表:/playerslist/

它返回给我一个像这样的球员名单:

http://pastebin.com/JYA39gHT

这正是我目前想要的。但现在,我需要这个:

Going for/playerslist/1/为我提供了不同的玩家编号 1 信息。这里的列表仅用于列出具有基本信息的玩家。但是我需要玩家的详细视图,包含来自其他模型的信息并具有不同的序列化,这一定是一个基本问题,但由于我对 Django 和 Python 总体而言是全新的,我必须误解一些东西。

这是我的视图集:

class PlayersListViewSet(viewsets.ModelViewSet):
    queryset = Player.objects.all()
    serializer_class = PlayersListSerializer
    http_method_names = ['get', 'post']
    pagination_class = None
    filter_backends = [filters.OrderingFilter]
    ordering_fields = ['name']

   def get_queryset(self):
      queryset = Player.objects.all()
      team_id = self.request.query_params.get('team', None)

      if team_id:
          try:
              queryset = queryset.filter(team=team_id)
          except ValueError:
              raise exceptions.ParseError()
       return queryset
Run Code Online (Sandbox Code Playgroud)

我怎样才能做到这一点?我必须使用@detail_route类似的东西playerslist/1/detail吗?我已经尝试过,但 DRF 的文档只显示了一个示例,对我来说根本不清楚。

python django django-queryset django-serializer django-rest-framework

5
推荐指数
1
解决办法
2155
查看次数

Django Rest Framework Serializer charfield 在提供源时不会更新

我有一个带有选择 charfield 的模型字段

class Vehicle(models.Model):
    name = models.CharField(max_length=100)

    STATUS_CHOICES = (
        ("N", "New"),
        ("U", "Used"),
        ("P", "Just Purchased")
    )
    status = models.CharField(max_length=3, choices=STATUS_CHOICES)
Run Code Online (Sandbox Code Playgroud)

序列化器类也有用于状态的字符字段,但带有source显示可读值的参数

class VehicleSerializer(ModelSerializer):
    status = serializers.CharField(source='get_status_display')

    class Meta:
        model = Vehicle
Run Code Online (Sandbox Code Playgroud)

当我尝试通过带有数据的补丁请求更新车辆时{'status': "U"},没有执行更新。但是,当我source从序列化程序状态字段中删除时会发生更新。必须提供来源才能在 Web 视图中显示正确的值。

我知道将序列化程序中的状态名称更改为其他名称并在模板中使用该名称的选项。还有一个选项可以覆盖序列化程序中的更新方法,但是我的问题是源代码在做什么来阻止更新?

django django-serializer django-rest-framework

5
推荐指数
1
解决办法
962
查看次数

如何显示外键值而不是 id?

我有以下型号:

class FlightSchedule(models.Model):
    tail_number = models.ForeignKey(TailNumber, null=False)
    flight_number = models.CharField(max_length=30, null=False)
    flight_group_code = models.ForeignKey(FlightGroup, null=False)
    origin_port_code = models.ForeignKey(Port, null=False, related_name="Origin")
    destination_port_code = models.ForeignKey(Port, null=False, related_name="Destination")
    flight_departure_time = models.TimeField()
    start_date = models.DateField()
    end_date = models.DateField()

def __unicode__(self):
    return u'%s' % self.flight_number

class Meta:
    verbose_name_plural = "Flight Schedule"


class FlightScheduleDetail(models.Model):
    flight_date = models.CharField(max_length=30, null=False)
    flight_number = models.ForeignKey(FlightSchedule, null=False, related_name="flight_number_schedule")
    route_id = models.CharField(max_length=30, null=False, unique=True)
    flight_status = models.ForeignKey(Status, null=True, default=1)

def __unicode__(self):
    return u'%s' % self.route_id

class Meta:
    verbose_name_plural = "Flight Schedule Details" …
Run Code Online (Sandbox Code Playgroud)

python django django-serializer django-rest-framework

5
推荐指数
1
解决办法
2474
查看次数

在序列化器中使用验证响应对字段长度约束进行建模

我正在使用序列化器中的数据验证来验证 django 的其余框架中的请求中的数据。我需要在单个响应中发送所有错误消息。

在发送太长的字符串时,我收到错误:

django.db.utils.DataError: value too long for type character varying(3)
Run Code Online (Sandbox Code Playgroud)

在我的模型中,我将字符字段的最大长度定义为 3(理论上需要的最大长度)。

我在序列化器中添加了验证以捕获包含太多字符的请求:

验证器.py

class CustomUserValidators():

    errors_to_return = {}
    def val_role(self, role):
            if len(role) > 3:
                self.errors_to_return["role_length"] = "Ensure this field has no more than 3 characters."
Run Code Online (Sandbox Code Playgroud)

序列化器.py

from Sea.validators import CustomUserValidators
class LagoonUserCreateSerializer(UserCreateSerializer, CustomUserValidators):
    class Meta:
        model = User
        fields = ('id', 'username', 'role',)


    def validate(self, attrs):
        self.val_role(attrs['role'])

        if len(self.errors_to_return) > 0:
            raise serializers.ValidationError(self.errors_to_return)

        return attrs
Run Code Online (Sandbox Code Playgroud)

模型.py

class SeaUser(AbstractUser):
    ...
    role = models.CharField(_('Role'), max_length=3)
Run Code Online (Sandbox Code Playgroud)

但请求仍然返回错误(value too …

python django django-models django-serializer django-rest-framework

5
推荐指数
1
解决办法
6526
查看次数

Django Serilizer:在嵌入式序列化器中获取有序字典

我是另一个序列化器中的一个序列化器,用于显示一个模型中的信息,并在同一响应中从另一个模型中选择字段。

这看起来像这样:

class SimpleRouteClientConstraintSerializer(serializers.ModelSerializer):

     name = serializers.SerializerMethodField()

    def get_name(self, obj):
        default_constraint = RouteDefaultConstraint.objects.get(pk=obj.route_default_constraint_id)
        return default_constraint.name

    class Meta:
        model = RouteClientConstraint
        fields = ('name', 'value')

class RouteSerializer(serializers.ModelSerializer):
    ...
    # Calling first serializer here
    routeClientConstraints = SimpleRouteClientConstraintSerializer(many=True, required=False)
    ...

    class Meta:
        model = Route
        fields = (..., 'routeClientConstraints', ...)
        depth = 1
Run Code Online (Sandbox Code Playgroud)

运行时RouteSerilalizer,我想要一个响应:

'routeClientConstraints': [{
    'name': 'my name'
    'value': 'confused'
},
...
]
Run Code Online (Sandbox Code Playgroud)

如果我像上面的代码一样使用序列化器,我会得到

'routeClientConstraints': [
    OrderedDict([
        ('name', 'Minimum life boats'),
        ('value', '6')
    ])
]
Run Code Online (Sandbox Code Playgroud)

我尝试将序列化器更改为:routeClientConstraints = SimpleRouteClientConstraintSerializer(many=True, required=False).data …

python django django-serializer

5
推荐指数
1
解决办法
538
查看次数

DRF - 如何根据条件更改 serializer.PrimaryKeyRelatedField 的过滤器查找键?

我正在尝试serializers.PrimaryKeyRelatedField根据序列化程序上的其他布尔字段更改的过滤器查找键,但我无法成功。PrimaryKeyRelatedFieldpk默认按键过滤。在某些情况下(如果condition序列化程序上的字段作为 发送True),我只想使用相关模型字段上的另一个字段更改该过滤键,例如remote_id.

class SomeSerializer(serializers.Serializer):
    condition = serializers.BooleanField(default=False)
    model_pks = serializer.PrimaryKeyRelatedField(queryset=Model.objects.all(), many=True)

Run Code Online (Sandbox Code Playgroud)

到目前为止,我尝试创建继承自PrimaryKeyRelatedField并覆盖get_queryset方法(不确定是否覆盖正确方法)的新字段,但我无法访问conditionmodel_pks字段值。

class CustomPrimaryKeyRelatedField(PrimaryKeyRelatedField):
    def get_queryset(self):
        queryset = self.queryset
        # model_pks = sent model_pks
        if condition:
            return queryset.filter(remote_id__in=model_pks)
        return queryset.filter(id__in=model_pks)

Run Code Online (Sandbox Code Playgroud)

另外,我尝试使用SerializerMethodField而不是PrimaryKeyRelatedField喜欢;

class SomeSerializer(serializers.Serializer):
    condition = serializers.BooleanField(default=False)
    model_pks = serializer.SerializerMethodField()

    def get_model_pks(self, value):
        pks = self.initial_data.get('model_pks', [])
        if value.get('condition', False):
            return Model.objects.filter(remote_id__in=pks)
        return Model.objects.filter(pk__in=pks)

Run Code Online (Sandbox Code Playgroud)

它提供了基于以下内容的更改查找键,condition但这次我无法model_pks使用 …

python django django-queryset django-serializer django-rest-framework

5
推荐指数
1
解决办法
909
查看次数

DRF:如何在使用深度选项的序列化器中隐藏密码?

我正在为模型使用下面的序列化器User,但是当我使用深度来处理外键时,密码会显示在User对象中。

用户序列化器:

class UserSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        read_only_fields = ('is_active', 'is_staff', 'is_superuser',)
        exclude = ('password', )
        extra_kwargs = {'password': {'write_only': True, 'min_length': 4}}
Run Code Online (Sandbox Code Playgroud)

在下面的序列化器中一切都很好:

class AuditSerializer(serializers.ModelSerializer):
    def __init__(self, instance=None, **kwargs):
        if instance:
            setattr(self.Meta, 'depth', 10)
        else:
            setattr(self.Meta, 'depth', 0)
        super(AuditSerializer, self).__init__(instance, **kwargs)

    initiator = UserSerializer(read_only=True)

    class Meta:
        model = Audit
        fields = ['id', 'initiator']
        read_only_fields = ['id', 'initiator']
        depth = 0
Run Code Online (Sandbox Code Playgroud)

但在下面与之前的模型/序列化器相关的内容中,我遇到了密码问题:

class AuditAttachmentSerializer(serializers.ModelSerializer):
    def __init__(self, instance=None, **kwargs):
        if instance:
            setattr(self.Meta, 'depth', 10)
        else: …
Run Code Online (Sandbox Code Playgroud)

python django django-serializer django-rest-framework drf-queryset

5
推荐指数
1
解决办法
2045
查看次数

带有序列化器的异步视图 Django 3.1

我正在尝试创建一个异步视图来解决 Django 3.1 的端点问题。

我有我的 AsyncView,在这个视图中我有下面的代码行:

try:
    db_result= await sync_to_async(list)(Plan.objects.filter())
    serializer =  MySerializer(db_results, many=True)
    return serializer.data
except Exception:
    # Handle Exception Code
Run Code Online (Sandbox Code Playgroud)

在我的序列化器中,我有一个自定义字段。使用其 obj 属性对数据库进行其他查询来检索其数据。这是我遇到一些问题的地方,因为这是一个异步上下文。

序列化器代码:

MySerializer(serializers.ModelSerializer):

    custom_field = serializers.SerializerMethodField(required=False)

    def get_custom_field(self, obj):
        try:
            # This is failing, is not retrieving data from DB since it's async context
            related_stuff = obj.related_stuff.filter(filter_condition=filter_condition)
            # More code after this
            .
            .
            .
            .
            return custom_field_object
        except Exception:
            return None

Run Code Online (Sandbox Code Playgroud)

我尝试在视图代码中的序列化器之前放置一个等待,并将 async 属性添加到 get_custom_field 方法(使用数据库查询中的sync_to_async 运算符)。什么也没得到。

有人知道如何解决这个具体问题吗?

django asynchronous django-serializer django-rest-framework python-asyncio

5
推荐指数
1
解决办法
833
查看次数

Django Rest Framework:在 GET 响应中发送完整的外键对象,但在 POST 负载中仅接受外来 ID,而不需要两个序列化器?

假设我有两个模型:

class Singer((models.Model):
   name = models.CharField(max_length=200)

class Song(models.Model):
   title = models.CharField(max_length=200)
   singer = models.ForeignKey(Singer)
Run Code Online (Sandbox Code Playgroud)

两个序列化器如下:

class SingerSerializer(serializers.ModelSerializer):
    class Meta:
        model = Singer
        fields = '__all__'

class SongSerializer(serializers.ModelSerializer):
    singer = SingerSerializer()

    class Meta:
        model = Singer
        fields = '__all__'
Run Code Online (Sandbox Code Playgroud)

我已经按照上面的方式定义了序列化器,因为我需要歌曲的 GET 响应中的完整外键对象:

{
    "singer": {
        "id": 1,
        "name": "foo"
    },
    "id": 1,
    "title": "foo la la"
}
Run Code Online (Sandbox Code Playgroud)

有没有办法允许 POST/PATCH 有效负载仅发送外部对象的 id 而不是整个对象,而无需编写不同的序列化程序?我希望 PATCH 有效负载是这样的:

{
    "singer": 1,
    "id": 1,
    "title": "foo la la"
}
Run Code Online (Sandbox Code Playgroud)

django django-models django-serializer django-rest-framework django-rest-viewsets

5
推荐指数
1
解决办法
2754
查看次数

Django DRF:read_only_fields 无法正常工作

我有以下型号

class Breed(models.Model)::
    name = models.CharField(max_length=200)

class Pet(models.Model):
    owner = models.ForeignKey(
        "User",
        on_delete=models.CASCADE,
    )
    name = models.CharField(max_length=200)
    breed = models.ForeignKey(
        "Breed",
        on_delete=models.CASCADE,
    )
Run Code Online (Sandbox Code Playgroud)

我正在尝试添加一些文件representation。我不希望他们被包括create在内update

class PetSerializer(serializers.ModelSerializer):
    owner_email = serializers.CharField(source='owner.email')
    breed_name = serializers.CharField(source='breed.str')
    class Meta:
        model = Pet
        fields = "__all__"
        read_only_fields = ["breed_name","owner_email"]
Run Code Online (Sandbox Code Playgroud)

这是行不通的。我在 HTMLform(DRF api 页面)中看到了owner_emailbreed_name

然而

class PetSerializer(serializers.ModelSerializer):
    owner_email = serializers.CharField(source='owner.email',read_only=True)
    breed_name = serializers.CharField(source='breed.str',read_only=True)
    class Meta:
        model = Pet
        fields = "__all__"
Run Code Online (Sandbox Code Playgroud)

这是有效的。我在 HTML 表单中没有看到它们

我还观察到,如果我直接在 read_only_fields 中使用模型字段,那么它就可以工作。

class PetSerializer(serializers.ModelSerializer): …
Run Code Online (Sandbox Code Playgroud)

django django-serializer django-rest-framework

5
推荐指数
1
解决办法
3049
查看次数