从单体到微服务:零基础也能搭建分布式系统
大家好,我是团队的后端培训负责人,带过几十位应届生。每次看到新人面对“微服务”这个词一脸茫然,我就想起自己刚入行时的样子——以为这玩意儿得懂高深算法、分布式理论才能碰。其实不然!今天这篇教程,就是专门为完全零基础的同学写的。无论你有没有写过后端,只要会一点 Python,就能跟着动手做出一个真正的微服务系统。
为什么我要写这篇教程?
很多教程一上来就讲“CAP理论”“服务注册中心”“熔断机制”,把新手直接劝退。但微服务的本质很简单:把一个大程序拆成几个小程序,各自独立运行,通过网络互相调用。就像一家餐厅,原来一个厨师既切菜又炒菜还收钱(单体),现在分成切配组、炒菜组、收银组(微服务),效率更高、出错也更容易定位。
今天我们就用 Python 和一点点前端知识,亲手完成这个转变。
第一步:开发环境准备(10分钟搞定)
💡 提示:哪怕你从来没装过 Python,照着做就行!
你需要安装:
| 工具 | 作用 | 安装方式 |
|---|---|---|
| Python 3.8+ | 编写后端服务 | 官网下载或 brew install python(Mac) |
| pip | Python 包管理器 | 随 Python 自带 |
| Flask | 轻量级 Web 框架 | pip install flask |
| requests | 发送 HTTP 请求 | pip install requests |
验证是否成功:
python --version # 应显示 Python 3.x
pip list # 看到 flask 和 requests 即可
✅ 新手常见问题:
Q:我用 Windows 怎么办?
A:完全没问题!官网下载 Python 安装包,勾选“Add to PATH”,其余步骤一样。
Q:能不能用 Django?
A:可以,但 Flask 更轻量,适合入门微服务概念。
第二步:先做一个“单体应用”
在拆分之前,我们得先有一个完整的应用。假设我们要做一个用户信息查询系统:
- 用户访问网页,输入 ID
- 后端返回该用户的名字和邮箱
1. 创建单体项目
新建文件夹 monolith-app,里面创建 app.py:
# app.py
from flask import Flask, request, jsonify, render_template_string
app = Flask(__name__)
# 模拟数据库
users_db = {
1: {"name": "张三", "email": "zhangsan@example.com"},
2: {"name": "李四", "email": "lisi@example.com"}
}
# 前端页面(极简版)
HTML_TEMPLATE = '''
<h2>用户查询系统</h2>
<form method="GET">
用户ID: <input type="number" name="user_id" min="1" max="2" required>
<button type="submit">查询</button>
</form>
{% if user %}
<p>姓名: {{ user.name }}</p>
<p>邮箱: {{ user.email }}</p>
{% endif %}
'''
@app.route('/')
def home():
user_id = request.args.get('user_id')
user = None
if user_id:
user = users_db.get(int(user_id))
return render_template_string(HTML_TEMPLATE, user=user)
if __name__ == '__main__':
app.run(port=5000)
运行:
python app.py
浏览器打开 http://localhost:5000,输入 1 或 2,就能看到用户信息。
🧠 我当初学的时候,总想把前端做得花里胡哨。其实微服务关注的是后端逻辑拆分,前端只要能发请求就行。所以这里用 Flask 内嵌 HTML,省去额外前端工程。
第三步:什么是微服务?通俗解释
微服务的核心思想就两点:
单一职责:每个服务只做一件事
- 用户服务:管用户数据
- 订单服务:管订单数据
- 支付服务:管支付逻辑
独立部署:一个服务挂了,不影响其他服务
对比单体与微服务:
| 特性 | 单体应用 | 微服务 |
|---|---|---|
| 代码结构 | 所有功能在一个项目里 | 每个功能一个独立项目 |
| 部署方式 | 整个应用一起上线 | 每个服务单独上线 |
| 扩展性 | 只能整体扩容 | 哪个服务压力大就扩哪个 |
| 开发难度 | 初期简单,后期混乱 | 初期复杂,长期清晰 |
第四步:动手拆!从单体到两个微服务
我们现在把刚才的单体拆成两个服务:
- 前端服务:只负责展示页面(纯前端)
- 用户服务:只提供 API 接口(纯后端)
第一步:创建用户服务(user-service)
新建文件夹 user-service,创建 user_api.py:
# user_api.py
from flask import Flask, jsonify
app = Flask(__name__)
users_db = {
1: {"name": "张三", "email": "zhangsan@example.com"},
2: {"name": "李四", "email": "lisi@example.com"}
}
@app.route('/user/<int:user_id>')
def get_user(user_id):
user = users_db.get(user_id)
if user:
return jsonify(user)
else:
return jsonify({"error": "User not found"}), 404
if __name__ == '__main__':
app.run(port=5001) # 注意端口改成了5001
运行:
python user_api.py
测试接口:浏览器访问 http://localhost:5001/user/1,应返回 JSON 数据。
第二步:创建前端服务(frontend)
新建文件夹 frontend,创建 web.py:
# web.py
from flask import Flask, request, render_template_string
import requests
app = Flask(__name__)
HTML_TEMPLATE = '''
<h2>用户查询系统(微服务版)</h2>
<form method="GET">
用户ID: <input type="number" name="user_id" min="1" max="2" required>
<button type="submit">查询</button>
</form>
{% if user %}
<p>姓名: {{ user.name }}</p>
<p>邮箱: {{ user.email }}</p>
{% elif error %}
<p style="color:red">{{ error }}</p>
{% endif %}
'''
@app.route('/')
def home():
user_id = request.args.get('user_id')
user = None
error = None
if user_id:
# 调用用户服务的 API
try:
resp = requests.get(f'http://localhost:5001/user/{user_id}')
if resp.status_code == 200:
user = resp.json()
else:
error = "用户不存在"
except requests.exceptions.ConnectionError:
error = "用户服务暂时不可用"
return render_template_string(HTML_TEMPLATE, user=user, error=error)
if __name__ == '__main__':
app.run(port=5000)
运行:
python web.py
现在,你的系统变成这样:
用户 → 前端服务 (5000端口) → 用户服务 (5001端口)
打开 http://localhost:5000,功能和之前一模一样!但架构已经完全不同。
🔍 关键变化:
- 前端不再直接访问数据库,而是调用另一个服务的 HTTP 接口
- 用户服务只暴露 API,不包含任何页面逻辑
- 两个服务可以分别重启、升级、扩容
第五步:新手常踩的坑 & 解决方案
❌ 坑1:跨域问题(CORS)
当你用真正的前端框架(如 Vue/React)调用 API 时,浏览器会报错:
Blocked by CORS policy
✅ 解决:在用户服务中添加 CORS 支持
from flask_cors import CORS # 先 pip install flask-cors
app = Flask(__name__)
CORS(app) # 允许所有来源(生产环境要限制)
❌ 坑2:服务之间调用失败
前端调用户服务时,如果用户服务没启动,会报连接错误。
✅ 解决:
- 开发时确保所有服务都运行
- 生产环境要用服务发现(如 Consul)或API 网关
❌ 坑3:数据一致性
如果未来加了“订单服务”,用户删了,订单还在怎么办?
✅ 初学者建议:先用最终一致性 + 重试机制,别一上来就想强一致。
第六步:下一步怎么学?
你已经迈出了微服务的第一步!接下来建议按这个路径走:
学 Docker:把每个服务打包成容器,一键启动
# 示例:user-service 的 Dockerfile FROM python:3.9 COPY . /app WORKDIR /app RUN pip install flask CMD ["python", "user_api.py"]引入服务注册与发现:用 Consul 或 Eureka 让服务自动找到彼此
加 API 网关:用 Nginx 或 Spring Cloud Gateway 统一入口
学消息队列:用 RabbitMQ/Kafka 解耦服务(比如用户注册后发欢迎邮件)
监控与日志:用 Prometheus + Grafana 监控服务健康度
💬 最后送大家一句话:微服务不是银弹,单体也不是垃圾。我见过太多团队为了“上微服务”而拆,结果维护成本翻倍。只有当你的单体应用真的变得庞大、难以维护时,才考虑拆分。
总结
今天我们:
- 用 Python Flask 做了一个单体应用
- 把它拆成前端服务 + 用户服务
- 理解了微服务的核心思想:拆分、独立、通信
- 避开了新手常见陷阱
记住:架构是为业务服务的,不是为了炫技。你现在做的这个小 demo,已经比很多“只会背概念”的人强多了。
下次团队面试,你可以自信地说:“我亲手做过微服务拆分。”
加油!有问题欢迎留言,我会一一解答。

评论 0