1、文件上传的小例子
1、新建images文件夹用来存放上传的图片
2、templates文件夹中创建模板文件upload.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>upload</title>
</head>
<body>
<!-- enctype="multipart/form-data"加上不要忘 -->
<form action="" method="post" enctype="multipart/form-data">
<table>
<tr>
<td>头像</td>
<td><input type="file" name="image_file"></td>
</tr>
<tr>
<td>描述</td>
<td><input type="text" name="desc"></td>
</tr>
<tr>
<td><input type="submit" value="上传"></td>
</tr>
</table>
</form>
</body>
</html>
注意点:
再上传文件时,需要在form中写入enctype=”multipart/form-data”这一参数
网页展示:
主文件入口:
from flask import Flask, request, render_template
# 用来拼接文件路径
import os
app = Flask(__name__)
@app.route("/")
def home():
return "首页"
@app.route("/upload/", methods=["GET", "POST"])
def upload():
if request.method == "GET":
return render_template("upload.html")
else:
# 接受文字或者数字时使用的request.form.get()进行接受
desc = request.form.get("desc")
# 对于文件则需要使用request.files.get()进行接收
image_file = request.files.get("image_file")
# image_file.save()中传入的是images//文件名这种格式,所以需要os进行拼接
image_file.save(os.path.join("images", image_file.filename))
return "文件上传成功"
if __name__ == '__main__':
app.run(debug=True)
2、werkzeug.utils.secure_filename对文件名进行过滤
from flask import Flask, request, render_template
import os
# 通过该方法可以将文件中的一些空格、点进行处理
from werkzeug.utils import secure_filename
app = Flask(__name__)
@app.route("/")
def home():
return "首页"
@app.route("/upload/", methods=["GET", "POST"])
def upload():
if request.method == "GET":
return render_template("upload.html")
else:
desc = request.form.get("desc")
image_file = request.files.get("image_file")
filename = secure_filename(image_file.filename)
image_file.save(os.path.join("images", filename))
return "文件上传成功"
if __name__ == '__main__':
app.run(debug=True)
注意点:filename = secure_filename(image_file.filename)由于采取的是ascii的编码方式,所以会将中文进行删除,如下:
解决方法,在如下链接:
https://blog.csdn.net/qq_36390239/article/details/98847888
文件重名的问题(重命名),uuid了解一些
3、对上传文件进行表单验证
为了规范上传的文件格式以及方式一些病毒的注入,因此需要对上传的文件进行表单验证
新建forms.py文件
from wtforms import Form, FileField, StringField
from wtforms.validators import InputRequired
# FileRequired文件必须上传, FileAllowed可以传入的种类
from flask_wtf.file import FileAllowed, FileRequired
class UploadForm(Form):
image_file = FileField(validators=[FileRequired(), FileAllowed(["jpg", "png", "gif"])])
desc = StringField(validators=[InputRequired()])
此时表单中上传了文件,form = UploadForm(request.form)已经不能满足要求需要额外导入
from werkzeug.datastructures import CombinedMultiDict
from flask import Flask, request, render_template
import os
from werkzeug.utils import secure_filename
# 将request.form和request.files一起传入UploadForm()中
from werkzeug.datastructures import CombinedMultiDict
from forms import UploadForm
app = Flask(__name__)
@app.route("/")
def home():
return "首页"
@app.route("/upload/", methods=["GET", "POST"])
def upload():
if request.method == "GET":
return render_template("upload.html")
else:
# 注意直接传入变量CombinedMultiDict([request.form, request.files]
form = UploadForm(CombinedMultiDict([request.form, request.files]))
if form.validate():
# 由于定义了form,所以下面的代码可以进行改写
# desc = request.form.get("desc")
desc = form.desc.data
# image_file = request.files.get("image_file")
image_file = form.image_file.data
filename = secure_filename(image_file.filename)
image_file.save(os.path.join("images", filename))
return "文件上传成功"
else:
print(form.errors)
return "文件上传失败"
if __name__ == '__main__':
app.run(debug=True)
4、通过路由访问资源
# 导入send_from_directory方法
from flask import send_from_directory
...
# 定义一个访问的方法,filename是想要的访问的文件名
@app.route("/images/<filename>")
def images(filename):
return send_from_directory('images', filename)