【发布时间】:2020-05-14 04:21:03
【问题描述】:
看不懂to_reprsentation(self, value)好吧,我有这样的案例
-
当我使用
postman时,当我发布并创建订单并且to_reprsentation中的value是int类型时,状态返回“ORDERED, ...” 当我打开
localhost:8000/orders/时,我得到Order对象不能转换成int,value这次是Order类型。
我搜索了我找到的每一篇文章,我不理解to_representation和to_internal_value这两种方法
models.py
class Product(models.Model):
title = models.CharField(max_length=120)
price = models.FloatField(max_length=20)
def __str__(self):
return f"{self.title} - {self.price}"
class Meta:
ordering = ['price']
@property
def images(self):
for image in Image.objects.filter(product=self):
yield image.src.url
和
class STATUS:
UNORDERED = 0
ORDERED = 1
BEING_PROCESSED = 2
BEING_DELIVERED = 3
DELIVERED = 4
RECEIVED = 5
REFUND_REQUESTED = 6
和
class Order(models.Model):
ORDER_STATUS = (
(STATUS.UNORDERED, 'Unordered'),
(STATUS.ORDERED, 'Ordered'),
(STATUS.BEING_PROCESSED, 'Being processed'),
(STATUS.BEING_PROCESSED, 'Being Delivered'),
(STATUS.DELIVERED, 'Delivered'),
(STATUS.RECEIVED, 'Received'),
(STATUS.REFUND_REQUESTED, 'Refund requested')
)
products = models.ManyToManyField(Product) #
status = models.IntegerField(choices=ORDER_STATUS, default=STATUS.UNORDERED)
class Meta:
ordering = ['pk']
serializers.py
class ProductSerializer(serializers.ModelSerializer):
images = serializers.SerializerMethodField()
class Meta:
model = Product
fields = ['id', 'title', 'price', 'images']
def get_images(self, obj):
request = self.context.get('request', None)
for url in obj.images:
yield request.build_absolute_uri(url)
class StatusField(serializers.RelatedField):
def to_internal_value(self, value):
try:
if int(value) > STATUS.ORDERED:
raise APIException("Can't update an ordered order.")
except ValueError:
raise APIException('Unknown order status code')
except TypeError:
raise APIException('Order status must be an integer.')
return value
def to_representation(self, value):
if isinstance(value, Order):
return value.status if value.status <= STATUS.ORDERED else APIException('Hi')
# if int(value) == 0:
# return "Unordered"
# elif int(value) == 1:
# return "Ordered"
# elif int(value) == 2:
# return "Being processed"
# elif int(value) == 3:
# return "Being Delivered"
# elif int(value) == 4:
# return "Delivered"
# elif int(value) == 5:
# return "Received"
# elif int(value) == 6:
# return "Refund requested"
# raise serializers.ValidationError('Invalid order status code')
class OrderSerializer(serializers.ModelSerializer):
products = ProductSerializer(many=True)
status = StatusField(queryset=Order.objects.all())
class Meta:
model = Order
fields = ['id', 'status', 'products']
depth = 2
def create(self, validated_data): # needs auth
products_list = validated_data.pop('products')
order = Order.objects.create(**validated_data)
for product_data in products_list:
product = Product.objects.create(**product_data)
order.products.add(product)
order.save()
return order
def update(self, instance, validated_data):
products_data = validated_data.pop('products')
if instance.status >= STATUS.ORDERED:
raise APIException("Can't update an ordered order")
instance.status = validated_data.get('status', instance.status)
如果我使用 if isInstance,它会起作用,但我确实想知道为什么有时它返回 Order 而其他时候它返回 int
文档说 The value argument will typically be a model instance. 而这在我的案例中没有发生。
我错过了什么?
提前致谢。
【问题讨论】:
标签: django api django-rest-framework model