02 第2周D11 PostgresSQL
D11 作业:建表查询 + 给 D10 的 API 接上数据库
D11 作业:建表查询 + 给 D10 的 API 接上数据库
目标
- 验证:会建表/查询/事务、理解金额用 NUMERIC,能把 FastAPI 接上 Postgres。
场景
- 本地开发机;本地 Postgres(Docker:
docker run -d --name pg16 -e POSTGRES_PASSWORD=z1a2q3W4 -p 5432:5432 postgres:16)。
任务
任务 1:建表 + 基础查询
-- 连上后执行
CREATE DATABASE labdb; -- 或直接连默认库- 建两张表(符合课程口径):
CREATE TABLE users (
id BIGSERIAL PRIMARY KEY,
name TEXT NOT NULL,
balance NUMERIC(20,8) NOT NULL DEFAULT 0
);
CREATE TABLE bills (
id BIGSERIAL PRIMARY KEY,
user_id BIGINT NOT NULL REFERENCES users(id),
amount NUMERIC(20,8) NOT NULL,
type TEXT NOT NULL,
created_at TIMESTAMPTZ NOT NULL DEFAULT now()
);- 插入 3 个用户、若干流水;写出 3 条查询:余额 >0 的用户、按 type 分组统计、某用户的总消费(JOIN)。
任务 2:验证事务(重点)
BEGIN;
UPDATE users SET balance = balance - 10 WHERE id = 1;
INSERT INTO bills (user_id, amount, type) VALUES (1, 10, 'chat');
COMMIT; -- 观察余额与流水一致
-- 再试一次中途 ROLLBACK,验证"要么全成要么全不成"
BEGIN;
UPDATE users SET balance = balance - 10 WHERE id = 1;
ROLLBACK; -- 观察余额没变- 用文字回答:为什么扣费必须用事务?如果"扣了余额但流水没记"会怎样?
任务 3:给 D10 的 API 接库(选做加分)
- 用 asyncpg 把 D10 的 users CRUD 从内存 dict 换成真库。
- 至少实现 GET /users/{uid} 读库、POST /users 写库,其余可留 TODO。
验收标准(讲师核验用)
- 任务 1:两张表结构正确(含外键),3 条查询输出正确
- 任务 2:事务两段演示结果正确,能口头解释原子性
- 任务 3(加分):CRUD 已从 dict 换成真库并能跑通
提交方式
- SQL 脚本与回答放
docs/training/学员/<姓名>/D11/,按 D6 流程提交 PR,中文提交信息,如:D11 作业:SQL与事务(姓名)。
参考
- 课程.md 第 2、4、5、6 节
- 学习网站.md → D11 分组