方法对象不是JSON可序列化的

问题描述 投票:3回答:1

我删除购物车项目时使用ajax刷新购物车项目。它工作得很好,如果我不用图像响应对象,否则我得到一个错误method object is not JSON serializable。如果我使用model_to_dict作为图像部分,我得到一个错误'function' object has no attribute '_meta'

这是代码

def cart_detail_api_view(request):
    cart_obj, new_obj = Cart.objects.new_or_get(request)
    products = [{
            "id": x.id,
            "url": x.get_absolute_url(),
            "name": x.name,
            "price": x.price,
            "image": x.first_image
            }
            for x in cart_obj.furnitures.all()]
    cart_data  = {"products": products, "subtotal": cart_obj.sub_total, "total": cart_obj.total}
    return JsonResponse(cart_data)

class Furniture(models.Model):
    name = models.CharField(max_length=100, blank=True, null=True)
    manufacturer = models.ForeignKey(Manufacturer, blank=True, null=True)
    slug = models.SlugField(max_length=200, unique=True)

    def __str__(self):
        return self.name

    def first_image(self):
        """
        Return first image of the furniture otherwise default image
        """
        if self.furniture_pics:
            return self.furniture_pics.first()
        return '/static/img/4niture.jpg'

class Cart(models.Model):
    user = models.ForeignKey(User, null=True, blank=True)
    furnitures = models.ManyToManyField(Furniture, blank=True)

在将'function' object has no attribute '_meta'包装到x.first_image时,我得到model_to_dict错误

我该如何解决这个问题?

更新

class FurniturePic(models.Model):
    """
    Represents furniture picture
    """
    furniture = models.ForeignKey(Furniture, related_name='furniture_pics')
    url = models.ImageField(upload_to=upload_image_path)
python django python-3.x django-views django-serializer
1个回答
6
投票

如你所知,问题在于:

"image": x.first_image

first_image是一个函数,因此无法转换为JSON。你想要做的是序列化first_image返回的值。所以,为此,你需要调用这个函数:

"image": x.first_image() # note the brackets

另外,我还注意到另一个问题:

return self.furniture_pics.first() # will return the image object; will cause error

所以,你必须改变它:

return self.furniture_pics.first().url # will return the url of the image

更新:

self.furniture_pics.first().url将返回FurniturePic.url,这是一个ImageField。您需要该图片的网址进行序列化。你必须这样做:

return self.furniture_pics.first().url.url # call url of `url`

如你所见,这让人感到困惑。我建议将FurniturePic.url字段的名称更改为FurniturePic.image。但是,随意忽略它。

© www.soinside.com 2019 - 2024. All rights reserved.