Become a sponsor

本章从全局视角阐述系统的整体技术架构,涵盖前端、后端、数据库及基础设施等核心组成部分。
┌─────────────────────────────────────────────────────────────────────────┐
│ Browser (Vue3 + AntDesign) │
│ Axios HTTP Request / Vite Dev Proxy │
└──────────────────────────────┬──────────────────────────────────────────┘
│
▼
┌─────────────────────────────────────────────────────────────────────────┐
│ Nginx (反向代理) │
│ 静态资源 / SSL 终止 / 负载均衡 / gzip 压缩 │
└──────────────────────────────┬──────────────────────────────────────────┘
│
▼
┌─────────────────────────────────────────────────────────────────────────┐
│ Tornado Application │
│ │
│ ┌───────────────────────────────────────────────────────────────────┐ │
│ │ Handler 生命周期 │ │
│ │ set_default_headers() → prepare() → handler_method() → on_finish()│ │
│ │ CORS + trace_id JWT 认证 权限+日志+业务逻辑 释放DB会话 │ │
│ └───────────────────────────────┬───────────────────────────────────┘ │
│ ▼ │
│ ┌───────────────────────────────────────────────────────────────────┐ │
│ │ Service Layer (业务逻辑层) │ │
│ │ BaseService / 自定义 Service │ │
│ │ 唯一性校验 · 字段组装 · 序列化 · 文件处理 │ │
│ └───────────────────────────────┬───────────────────────────────────┘ │
│ ▼ │
│ ┌───────────────────────────────────────────────────────────────────┐ │
│ │ Repository Layer (数据访问层) │ │
│ │ BaseRepository │ │
│ │ CRUD · 软删除 · 分页 · 等值查询 · 原始条件查询 │ │
│ └───────────────────────────────┬───────────────────────────────────┘ │
│ ▼ │
│ ┌─────────────────────┐ ┌──────────────────────────────────────────┐ │
│ │ SQLAlchemy 2.0 │ │ Redis (同步客户端) │ │
│ │ ORM → SQL 生成 │ │ Token 黑名单 · 登录锁 · 字典缓存 · 权限缓存│ │
│ └──────────┬──────────┘ └──────────────────────────────────────────┘ │
└─────────────┼───────────────────────────────────────────────────────────┘
▼
┌─────────────────────────────────────────────────────────────────────────┐
│ Database (MySQL / PostgreSQL / SQL Server / SQLite / Oracle)│
│ 表前缀: tornado_ · 软删除: is_delete │
└─────────────────────────────────────────────────────────────────────────┘前端 Vue3 应用通过 HTTP API 调用后端 Tornado 服务,两者独立开发、独立部署。前端开发阶段通过 Vite 的 proxy 配置将 /api 请求代理到后端 http://127.0.0.1:8041,生产环境由 Nginx 统一反向代理。
后端严格分为四层,每层职责单一、依赖单向:
| 层次 | 目录 | 职责 |
|---|---|---|
| HTTP 层 | modules/{module}/handlers.py | 路由定义、权限装饰器、操作日志、响应返回 |
| 业务层 | modules/{module}/service.py | 业务逻辑、校验规则、序列化加工 |
| 数据层 | modules/{module}/repository.py | 数据库 CRUD、查询条件组装 |
| 模型层 | modules/{module}/models.py | 表结构定义、字段映射 |
通过 BaseRepository 和 BaseService 基类,将通用 CRUD 流程固化为模板方法。子类只需声明差异点(过滤字段、排序规则、唯一性校验等),即可获得完整的增删改查能力。
Tornado 通过 Handler 生命周期方法实现横切关注点:
# src/core/base_handler.py
class BaseHandler(tornado.web.RequestHandler):
def set_default_headers(self):
"""① 设置 CORS 头 + trace_id"""
cros_required(self)
apply_trace_id(self)
@login_required
def prepare(self):
"""② JWT 认证(白名单 URL 跳过)"""
pass
def on_finish(self):
"""④ 请求结束后释放数据库会话"""
db.close()
def write_error(self, status_code, **kwargs):
"""⑤ 异常统一响应"""
...Handler 方法中通过装饰器实现权限/演示模式/操作日志:
class PositionAddHandler(BaseHandler):
@permission_required("sys:position:add") # RBAC 权限校验
@check_demo # 演示模式拦截
@operation_log("岗位管理", "添加") # 操作日志记录
async def post(self):
return await position_service.add(self)BaseHandler.write_error() 统一捕获异常并返回标准响应:
| 异常类型 | 触发场景 | 响应 |
|---|---|---|
AuthError | JWT 过期 / 未登录 | {"code": 401, "msg": "登录过期"} |
PermissionDeniedError | 权限不足 | {"code": 403, "msg": "权限不足"} |
BusinessError | 业务逻辑错误 | {"code": 1, "msg": "..."} |
ValidationError | Pydantic 校验失败 | {"code": 1, "msg": "field: message"} |
NotFoundError | 记录不存在 | {"code": 404, "msg": "记录不存在"} |
Exception | 未捕获异常 | {"code": 500, "msg": "服务器内部错误"} |
所有 API 端点返回统一的 JSON 结构:
{
"code": 0,
"data": {},
"msg": "操作成功",
"ok": true
}成功响应 code=0,失败响应 code=1(或其他业务码),前端无需针对不同接口做差异化解析。
所有业务表通过 is_delete 字段实现软删除(0=正常,1=已删除)。BaseRepository 的等值查询方法自动追加 is_delete=0 过滤,业务代码无需关心已删除数据。
数据库事务由 Repository 层的 create() / update() / batch_delete() 方法内部 db.commit() 管理。Service 层的 try/finally 块确保 repo.close() 释放会话。BaseHandler.on_finish() 兜底关闭会话,避免长连接泄漏。
通过 DB_DRIVER 环境变量切换数据库驱动(MySQL / PostgreSQL / SQL Server / SQLite / Oracle),SQLAlchemy 的方言层屏蔽了底层差异,业务代码无需修改。
# app.py(入口)→ bootstrap.py(启动引导)→ src/app.py(应用工厂)
# 启动流程:
# 1. bootstrap.main() 解析 --port 参数
# 2. create_app() 构建 Application(路由、模板、静态目录)
# 3. register_extensions() 初始化扩展(SQLAlchemy、Redis)
# 4. HTTPServer.listen(port) 开始监听
# 5. init_scheduler() 启动定时任务调度器
# 6. 注册 SIGINT/SIGTERM 信号实现优雅关闭
# 7. ioloop.start() 启动事件循环┌──────────────────────────────────────────────────────────────┐
│ Frontend (Vue3) │
│ AntDesign · Pinia · Vue Router · Axios │
└──────────────────────────┬───────────────────────────────────┘
│ HTTP / JSON
┌──────────────────────────┴───────────────────────────────────┐
│ Tornado Application │
│ │
│ ┌─────────────┐ ┌─────────────┐ ┌──────────────────────┐ │
│ │ Handler │ │ Router │ │ Exception Handler │ │
│ │ ───────── │ │ ───────── │ │ ───────────────── │ │
│ │ CORS │ │ auth │ │ BaseAppError │ │
│ │ trace_id │ │ v1 (login │ │ write_error() │ │
│ │ login_ │ │ required) │ │ 统一 {code,data,msg} │ │
│ │ required │ │ │ │ │ │
│ └─────────────┘ └─────────────┘ └──────────────────────┘ │
│ │
│ ┌──────────────────────────────────────────────────────────┐ │
│ │ Handlers (modules/{module}/handlers.py) │ │
│ │ @permission_required · @check_demo · @operation_log │ │
│ └──────────────────────────────────────────────────────────┘ │
│ │ │
│ ┌──────────────────────────────────────────────────────────┐ │
│ │ Services (modules/{module}/service.py) │ │
│ │ BaseService · 自定义 Service │ │
│ └──────────────────────────────────────────────────────────┘ │
│ │ │
│ ┌──────────────────────────────────────────────────────────┐ │
│ │ Repositories (modules/{module}/repository.py) │ │
│ │ BaseRepository · 自定义 Repository │ │
│ └──────────────────────────────────────────────────────────┘ │
│ │ │
│ ┌──────────────────────────────────────────────────────────┐ │
│ │ Models (modules/{module}/models.py) │ │
│ │ BaseModel → SQLAlchemy ORM │ │
│ └──────────────────────────────────────────────────────────┘ │
└──────────────────────────┬───────────────────────────────────┘
│
┌────────────┴────────────┐
▼ ▼
┌────────────┐ ┌─────────────┐
│ Database │ │ Redis │
│ (MySQL等) │ │ (同步客户端) │
└────────────┘ └─────────────┘系统采用经典的前后端分离 + 分层架构设计,通过 Handler 生命周期方法和装饰器实现横切关注点(认证、权限、日志),通过基类模板方法消除重复 CRUD 代码,通过 Pydantic 实现请求参数的声明式校验。整体架构在保持简洁的同时,具备良好的可扩展性和可维护性。