【Python-Web后端开发框架】Flask | Django | FastAPI | Tornado 选型与 使用 | 特性

开发架构特性与使用场景

框架 架构类型 核心定位 实时能力 学习曲线 性能 适用场景
Flask 微框架 灵活自由 ⭐⭐ 中等 小型项目、API服务、快速原型
Django 全栈框架 开箱即用 最弱(Channels) ⭐⭐⭐⭐ 中等 企业级应用、内容管理系统
FastAPI API框架 现代高性能,自动文档 ⭐⭐⭐ REST API、微服务、实时应用
Tornado 异步框架 异步高并发 最强 ⭐⭐⭐ 极高 长连接、WebSocket、实时推送

开发框架架构对比

ORM区别

ORM概念

  • ORM: 对象关系映射, 核心:在代码里用对象对去操作数据库,主要解决编程语言里的对象模型和数据库的表结构之间不匹配的问题,让我们不用手动写SQL,就能通过操作对象来增删改查数据库,算是专门为数据库设计的工具。

关联使用总结见:

【关系型数据库】RdbMS 关系型数据库通用操作 - python-SQLAlchemy

ORM 除了能操作Mysql、Pgsql这些关系型数据库,现在也能和一些非关系型数据库配合使用。如:

  • MongoDB: 有MongoEngine这样的ORM工具,能用类似操作关系型数据库的方式去操作MongoDB
  • Redis: Walrus库,提供了类似ORM的接口,方面用对象的方式操作Redis数据结构

实现差异

除了Django自带ORM,Flask | FastAPI | Tornado 都不自带,但是都可通过集成SQLAlchemy等实现。

底层核心技术栈区别

  1. Flask

    复制代码
    WSGI服务器:Werkzeug(核心HTTP/WSGI处理)
    
    模板引擎:Jinja2(默认,可替换)
    
    依赖注入:简单的函数装饰器模式
    
    路由系统:基于Werkzeug的路由表
    
    线程模型:同步多线程(默认)

    设计哲学:微框架,保持核心简单,通过扩展增强功能

  2. Django

    复制代码
     WSGI服务器:自研WSGI处理器(django.core.handlers.wsgi/wsgi)
    
     ORM系统:自研ORM(django.db.models)
    
     模板引擎:Django Template Language(DTL)
    
     中间件系统:基于类的请求/响应处理链
    
     路由系统:基于正则表达式和路径转换器
    
     线程模型:同步多线程

    设计哲学:全功能框架,"开箱即用",约定优于配置

  3. FastAPI

    复制代码
     ASGI服务器:Starlette(核心HTTP/WebSocket处理)
    
     数据验证:Pydantic(基于Python类型提示)
    
     依赖注入:自研依赖注入系统
    
     异步支持:基于asyncio的协程
    
     文档生成:OpenAPI/Swagger自动生成
    
     路由系统:Starlette路由系统

    设计哲学:高性能API优先,类型安全,自动文档生成

  4. Tornado

    复制代码
     HTTP服务器:自研非阻塞HTTP服务器
    
     I/O模型:事件循环(ioloop)
    
     协程支持:自研协程(早期)或asyncio集成
    
     模板引擎:自研模板系统
    
     WebSocket:原生支持
    
     线程模型:单线程事件循环

    设计哲学:异步非阻塞,长连接优化,适合实时应用

请求处理区别

框架 并发模型 I/O处理
Flask 同步多线程
Django 同步多线程 阻塞I/O
FastAPI 异步单线程 非阻塞I/O
Tornado 异步单线程 非阻塞I/O

中间件区别

  • 是一种用于在请求达到视图之前或者响应返回客户端之前,对请求/响应进行统一处理的机制

应用:日志记录、身份验证、跨域处理、错误处理等

