编辑模式 · 点击文字即可修改 · Ctrl+S 导出 再次按 E 或点击左上角退出
模块 7.1 · 全栈部署

用朴素的方案来部署

先上线

清点行囊

项目由三样东西组成

前端
静态前端
基于 React 与 Next.js 开发
可以构建成静态前端代码
后端
FastAPI 后端
基于 Python 开发
通过 Uvicorn 提供服务
存储
SQLite
硬盘上的
一个 .db 文件
模块 7 · 六节课

从"能跑"到"能长久地跑"

7.1用最朴素的办法把整套跑通、上线
7.2换成更易于维护的部署方式,反向代理实现前后端同源
7.3域名与 HTTPS
7.4通过日志与统计数据观察用户行为
7.5把存储换成 PostgreSQL
7.6调优、安全、一键发布
部署的本质

把在我们自己电脑上
能跑的东西,
在另一台机器上跑起来。

在本地

我的电脑
浏览器
拿到了页面
页面里的 JS
① 要页面
HTML · CSS · JS
:3000
npm run dev
Next.js 开发服务器
② 要数据
JSON
:8000
fastapi dev
背后是 Uvicorn
12

在线上

用户的浏览器
拿到了页面
页面里的 JS
互联网
服务器
① 要页面
HTML · CSS · JS
:80
Nginx
把 out/ 里的静态文件送出去
② 要数据
JSON
:8000
Uvicorn
跑 FastAPI,落库到 SQLite
12
盘一盘

我们已经知道的

1前端部署流程推代码 → 构建静态代码 → 交给 Nginx。模块 3、4 已经轻车熟路
2Python 环境Ubuntu 自带,想换版本也容易
3.venv 和依赖一条 pip install -r requirements.txt 全装回来
4代码和数据库代码走 git;SQLite 后端一跑就自己建出来
5启动后端服务Uvicorn 监听端口,本地一直用 fastapi dev
12345
但是

我们会遇到哪些挑战

1缺失前端配置.env.local 不进 git,服务器上没有任何前端配置
2后端配置不匹配allow_origins 写死着 localhost,线上会水土不服
3fastapi dev
只认本机
它只接收本机发来的请求,公网进不来
4终端窗口不敢关后端寄生在 SSH 会话里,窗口一关就停
5防火墙云平台安全组默认不开 8000 端口
12345
五条挑战,归拢一下

其实是四件事

1处理配置文件挑战 1、2 · 这件得在本地办,上服务器之前就要办完
2换成 fastapi run挑战 3 · 一条命令的事
3开通防火墙挑战 5 · 去云平台控制台点一下
4让后端在后台常驻挑战 4 · 等前面都跑通了,最后办
app.py
API_BASE = "https://api.weather.com"os.getenv("API_BASE") API_KEY = "sk-9f2c8a71d4e6"os.getenv("API_KEY") db = connect("postgres://root:pa55w0rd@10.0.3.17/app")os.getenv("DATABASE_URL")) app = FastAPI() app.add_middleware( CORSMiddleware, allow_origins=["http://localhost:3000"],os.getenv("ALLOWED_ORIGINS").split(","), allow_methods=["GET", "POST"], ) @app.get("/weather") def weather(city): r = requests.get(f"{API_BASE}/now", params={"key": API_KEY}) return r.json()
抽出来
+
.env · 线上服务器
.env · 测试机
.env · 我的电脑
# 换一台机器,只改这里 API_BASE=https://api.weather.com API_KEY=sk-9f2c8a71d4e6 DATABASE_URL=postgres://root:pa55w0rd@10.0.3.17/app ALLOWED_ORIGINS=http://localhost:3000
1234
配置文件的命名

基本都叫 .env,后缀在传递不同的意思

文件名
后缀在说什么
谁认这个名字
进 GIT
.env
各环境通用的那一份优先级最低,别的都盖得住它
Python 后端认的就是它Next.js 也认
✗
.env.local
本机私有别人机器上没有,也别提交 · 5.5 建的前端配置就是它
Next.js 的机制
✗
.env.production
npm run build 时才用线上前端那一份,等会儿部署时就会建
Next.js 的机制
✗
.env.example
给人看的样板键一个不少,值全是示例
没有程序认它纯粹是人的约定
✓
点开头 = 隐藏文件,ls 默认看不见 · 前端那份放项目根目录,后端那份放 backend/
本地 → 线上

两份配置的变化规律,并不一样

本地
线上
NEXT_PUBLIC_API_BASE_URL前端去哪儿找后端
http://localhost:8000
http://服务器IP:8000只换了地址
ALLOWED_ORIGINS后端允许谁来找我
http://localhost:3000
http://服务器IP地址换了,端口也没了
线上前端由 Nginx 在 80 端口提供,而 80 是 http 的默认端口——浏览器发出的 Origin 里根本不带它
1
挑战 3 · 一条命令的事

fastapi dev 与 fastapi run

fastapi dev
fastapi run
改代码自动重启
有开发时省事
没有服务器上不需要,也不该要
默认监听
127.0.0.1只听本机,外面连不进来
0.0.0.0听所有网卡,外面也能连进来
给谁用
自己电脑上开发
服务器上跑给全世界用
挑战 5 · 防火墙

80 是通的,8000 还堵着

互联网
SERVER
:80
Nginx讲前端时就放行过了
:8000
✕
Uvicorn默认不放行,堵在门外
Uvicorn去控制台放行之后,通了
云平台的安全组 / 防火墙
1
挑战 4 · 让后端在后台常驻

一句话,四个零件

nohup .venv/bin/fastapi run > backend.log 2>&1 &
&
把命令丢到后台跑,终端不用干等着
nohup
no hang up,别挂断——不再随 SSH 断开而被杀掉
> backend.log
把输出重定向进文件,没终端可打了,不接住就全丢
2>&1
把错误输出也塞进同一个文件,翻起来方便
1234
做完了,再写下来

README 该有什么

01项目名 + 一句话 它是什么、解决什么
02技术栈 用了什么语言、什么框架
03本地怎么跑起来 可复制粘贴的命令
04部署到服务器 今天走通的这一套
05配置说明 有哪些键、本地填什么、线上填什么
站点上线了,但是

这么部署,好不好?

一
后端服务脆弱
·服务器重启,不会自己起来
·崩了也不会自己起来
·停、看状态、看日志,全靠手工找
二
裸奔的 8000 端口
·没有日志
·没有加密,HTTPS 保护不到
·没有任何管控
三
前后端跨源
·CORS 限制一直得伺候
·上域名、上 HTTPS 还会持续困扰
·能不能让前后端变成同源?
123
下一节

今天先求"有",下一节再求"好"

nohup 吊着
→
systemd
开机自启、崩溃自愈、一句命令问状态看日志
8000 裸端口对着公网
→
Nginx 反向代理
把 /api/ 接进 80,8000 不再对外
前后端跨源
→
同源
都走 80,配置文件也就更简单了