A-A+
FastAPI 上传文件 保存文件方法 UploadFile示例详解

【注意:此文章为博主原创文章!转载需注意,请带原文链接,至少也要是txt格式!】
最近准备利用FastAPI写个系统,在研究upload上传文件,但是发现很多很多案例上传的点讲的并不详细,下面经过我自己的总结,把上传点详细分享给打家。直接看代码吧,非常直接。
主文件程序,名命为mian.py,代码为:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 | # -*- coding: utf-8 -*- from typing import List from starlette.requests import Request from fastapi import FastAPI, Form, File, UploadFile from starlette.templating import Jinja2Templates import utils app = FastAPI() templates = Jinja2Templates(directory="templates") upload_tmp_full = 'E:\\fastapi_xuexi\\' @app.post("/files/") async def files( request: Request, files_list: List[bytes] = File(...), # List多个文件 files_name: List[UploadFile] = File(...), ): return templates.TemplateResponse("index.html", { "request": request, "files_sizes": [len(file) for file in files_list], # 注意files_list是多个文件 "filenames": [file.filename for file in files_name] } ) @app.post("/create_file/") async def create_file( request: Request, # 单个文件 fileb: UploadFile = File(...), notes: str = Form(...), ): logs = [] content = await fileb.read() file_name = fileb.filename if len(content) > 0: file_name = utils.standardization_filename(fileb.filename) addr = upload_tmp_full + file_name with open(addr, 'wb') as f: f.write(content) logs.append({'origin': fileb.filename, 'type': fileb.content_type, 'save_name': file_name}) else: logs.append({'status': 'isn`t file'}) return templates.TemplateResponse("index.html", { "request": request, "fileb_size": len(content), "fileb_content_type": fileb.content_type, "fileb_name": file_name, "notes": notes, "上传结果": logs }) @app.get("/") async def main(request: Request): return templates.TemplateResponse('main.html', {"request": request, }) if __name__ == "__main__": import uvicorn uvicorn.run(app, host='0.0.0.0', port=80) |
次要python文件,名命为utils.py,代码为:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 | # -*- coding: utf-8 -*- # __author__ = xieyunlong # __Blog__ = https://woj.app # __Date__ = 2021/7/7 from datetime import datetime, timezone, timedelta import uuid def get_standard_time() -> str: return (datetime.now(timezone.utc) + timedelta(hours=8)).strftime('%Y-%m-%dT%H:%M:%S%z') def get_string_time() -> str: return (datetime.now(timezone.utc) + timedelta(hours=8)).strftime('%Y%m%d%H%M%S+z%f') def generate_doc_id() -> str: # 生成唯一编号,所有doc都将使用其作为doc_id return str(uuid.uuid1()) def standardization_filename(origin_name) -> str: splitted = origin_name.split('.') if len(splitted) >= 2: return splitted[0] + '_' + get_string_time() + '.' + splitted[-1] return splitted[0] + '_' + get_string_time() + '.unknown' def standardization_filename2taskname(name) -> str: splitted = name.split('_') # 保留原名称中的_,去除正规化后附加的时间及原后缀 return "_".join(splitted[0:-1]) def standardization_filename(origin_name) -> str: splitted = origin_name.split('.') if len(splitted) >= 2: return splitted[0] + '_' + get_string_time() + '.' + splitted[-1] return splitted[0] + '_' + get_string_time() + '.unknown' |
要在当前主文件下面建立一个目录,名字为“templates”,在目录里放入如下两个Html文件。
名命为:main.html
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>文件上传页</title> </head> <body> <form action="/files/" enctype="multipart/form-data" method="post"> <input name="files_list" type="file" multiple><br><br> <input name="files_name" type="file" multiple><br><br> <input type="submit" value="点击这里显示文件名字与大小"> </form> <br><br><br> <form action="/create_file/" enctype="multipart/form-data" method="post"> <input name="fileb" type="file" multiple><br><br> <input name="notes" type="text" multiple><br><br> <input type="submit" value="点击这里显示文件属性"> </form> </body> </html> |
命名为:index.html
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>文件上传之后的页面</title> </head> <body> <div class="container"> <h1>NO.1</h1> <h2>File Name:{{ filenames }}</h2> <h2>File Size:{{ file_sizes }}</h2> <h1>NO.2</h1> <h2>File Size:{{ fileb_size }}</h2> <h2>File Type:{{ fileb_content_type }}</h2> <h2>File Name:{{ fileb_name }}</h2> <h2>File Notes:{{ notes }}</h2> <h2>上传结果:{{ 上传结果 }}</h2> </div> <!-- /container --> </body> </html> |
部分代码参考:https://github.com/kaikai03/inpainting_backen
布施恩德可便相知重
微信扫一扫打赏
支付宝扫一扫打赏