默认Django的Ajax的上传与S3后端给MalformedXML错误 [英] Default django-ajax-uploader with s3 backend gives MalformedXML error

查看:573
本文介绍了默认Django的Ajax的上传与S3后端给MalformedXML错误的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我成立了一个测试脚本几乎完全一样在这里的例子: https://github.com/GoodCloud/django-ajax-uploader

这似乎开始上传文件(JavaScript的更新名和文件大小),但鉴于给了我一个500错误与此消息。我无法找到如何解决这事。

  S3ResponseError:S3ResponseError:400错误的请求
&LT;错误&GT;&LT; code取代; MalformedXML&LT; / code&GT;&LT;消息&gt;而没有良好的您提供的XML或没有验证对我们公布schema</Message><RequestId>26E6EF8296A0E585</RequestId><HostId>F4QUOsVT4LxC+6OUP2lE1/9uPC77keOejyWs57GpS5kjvHXpun3U+81ntL8ZTgDa</HostId></Error>
 

我能上传文件的外壳,这里使用的命令博托: 上传0字节的文件到Amazon S3

视图:

 从ajaxuploader.views进口AjaxFileUploader
从ajaxuploader.backends.s3进口S3UploadBackend

import_uploader = AjaxFileUploader(后端= S3UploadBackend)
 

JavaScript的:

  VAR上传=新qq.FileUploader({
    动作:/ AJAX / profile文件上传/,
    元素:$('#文件上传')[0],
    多:真,
    的onComplete:功能(ID,文件名,responseJSON){
        如果(responseJSON.success){
            警报(成功!);
        } 其他 {
            警报(上传失败!);
        }
    },
    onAllComplete:功能(上传){
        //上传是地图数组
        //地图是这样的:{文件:文件对象,响应:JSONServerResponse}
        警报(全部完成!);
    },
    PARAMS:{
        csrf_token'。$('[NAME = csrfmiddlewaretoken])VAL()
        csrf_name':'csrfmiddlewaretoken,
        csrf_xname':'X-CSRFToken',
    },
});
 

模板:

 &LT; D​​IV ID =文件上传&GT;
    &LT; NOSCRIPT&GT;
        &LT; P&gt;请启用JavaScript才能使用文件上传&LT; / P&GT;
    &LT; / NOSCRIPT&GT;
&LT; / DIV&GT;
 

我在settings.py文件中的S3访问变量(他们被称为在ajaxuploader /后端/ s3.py文件):

  AWS_ACCESS_KEY_ID = myAccessKey
AWS_SECRET_ACCESS_KEY = mySecretKey
AWS_BUCKET_NAME = bucketName
 

解决方案

我解决了这个问题,一个自定义的S3后端的覆盖上传功能和安培;使用Django的存储器,而不是博托保存文件。试试这个:

 从ajaxuploader.backends.base进口AbstractUploadBackend
从django.core.files.storage进口default_storage

类S3CustomUpload(AbstractUploadBackend):
    NUM_PARALLEL_PROCESSES = 4

    高清upload_chunk(个体经营,分块):
        #save文件到S3
        self._fd.write(块)
        self._fd.close()

    DEF设置(个体经营,文件名):
        self._fd = default_storage.open('%S /%s的%(上传/材料/',STR(文件名)),世行)

    高清上传(个体经营,上传,文件名,raw_data,*的args,** kwargs):
        尝试:
            如果raw_data:
                #文件是通过AJAX上传,并流研究。
                块= uploaded.read(self.BUFFER_SIZE)
                而LEN(块)&GT; 0:
                    self.upload_chunk(块,*的args,** kwargs)
                    块= uploaded.read(self.BUFFER_SIZE)
            其他:
                #文件是通过POST上传的,而且是在这里。
                对于大块uploaded.chunks():
                    self.upload_chunk(块,*的args,** kwargs)
            返回True
        除:
            #事情进展得很厉害。
            返回False

    高清upload_complete(个体经营,要求,文件名,*的args,** kwargs):
        上传=上传()
        upload.upload = settings.S3_URL +上传/材料/+文件名
        upload.name =文件名
        upload.save()

        返回{'PK':upload.pk}
 

I set up a test script almost exactly like in the example here: https://github.com/GoodCloud/django-ajax-uploader

It seems to start uploading the file (javascript updates the name and size of the file), but the view gives me a 500 error with this message. I can't find anything on how to fix it.

S3ResponseError: S3ResponseError: 400 Bad Request
<Error><Code>MalformedXML</Code><Message>The XML you provided was not well-formed or did not validate against our published schema</Message><RequestId>26E6EF8296A0E585</RequestId><HostId>F4QUOsVT4LxC+6OUP2lE1/9uPC77keOejyWs57GpS5kjvHXpun3U+81ntL8ZTgDa</HostId></Error>

I was able to upload a file in the shell with boto using the commands here: Upload 0 byte file to Amazon S3

The view:

from ajaxuploader.views import AjaxFileUploader
from ajaxuploader.backends.s3 import S3UploadBackend

import_uploader = AjaxFileUploader(backend=S3UploadBackend)

javascript:

var uploader = new qq.FileUploader({
    action: "/ajax/profile-upload/",
    element: $('#file-uploader')[0],
    multiple: true,
    onComplete: function(id, fileName, responseJSON) {
        if(responseJSON.success) {
            alert("success!");
        } else {
            alert("upload failed!");
        }
    },
    onAllComplete: function(uploads) {
        // uploads is an array of maps
        // the maps look like this: {file: FileObject, response: JSONServerResponse}
        alert("All complete!");
    },
    params: {
        'csrf_token': $('[name=csrfmiddlewaretoken]').val(),
        'csrf_name': 'csrfmiddlewaretoken',
        'csrf_xname': 'X-CSRFToken',
    },
});

template:

<div id="file-uploader">       
    <noscript>          
        <p>Please enable JavaScript to use file uploader.</p>
    </noscript>         
</div>

I have the s3 access variables in my settings.py file (they are called in the ajaxuploader/backends/s3.py file):

AWS_ACCESS_KEY_ID = myAccessKey
AWS_SECRET_ACCESS_KEY = mySecretKey
AWS_BUCKET_NAME = bucketName

解决方案

I solved this problem with a custom s3 backend that override the upload function & use django-storages instead of boto to save files. try this :

from ajaxuploader.backends.base import AbstractUploadBackend
from django.core.files.storage import default_storage

class S3CustomUpload(AbstractUploadBackend):
    NUM_PARALLEL_PROCESSES = 4

    def upload_chunk(self, chunk):
        #save file to s3
        self._fd.write(chunk)
        self._fd.close()

    def setup(self, filename):
        self._fd = default_storage.open('%s/%s' % ('uploads/materials/', str(filename)), 'wb')

    def upload(self, uploaded, filename, raw_data, *args, **kwargs):
        try:
            if raw_data:
                # File was uploaded via ajax, and is streaming in.
                chunk = uploaded.read(self.BUFFER_SIZE)
                while len(chunk) > 0:
                    self.upload_chunk(chunk, *args, **kwargs)
                    chunk = uploaded.read(self.BUFFER_SIZE)
            else:
                # File was uploaded via a POST, and is here.
                for chunk in uploaded.chunks():
                    self.upload_chunk(chunk, *args, **kwargs)
            return True
        except:
            # things went badly.
            return False

    def upload_complete(self, request, filename, *args, **kwargs):
        upload = Upload()
        upload.upload = settings.S3_URL + "uploads/materials/"+ filename
        upload.name = filename
        upload.save()

        return {'pk': upload.pk}

这篇关于默认Django的Ajax的上传与S3后端给MalformedXML错误的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