Я работаю над флеш-приложением, которое будет обрабатывать большие загрузки файлов (250 МБ +). Я запускаю это приложение, используя Tornado с несколькими процессами, поэтому он может обрабатывать параллельные запросы без блокировки.MemoryError при загрузке больших файлов на HTTP-сервер Tornado
import os.path
import tempfile
from flask import Flask, request, jsonify
from tornado.wsgi import WSGIContainer
from tornado.httpserver import HTTPServer
from tornado.ioloop import IOLoop
from werkzeug import secure_filename
app = Flask(__name__)
@app.route("/test", methods=["GET"])
def test_route():
return jsonify(msg='Ok'), 200
@app.route("/upload", methods=["GET", "POST"])
def upload_file():
if request.method == 'POST':
temp_directory = app.config['TMP_DIRECTORY']
uploaded_file = request.files['filename']
filename = secure_filename(uploaded_file.filename)
uploaded_file.save(os.path.join(temp_directory, filename))
return jsonify(msg="File upload successfully"), 200
else:
return jsonify(msg="Use POST to upload a file"), 200
if __name__ == '__main__':
app.config['TMP_DIRECTORY'] = tempfile.mkdtemp()
address = '0.0.0.0'
port = 8000
max_buffer_size = 500 * 1024 * 1024
server = HTTPServer(WSGIContainer(app), max_buffer_size=max_buffer_size)
server.bind(port=port, address=address)
print("Starting Tornado server on %s:%s" % (address, port))
server.start(2)
IOLoop.instance().start()
Я получаю следующее MemoryError при загрузке нескольких больших файлов одновременно:
$ curl -i -F name=file -F [email protected] http://127.0.0.1:8000/upload
ERROR:tornado.application:Uncaught exception
Traceback (most recent call last):
File "/usr/lib64/python2.7/site-packages/tornado/http1connection.py", line 238, in _read_message
delegate.finish()
File "/usr/lib64/python2.7/site-packages/tornado/httpserver.py", line 285, in finish
self.request.body = b''.join(self._chunks)
MemoryError
Я считаю, что Торнадо хранит весь загруженный файл в память и только записывает его на диск после того, как клиент завершена загрузка. Можно ли изменить это поведение, чтобы выписать куски на диск?
Вы совершенно правы. Вместо этого я собираюсь использовать пушки. –