Flask 第十二话之文件上传

一、上传文件注意事项

1.在html中form必须带有`enctype="multipart/form-data"`属性才能上传文件

2.在后台获取上传文件:request.files.get('input name属性值')

3.保存文件前导入from werkzeug.utils import secure_filename,使用secure_filename过滤文件名排除文件名为:"../../.bash"等的安全隐患

4.获取上传文件后使用save方法来保存文件

示例代码:

1.html

<form action="" method="post" enctype="multipart/form-data">
    <table>
        <tbody>
            <tr>
                <td>头像:</td>
                <td><input type="file" value="" name="avatar"></td>
            </tr>
            <tr>
                <td>描述:</td>
                <td><input type="text" value="" name="desc"></td>
            </tr>
            <tr>
                <td></td>
                <td><input type="submit" value="提交"></td>
            </tr>
        </tbody>
    </table>
</form>

2.app.py

注:UPLOAD_PATH = os.path.join(os.path.dirname(__file__),'文件夹路径') ==> UPLOAD_PATH = os.path.join(os.path.dirname(__file__),'static/images')

from werkzeug.utils import secure_filename
import os
UPLOAD_PATH = os.path.join(os.path.dirname(__file__),'images')
# 上传文件
@app.route('/',methods=["GET","POST"])
def upload():
    if request.method == "GET":
        return render_template('upload.html')
    else:
        avatar = request.files.get('avatar')
        desc = request.form.get('desc')

        # 去除上传得安全隐患:例如文件名为:../../user/xx.zip
        filename = secure_filename(avatar.filename)
        avatar.save(os.path.join(UPLOAD_PATH,filename))

        return 'ok'

 二、获取文件

注:需要导入from flask import send_from_directory,使用send_from_directory返回文件路径及文件名

实例代码:

1.html

<img src="{{ url_for("get_images",filename="20200306163522.jpg") }}" alt="">

2.app.py

# 获取文件:http://127.0.0.1:5000/images/4.png
from flask import send_from_directory
@app.route('/images/<filename>')
def get_images(filename):
    return send_from_directory(UPLOAD_PATH,filename)

 三、使用flask-wtf处理文件上传

1.forms.py

注:导入from flask_wtf.file import FileAllowed,FileRequired 使用FileAllowed验证什么文件类型可以通过

from wtforms import Form,FileField,StringField
from wtforms.validators import InputRequired

# flask_wtf
from flask_wtf.file import FileAllowed,FileRequired

class UploadForm(Form):
    avatar = FileField(validators=[
        FileRequired(),
        FileAllowed([
            'jpg',
            'png',
            'gif'
        ])
    ])

    desc = StringField(validators=[
        InputRequired()
    ])

2.app.py

注:需要导入from werkzeug.datastructures import CombinedMultiDict,将request.form和request.files共同放入到forms中进行验证

from flask import Flask,render_template,request
from werkzeug.utils import secure_filename
import os
UPLOAD_PATH = os.path.join(os.path.dirname(__file__),'images')
from forms import UploadForm
from werkzeug.datastructures import CombinedMultiDict
# 上传文件
@app.route('/',methods=["GET","POST"])
def upload():
    if request.method == "GET":
        return render_template('upload.html')
    else:
        # 使form同时接收request.form, request.files
        form = UploadForm(CombinedMultiDict(
            [request.form, request.files]
        ))

        if form.validate():
            avatar = request.files.get('avatar')
            desc = request.form.get('desc')
            # 去除上传得安全隐患:例如文件名为:../../user/xx.zip
            filename = secure_filename(avatar.filename)
            avatar.save(os.path.join(UPLOAD_PATH,filename))

            return 'ok'
        else:
            print(form.errors)
            return 'filed'

3.html

<form action="" method="post" enctype="multipart/form-data">
    <table>
        <tbody>
            <tr>
                <td>头像:</td>
                <td><input type="file" value="" name="avatar"></td>
            </tr>
            <tr>
                <td>描述:</td>
                <td><input type="text" value="" name="desc"></td>
            </tr>
            <tr>
                <td></td>
                <td><input type="submit" value="提交"></td>
            </tr>
        </tbody>
    </table>
</form>
原文地址:https://www.cnblogs.com/lee-xingxing/p/12441457.html