框架 中间件
Flask 上下文全局变量 + 装饰器中间件
Django 类基础的中间件链(process_request/process_response)
FastAPI Starlette中间件系统 + 依赖注入
Tornado 请求钩子(prepare/on_finish

路由实现区别

  • Flask: 基于装饰器的简单路由
python 复制代码
@app.route('/user/<id>')
def get_user(id):
    pass
  • Django: URLconf模式
python 复制代码
# urls.py
path('user/<int:id>/', views.get_user)
  • FastAPI: 类型提示路由
python 复制代码
@app.get('/user/{id}')
async def get_user(id: int):
    pass
  • Tornado: 类处理器路由
python 复制代码
class UserHandler(tornado.web.RequestHandler):
    def get(self, id):
        pass

RESTful

  • 本质上是对规范HTTP接口设计风格的实现
  • 核心是通过 "资源URI + HTTP方法 + 状态码" 实现语义清晰、可扩展、无状态的接口通信
  1. 以资源为中心的URI设计
  2. 使用标准HTTP方法表达操作
  • GET :获取资源
  • POST:创建资源
  • PUT/PATCH :更新资源
  • DELETE:删除资源
  1. 无状态通信
    不保存客户端的状态信息,每次请求都必须包含此次所需的所有请求参数
  2. 资源的多种表达形式
    资源可以通过多种格式返回,如:json/xml/html等
    客户端通过请求头里面的Accept请求头字段指定
  • 如:Accept:application/json
  1. 状态妈域错误处理
    使用标准HTTP状态码表达请求结果
  • 1xx: 提示信息状态码
  • 2xx: 成功状态码
  • 3xx: 资源重定向
  • 4xx: 客户端错误(请求有问题)
  • 5xx: 服务端错误(服务端错误)
  • 是目前前后端分离、微服务架构中最主流的设计方式

Flask

  • 优点:轻量级,灵活,核心功能简单,很适合小型项目或者需要高度定制的项目
  • 缺点: 扩展性差,异步支持不够好

RESTful 手动支持

Falsk 通过使用红图 + 蓝图 + 应用 的三级架构实现; FastAPI 原生支持

中间件

在对应的功能函数前,使用以下装饰器修饰:

@app.before_request:每个请求(不分路由)到达视图前必须前(按注册顺序)执行

@app.after_request:每个请求(不分路由)正常返回后(按注册逆序)执行

FastAPI

  • 优点:性能高、支持异步编程、自动生成API文档、自带数据库类型校验(Pydantic)
  • 缺点:生态支持比Django小,由于使用的人没有那么庞大,缺少一些现成的第三库

自动生成OpenAPI文档

  • OpenAPI规范:一种用于描述RESTful API标准格式的规范
  • FastAPI 会自动生成交互式界面,方便开发者调试和对接
  • 支持在文档中发送请求、查看响应结果,不需要postman等调试工具。
  • 自定展示API的路径,请求方法、参数(路径参数、查询参数、请求体)、响应状态码和数据结构。
    -可以根据代码修改,自动调整对应的交互调试文档

类型校验

  • 类型提示主要了解Python内置的类型,比如:str, int, list, tuple等
  • 使用Pydantic中的BaseModel来作为定义数据结构和类型的模板

Pydantic:BaseModel

python 复制代码
from pydantic import BaseModel
from fastapi import FastAPI

app = FastAPI()

class User(BaseModel):
	name: str
	age: int

@app.post("/users/")
async def create_user(User:user):
	return {"message":f"crated user:{user.name} and age:{user.age}"}

异步支持 async/await

python 复制代码
from fastapi import FastAPI
import asyncio

app = FastAPI()

class User(BaseModel):
	name: str
	age: int
	user_id: int

async def async_query_db(user_id:int):
	r_json = {}
	return r_json

@app.get("/user/{user_id}")
async def get_userinfo(user_id):
	info = await async_query_db(user_id)
	return info

Django

  • 优点:大而且全,自带ORM、Admin后台、用户认证等很好多功能。适合快速开发大项目,安全性和扩展性都很强
  • 缺点:比较笨重,不适合小型项目,用它会有点杀鸡用牛刀

Tornado

  • 优点:支持异步非阻塞IO,处理高并发请求能力强,像长连接、WebSockets这种场景用它就很合适; 自带HTTP服务器,能独立运行,不用搭别的服务器
  • 缺点:学习难度大,生态小

web后端开发框架域前端的连接

  • 后端域前端的连接本质上通过网络通信实现的数据交互,核心是前端发送请求,后端处理请求并返回响应。
  • 常见的通信方式:HTTP/HTTPS 和 WebSocket

HTTP/HTTPS协议通信(主流)

  • 单向 请求-响应模式

基本流程

  1. 前端通过浏览器/客户端(如:Vue、React)的API(如:fetch、axios)发送HHTP请求(含参数)前端框架
  2. 后端通过框架(如:Flask、Djingo、FastAPI、Tornado)通过路由匹配接受请求,解析参数并处理
  3. 后端将处理结果封装为HTTP响应返回给前端
  4. 前端接受响应,更新页面UI

参数传递方式

  • 取决于HTTP请求的方法和参数的类型
1. GET 请求(参数在URL中传递)
  • 适合传递少量敏感数据(如查询条件)
  • 参数会在URL中显示

例:axios + FastAPI

javascript 复制代码
// 传递id=123和name="test"两个参数
axios.get('/api/user', {
  params: {
    id: 123,
    name: 'test'
  }
}).then(response => {
  console.log(response.data); // 接收后端返回的数据
});

实际请求URL为:/api/user?id=123&name=test

python 复制代码
from fastapi import FastAPI
app = FastAPI()

# 从URL查询参数中获取id和name
@app.get("/api/user")
def get_user(id: int, name: str):
    return {"message": f"用户ID:{id},名称:{name}"} # {"message": f"用户ID:123,名称:test"}

如果是flask,需要手动获取参数:

python 复制代码
request_json = request.args # type(request_json) : dict
2. POST 请求(参数在请求体中传递)
  • 适合传递大量数据、敏感数据(如表达提交、json数据)
  • 参数不在URL中显示

例:axios + FastAPI

javascript 复制代码
axios.post('/api/login', {
  username: 'admin',
  password: '123456'
}).then(response => {
  console.log(response.data);
});
python 复制代码
from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()

# 定义请求体模型(自动验证参数)
class LoginData(BaseModel):
    username: str
    password: str

@app.post("/api/login")
def login(data: LoginData):
    if data.username == 'admin' and data.password == '123456':
        return {"status": "success", "token": "xxx"}
    else:
        return {"status": "error", "message": "账号密码错误"}

如果是flask,需要手动获取参数:数据格式字段标识:Content-Type

python 复制代码
# Content-Type: application/json
request_json = request.get_json() #type(request_json) : dict

# Content-Type: x-www-form-urlencoded 
# 或者Content-Type: multipart/form-data
r_name = request.form.get("name")
3. 路径参数(参数作为URL的一部分)
  • 适合标识资源
  • 参数直接嵌入URL路径中

例:axios + Falsk

javascript 复制代码
// 获取ID为123的用户信息,参数123在URL路径中
axios.get('/api/user/123').then(response => {
  console.log(response.data);
});
python 复制代码
rom flask import Flask, jsonify
app = Flask(__name__)

# 从URL路径中获取user_id
@app.route('/api/user/<int:user_id>')
def get_user(user_id):
    return jsonify({"user_id": user_id, "name": "张三"})
4. 文件上传(通过multipart/form-data格式)
  • 适合传递文件:图前、文档
  • 前端需要设置请求头:Content-Type:multipart/form-data

例:HTML表单/javaScript + Django

xml 复制代码
<form id="uploadForm">
  <input type="file" name="file" id="fileInput">
  <button type="button" onclick="uploadFile()">上传</button>
</form>

<script>
function uploadFile() {
  const formData = new FormData();
  formData.append('file', document.getElementById('fileInput').files[0]);
  axios.post('/api/upload', formData, {
    headers: {'Content-Type': 'multipart/form-data'}
  }).then(response => {
    console.log(response.data);
  });
}
</script>
python 复制代码
from django.http import JsonResponse
from django.views.decorators.csrf import csrf_exempt

@csrf_exempt  # 测试环境关闭CSRF验证
def upload(request):
    if request.method == 'POST' and request.FILES.get('file'):
        file = request.FILES['file']
        # 处理文件(如保存到服务器)
        return JsonResponse({"status": "success", "filename": file.name})
    return JsonResponse({"status": "error"})

WebSocket(实时|双向通信)

HTTP是单向的"前端请求-后端响应"模式,不合适聊天或者需要实时更新数据的场景

  • 支持全双工通信: 前后端可主动发送消息

基本流程

  1. 前端于后端通过webSocket简历持久连接(握手阶段用HTTP)
  2. 连接建立后,双方可随时发送消息(不用反复建立连接)
  3. 断开连接时需要手动关闭

例:webSocket + Flask

javascript 复制代码
// 建立WebSocket连接(ws://或wss://)
const ws = new WebSocket('ws://localhost:8000/ws/chat');

// 接收后端消息
ws.onmessage = function(event) {
  console.log('收到消息:', event.data);
};

// 发送消息到后端
function sendMessage() {
  ws.send(JSON.stringify({user: '张三', content: '你好'}));
}
python 复制代码
from fastapi import FastAPI, WebSocket
from fastapi.responses import HTMLResponse

app = FastAPI()

@app.websocket("/ws/chat")
async def websocket_endpoint(websocket: WebSocket):
    await websocket.accept()  # 接受连接
    while True:
        data = await websocket.receive_text()  # 接收前端消息
        # 处理消息(如广播给其他用户)
        await websocket.send_text(f"后端收到:{data}")  # 发送消息给前端
相关推荐
2401_831920742 小时前
Python生成器(Generator)与Yield关键字:惰性求值之美
jvm·数据库·python
光影少年2 小时前
说说模块化规范?CommonJS和ES Module的区别?
前端·javascript·elasticsearch
飞Link2 小时前
具身智能中 Wrapper 架构的深度解构与 Python 实战
开发语言·python·架构
2401_842623652 小时前
使用Seaborn绘制统计图形:更美更简单
jvm·数据库·python
telllong2 小时前
C++20 Modules:从入门到真香
java·前端·c++20
weixin_531651812 小时前
Python 渐进式学习指南
开发语言·windows·python
2401_832035342 小时前
Python数据库操作:SQLAlchemy ORM指南
jvm·数据库·python
七夜zippoe2 小时前
Elasticsearch全文搜索与数据分析实战指南
大数据·python·elasticsearch·数据分析·全文搜索