在Django后端中从FormData数组获取文件

时间:2019-03-14 18:11:44

标签: python django django-rest-framework

我尝试发送POST请求。

我尝试从包含图像数组的javascript发布数据(FormData) 我控制台中的 print(request.data)命令显示以下内容:

 <QueryDict: 
     {'title': ['testTitle'], 'text': ['testText'], 
      'images': [<InMemoryUploadedFile: 486217.jpg (image/jpeg)>, 
                 <InMemoryUploadedFile: 344611.jpg (image/jpeg)>, 
                 <InMemoryUploadedFile: default.png (image/png)>]
              }>

django中的代码:models.py

class Article(models.Model):

title = models.CharField(max_length=120)
text = models.TextField()
create_time = models.DateTimeField(default=datetime.utcnow, blank=True, 
              null=True)

def __str__(self):
    return self.title     

class ArticleImage(models.Model):
    article = models.ForeignKey(Article, related_name='images', 
              on_delete=models.CASCADE)
    img = models.ImageField(upload_to='article_images/')
    is_main = models.BooleanField(default=False,blank=True,null=True)
    create_time = models.DateTimeField(default=datetime.utcnow, blank=True, 
                  null=True)

def __str__(self):
    return  self.article.title

views.py

class ArticleMixinView(generics.GenericAPIView,
                    mixins.ListModelMixin,
                    mixins.CreateModelMixin,
                    ...)
serializer_class = ArticleSerializer
queryset = Article.objects.all()
lookup_field = 'id'


def post(self, request):
    print(request.data)
    new_article = Article.objects.create(title=request.data.get('title'), 
                  text=request.data.get('text'))
    new_article.save()
    for img in request.data.get('images'):
        # article_img = ArticleImage(article=new_article,img=File(img), 
        #                             is_main=False )
        # article_img.save()

    return Response({
            'article': ArticleSerializer(new_article, 
                       context=self.get_serializer_context()).data

    }) 

创建Article对象的工作正常,但是此数组存在一些问题。有什么问题,或者如何从 InMemoryUploadedFile 对象获取图像? 请任何帮助。谢谢你前进

1 个答案:

答案 0 :(得分:0)

我认为您是从前端发送images作为数组。您可以更好地格式化它们,以使数组的每个对象与您的ArticleImage模型相匹配。例如,images键的每个对象都应具有针对img键的文件(因为这是模型中字段的名称):

<QueryDict: 
   {'title': ['testTitle'], 
    'text': ['testText'], 
    'images': [{'img': <InMemoryUploadedFile: 486217.jpg (image/jpeg)>},
             {'img': <InMemoryUploadedFile: 344611.jpg (image/jpeg)>}]
   }>

现在,您可以将ModelSerializermany=True结合使用了。

例如,为ArticleImage模型创建一个序列化器:

class ArticleImageSerializer(serializers.ModelSerializer):
    class Meta:
        model = ArticleImage
        fields = ('article', 'img', 'is_main', 'create_time')
        read_only_fields = ('article', 'is_main', 'create_time') # so that only `img` field comes from input

现在使用它来将图像保存在模型中:

def post(self, request):
    print(request.data)
    images = request.data.pop('images')

    serializer = self.get_serializer_class(data=request.data) # why not use ArticleSerializer?
    serializer.is_valid(raise_exception=True)                 # this lets you validate if something is wrong with user's input
    new_article = serializer.save()                           # similar to Article.objects.create

    images_serializer = ArticleImageSerializer(data=images, many=True)  # only `img` comes from data
    images_serializer.is_valid(raise_exception=True)
    images_serializer.save(article=new_article, is_main=False) # adding additional fileds

    return Response(serializer.data) 

此代码未经测试,请告知我是否无法正常运行。希望对您有所帮助。