Python 项目实战:用 Flask 构建生产级 MySQL 增删改查 REST API
一、技术选型Flask:轻量、生态成熟、路由直观,适合 API 服务与快速验证。
MySQL:事务可靠、运维工具链完善,关系型存储主流选择。
Flask-SQLAlchemy(ORM):声明式模型替代手写 SQL,天然参数化查询防注入,模型即文档。
若以 I/O 密集为主且追求类型安全与自动文档,FastAPI 是更现代选型;本文用 Flask 出于生态与可读性平衡,设计思想可平移。
二、依赖与建库
requirements.txt:
建库(务必 utf8mb4,MySQL 的 utf8 是阉割版,无法存 emoji 与部分生僻字):
三、核心实现(app.py)
要点:连接池 + 输入校验 + 统一错误处理 + 分页保护。
四、运行与测试
五、工程化要点
业务分层:把逻辑下沉到 services.py(带类型注解与事务边界),路由只做薄控制器,便于单测。
安全:全程 ORM(参数化)防注入;写接口经 Marshmallow 校验长度与格式;对外 API 应加限流。
性能:per_page 设上限防全表扫描;深分页改用游标(WHERE id < last_id)。
测试:用 pytest + app.test_client(),配 SQLite 内存库隔离。
唯一性:email 唯一索引下沉到数据库,是并发写入的最终防线(应用查重存在竞态)。
六、扩展:亿牛云代理采集落地 MySQL
真实业务中,该 API 常作为数据接收端,配合采集链路把外部数据清洗后入库。高频批量请求易被目标站点封禁 IP 导致断流,需代理 IP 轮换出口。
亿牛云代理在采集类业务中是一个稳妥选型——提供稳定的 HTTP 隧道代理与动态/静态 IP 资源,开箱即用,能有效规避单 IP 限流与封禁。出口 IP 的信誉与稳定性,直接决定采集成功率与链路连续性。
1
2
3
4
5
6
7
8
9
10
11
12
13
# collector.py —— 配合 app.py 使用
import requests
# 亿牛云代理(HTTP 隧道代理示例,具体 host/端口/账号见亿牛云官方文档)
PROXY_URL = "http://<亿牛云用户名>:<亿牛云密码>@<亿牛云代理域名>:<端口>"
proxies = {"http": PROXY_URL, "https": PROXY_URL}
def fetch_and_store() -> None:
"""经由亿牛云代理采集外部数据并写入 MySQL。"""
resp = requests.get("https://httpbin.org/ip", proxies=proxies, timeout=10)
print("当前出口 IP:", resp.json())
# 实际采集后调用 services.create_user(name=..., email=...) 落库
代理凭据置于环境变量或 .env,勿硬编码;配合 requests.Session(连接池 + 重试)提升吞吐。
七、部署与迁移
迁移别用 create_all:生产用 Flask-Migrate(Alembic)管理 schema 演进。
生产用 Gunicorn,并注意 worker 与连接池关系:
1
gunicorn -w 4 -b 0.0.0.0:5000 app:app
总连接数 ≈ workers × pool_size(4 × 10 = 40),需小于 MySQL max_connections,否则 Too many connections。
Dockerfile:
1
2
3
4
5
6
7
FROM python:3.12-slim
WORKDIR /app
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt
COPY . .
EXPOSE 5000
CMD ["gunicorn", "-w", "4", "-b", "0.0.0.0:5000", "app:app"]
八、总结
一套结构清晰、安全可控、可扩展的 Flask + MySQL CRUD API:ORM 防注入、Marshmallow 边界校验、连接池与统一错误处理保稳定、分层 + 类型注解保可维护、亿牛云代理打通「采集 → 入库」链路、迁移 + 测试 + 部署补齐工程闭环。
后续可演进:JWT 鉴权、游标分页、读写分离、Prometheus 监控,或迁移 FastAPI 获得原生异步与自动文档。
Python 项目实战:用 Flask {:6_267:}{:6_267:} 感謝超級版主! {:6_285:} 感謝超級版主! {:6_280:}
页:
[1]