【问题标题】:Django Rest Framework upload file to a methodDjango Rest Framework 将文件上传到方法
【发布时间】:2014-10-31 11:24:57
【问题描述】:

所以我一直在尝试将文件上传到使用 DRF 的方法,但到目前为止没有运气。

我能够毫无问题地使用(FormParser, MultiPartParser,) 上传到ModelViewSet,但我真的需要在类似http://localhost:8000/api/v1/women/{pk}/upload_avatar/ 的地方使用它,我想先按id 过滤女人并上传到她的头像(这是多媒体模型的外键)。我尝试使用嵌套资源库,但没有成功。

到目前为止,我的模型视图集中有:

class WomenNativePassportViewSet(viewsets.ModelViewSet):
    queryset = Women.objects.all()
    serializer_class = WomenNativePassportSerializer
    authentication_classes = (NoAuthentication,)
    permission_classes = (AllowAny,)
    parser_classes = (FormParser, MultiPartParser,)

    @detail_route(
        methods=['post', 'put', 'patch', 'get'], permission_classes=[AllowAny],
        authentication_classes=[NoAuthentication], serializer_class=MultimediaSerializer,
        parser_classes=(FormParser, MultiPartParser,)
    )
    def upload_avatar(self, request, pk=None, *args, **kwargs):
        if 'POST' in request._method or 'PATCH' in request._method:
            # Write code to save the file??
        else:
            multimedia = Multimedia.objects.filter(user_profiles_avatares__pk=pk)
            page = self.paginate_queryset(multimedia)
            serializer = self.get_pagination_serializer(page)
        return Response(serializer.data)

我的模型:

class Women(models.Model):
    user = models.OneToOneField(settings.AUTH_USER_MODEL)
    avatar = models.ForeignKey(
        'core.Multimedia', blank=True, null=True,
        related_name='user_profiles_avatares'
    )

class Multimedia(models.Model):
    file = models.FileField(upload_to=upload_to, null=True, blank=True)
    thumbnail = models.FileField(upload_to=upload_to, null=True, blank=True)

基本上我想知道这是否是我所采取的正确路径,如果是,我怎样才能正确地将上传的文件保存在模型中??

【问题讨论】:

    标签: python django django-rest-framework


    【解决方案1】:

    这是我为克服这个问题所做的一些代码。尽管 Kevin Brown 的回答可能有效,但我发现我的代码有点“更简单”:

        @detail_route(
            methods=['post', 'put', 'patch', 'get'], permission_classes=[AllowAny],
            authentication_classes=[NoAuthentication], serializer_class=MultimediaSerializer,
            parser_classes=(FormParser, MultiPartParser,)
        )
        def upload_avatar(self, request, pk=None):
            # Because we are using nested resources this was the only way i found to
            # upload a file. Maybe there is a better way
            if request.method in ['PATCH', 'POST']:
                avatar = request.FILES.get('avatar')
                if not avatar:
                    return Response(status=404)
    
                try:
                    woman = WomenNativePassport.objects.get(pk=pk)
                except WomenNativePassport.DoesNotExist:
                    return Response(status=404)
                else:
                    request.FILES['thumbnail'] = request.FILES['avatar']
                    serializer = AvatarSerializer(
                        data=request.DATA, files=request.FILES
                    )
                    if serializer.is_valid():
                        woman.avatar.thumbnail.save(str(avatar), File(avatar))
                        return Response(status=204)
                    else:
                        return Response(status=404)
            else:
                multimedia = Multimedia.objects.filter(user_profiles_avatares__pk=pk)
                page = self.paginate_queryset(multimedia)
                serializer = self.get_pagination_serializer(page)
                return Response(serializer.data)
    
    
    # serializer 
    
    class AvatarSerializer(serializers.Serializer):
        thumbnail = serializers.ImageField()
    

    【讨论】:

    • 我建议将方法检查更改为类似于if request.method in ['PATCH', 'POST'],因为request.method 始终是一个方法。
    【解决方案2】:

    任何上传的文件都应该在request.FILES 中可用,这是一个由上传时使用的字段键入的字典。获得文件后,就可以像处理任何其他 uploaded file in Django 一样处理它。

    如果可以的话,我会使用第二个序列化程序来包装Multimedia 模型,以便可以通过 Django REST 框架自动完成图像验证和保存。有an ImageField 会自动通过Pillow 验证图像,您可以在序列化器上使用它。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2015-11-29
      • 2017-07-17
      • 2016-05-12
      • 2017-02-28
      • 2015-10-06
      • 2018-02-21
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多