Flaskで Content-Type: multipart/form-dataを処理した時のメモ。
from flask import Flask, request, jsonify
app = Flask(__name__)
@app.route('/', methods=['POST'])
def index():
for key, value in request.files.items():
# 何かやる
do_something(key, value.read(), value.memetype)
return jsonify({'success': True})
if __name__ == '__main__':
app.debug = True
app.run(host='0.0.0.0', port=8000)
curl で以下のようにリクエストを送ります。
$ curl --trace-ascii - -X POST \
-F "upload_image=@image.jpg;type=image/jpeg" \
-F 'meta=@payload.json;type=application/json' \
http://0.0.0.0:8000/
form-dataの処理
request.files
リクエストデータは request.files に格納されています。
keyを送信時のキー名、valueをFileStorageとしたMultiDict 型で格納されています。
FileStorageは file-like objectと同じように storage.read() のようにすることでコンテンツを読むことができます。
request.form
request.formでもリクエストデータを扱うことが可能ですが、 Content-Typeを取得する方法が確認できませんでした。(要調査)
Content-Typeでハンドリングするためにrequest.filesを使うのがとりあえずは良さそう。(クライアントが Content-Typeを付けている前提ですが。。。)
curl
curlでmultipart/form-dataを扱う時に気になったところもついでにメモ。
Content-Type を指定する
送るファイルの後に ;区切りで Content-Typeそ指定できます。
trace-asciiをつける
curl -vしてもどのようなpayloadが送られているか全体を確認することはできません。そのため、--trace-ascii -を付けて確認すると楽でした。