在Django Rest Framework中接收Base64编码图像并保存到ImageField中

goz*_*lli 15 django json django-models django-rest-framework

我需要从应用程序接收图像,我能想到的最好方法是将其发送到Base64编码的JSON数组中.图像非常小,所以我不在乎额外的开销.

我有一个模特:

class Observation(models.Model):    
    ...
    sonogram_image = models.ImageField(upload_to=sonogram_dir)
Run Code Online (Sandbox Code Playgroud)

它的序列化器:

class ObsvSerializerNoDetect(serializers.HyperlinkedModelSerializer):

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

我应该在哪里放置代码来解码图像?

Nik*_*hil 11

以下是如何在基于Django(drf的)API端的post请求中处理Base64编码的图像文件,并将其保存为ImageField.

假设你有一个模型如下:

Class MyImageModel(models.Model):
      image = models.ImageField(upload_to = 'geo_entity_pic')
      data=model.CharField()
Run Code Online (Sandbox Code Playgroud)

所以对应的Serializer如下:

 from drf_extra_fields.fields import Base64ImageField

 Class MyImageModelSerializer(serializers.ModelSerializers):
      image=Base64ImageField()
      class meta:
         model=MyImageModel
         fields= ('data','image')
      def create(self, validated_data):
        image=validated_data.pop('image')
        data=validated_data.pop('data')
       return MyImageModel.objects.create(data=data,image=image)
Run Code Online (Sandbox Code Playgroud)

相应的View可以如下:

elif request.method == 'POST':
    serializer = MyImageModelSerializer(data=request.data)
    if serializer.is_valid():
        serializer.save()
        return Response(serializer.data, status=201)
    return Response(serializer.errors, status=400)
Run Code Online (Sandbox Code Playgroud)

注意在Serializer中,我使用了模块django-extra-field中提供的Base64ImageField实现

要安装此模块,请运行该命令

pip install django-extra-fields
Run Code Online (Sandbox Code Playgroud)

导入相同和完成!

发送(通过post方法)您的图像作为JSON对象中的Base64编码字符串以及您拥有的任何其他数据.


Den*_*ehl 2

根据您的用例,可能有两个最佳位置:

  1. 在序列化器中,您可以为字段覆盖validate_X和方法(请参阅验证文档)以及此处的双向转换。transform_X

  2. 如果您更频繁地需要该功能,请编写您自己的自定义字段。您只需在to_native和中定义转换如何在两个方向上运行from_native。也许可以扩展原始 DRFImageField以保持使用 PIL 进行图像数据验证。

更新 DRF3:

transform_X方法替换为to_representation(). 请参阅removal-of-transform_field_name覆盖序列化和反序列化行为

另请查看此 DRF Base64ImageFieldMixin示例。