简体   繁体   English

将文件作为JSON上载到Python Web服务器

[英]Upload file as JSON to Python webserver

I want to upload a file as JSON from the client to a Python webserver (Tornado) and save it on the server. 我想将文件作为JSON从客户端上传到Python网络服务器(Tornado)并将其保存在服务器上。 This is my simplified setup: 这是我的简化设置:

Client HTML: 客户端HTML:

<input type="file" id="myFile" onchange="fileChange" />

Client JS: 客户端JS:

function fileChange(event) {
    const file = event.target.files[0];
    const fileReader = new FileReader();
    fileReader.onload = (e) => uploadFile(e.target.result, file.name);
    fileReader.readAsText(file);
}

function uploadFile(fileContent, fileName) {
    const data = {fileContent, fileName};
    axios.post('http://localhost:8080/api/uploadFile', JSON.srtingify(data));
}

Python Webserver: Python Web服务器:

class UploadFileHandler(tornado.web.RequestHandler):

    def post(self):
        requestBody = tornado.escape.json_decode(self.request.body)
        file = open(requestBody["fileName"], "w+")
        file.write(requestBody["fileContent"].encode("UTF-8"))
        file.close()
  1. All uploaded files are empty (blank pages in a PDF, file type of JPG is 'not supported', Word file cannot be opened) and are nearly twice as big as the original file. 所有上传的文件都是空的(PDF中为空白页,“不支持JPG”文件类型,无法打开Word文件),并且其大小几乎是原始文件的两倍。 How can I fix this? 我怎样才能解决这个问题?
  2. Is there a way to improve this setup? 有没有办法改善此设置?

You are trying to upload binary files (word, jpg), serialised as JSON, and store them on the server. 您正在尝试上传二进制文件(word,jpg),将其序列化为JSON,并将其存储在服务器上。

To handle binary data in JSON, encode the binary data as base64 first, then call JSON.stringify . 要处理JSON中的二进制数据,请首先将二进制数据编码为base64 ,然后调用JSON.stringify

Like this (untested): 像这样(未经测试):

function uploadFile(fileContent, fileName) {
    // Encode the binary data to as base64.
    const data = {
        fileContent: btoa(fileContent),
        fileName: fileName
    };
    axios.post('http://localhost:8080/api/uploadFile', JSON.stringify(data));
}

On the server side, you need to deserialise from JSON, decode the base64 and the open a file in binary mode to ensure that what you are writing to disk is the uploaded binary data. 在服务器端,您需要从JSON反序列化,解码base64并以二进制模式打开文件,以确保要写入磁盘的是上载的二进制数据。 Opening the file in text mode requires that the data be encoded before writing to disk, and this encoding step will corrupt binary data. 以文本模式打开文件要求在写入磁盘之前对数据进行编码,并且此编码步骤将破坏二进制数据。

Something like this ought to work: 这样的事情应该起作用:

class UploadFileHandler(tornado.web.RequestHandler):

    def post(self):
        requestBody = tornado.escape.json_decode(self.request.body)
        # Decode binary content from base64
        binary_data = base64.b64decode(requestBody[fileContent])
        # Open file in binary mode
        with open(requestBody["fileName"], "wb") as f:
            f.write(binary_data)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM