改数据库字段前,先让 Codex 读迁移历史搞清字段为什么长这样
这篇文章教你在改数据库字段之前,用 Codex 把迁移历史读一遍,还原每个字段是什么时候、因为什么加进来的,后来有没有被废弃或加了兼容逻辑。做完后你会得到一份字段演进时间线,以及哪些字段能改、哪些改起来有兼容包袱的判断。它解决的不是“这个字段存什么”,而是“这个字段为什么长成这样、动了会牵连谁”。
适合人群
需要改数据库字段的后端工程师
先解决什么
数据库里有多个相似字段,没人确定哪个还能用。
学完结果
字段演进时间线和可修改建议。
你会学到什么
让 Codex 按迁移时间线还原字段新增、废弃和兼容逻辑。
准备材料:迁移文件目录、schema 快照、相关查询代码、线上字段样例。
交付物:字段演进时间线和可修改建议。
边界:比数据流主题更关注数据库历史和兼容包袱。
教程定位
这篇教程解决什么问题
这篇文章教你在改数据库字段之前,用 Codex 把迁移历史读一遍,还原每个字段是什么时候、因为什么加进来的,后来有没有被废弃或加了兼容逻辑。做完后你会得到一份字段演进时间线,以及哪些字段能改、哪些改起来有兼容包袱的判断。它解决的不是“这个字段存什么”,而是“这个字段为什么长成这样、动了会牵连谁”。
很多数据库问题卡在“历史”。你打开表结构,看到 `price`、`list_price`、`sale_price` 三个字段,代码里三处各用各的,没人敢删。直接问 Codex“这三个字段哪个有用”,它只能猜;但如果先喂迁移历史,Codex 能按时间顺序还原:哪个是原价、哪个后来为了活动引入、哪个只剩兼容。本文就是这套让 Codex 基于证据而不是猜测来回答的方法。
使用场景
什么情况下最适合用这一套
你接手一个项目,要改某个表字段,比如给订单表加一个状态,或者把 `customer_phone` 从必填改成选填。改之前你发现表里已经有几个看起来重复的字段,旧的迁移文件、schema 快照、查询代码散落各处,团队里没有人能说清这些字段当初为什么加。
最怕的是你按自己的理解改了字段,结果线上某个老功能、报表、导入脚本还在读旧字段,悄悄出问题。本文的方法就是:让 Codex 沿着迁移时间线把字段的“出生”和“变化”读出来,标注哪些是活跃使用、哪些只剩兼容、哪些可能已经没人用,再决定改不改。
材料准备
开始前先把材料和边界备齐
准备下面这些材料,Codex 才有足够证据判断:
如果迁移文件很多,先只挑和目标表相关的,不要一次把所有库都丢给 Codex,否则它会被无关信息淹没。
- 迁移文件目录:项目里所有 `migrations/` 或 `db/migrations` 下的 SQL 或 ORM 迁移文件,按文件名里的时间戳或版本号排序。
- 当前 schema 快照:建表语句、或 `schema.prisma` / `schema.rb` 等最新定义。
- 相关查询代码:读取或写入这些字段的 repository、service、报表 SQL。
- 线上字段样例:一两条真实数据里这些字段的值,用来佐证哪个在真正使用。
- 你真正要做的改动:加字段、改类型、改必填、删除字段还是加索引。
实操流程
按这套步骤把工作跑起来
【第一步:把目标表的迁移按时间排序】
先找出所有影响目标表的迁移文件。用 Codex 帮你按文件名里的版本号或时间戳排序,去掉和这张表无关的。排序后你就能得到一个时间线,这是后面所有判断的基础。
【第二步:让 Codex 逐条还原每个字段的变更】
针对目标表的每个字段,让 Codex 在时间线上找出:第一次出现的迁移、之后每次改类型/改默认值/加索引的迁移、以及任何标记废弃或兼容的注释。产出是一张“字段 × 迁移”的对照表。
【第三步:标注字段当前的使用情况】
把查询代码交给 Codex,让它统计每个字段在哪些代码路径里被读、被写、被用于条件判断。重点标记:还有没有活跃写入、有没有只在历史兼容分支里读、有没有既没写入也没读取。
【第四步:区分活跃、兼容、废弃三类字段】
结合前两步,让 Codex 把字段分成三类:活跃使用(改它有风险)、仅兼容(旧数据或旧代码还在读,不能直接删)、疑似废弃(没有引用,可进一步确认)。产出一张分类表。
【第五步:给出可修改建议和验证清单】
最后让 Codex 针对你的目标改动,给出建议:哪些字段可以放心改、哪些要先加兼容逻辑、哪些改动上线后要跑什么验证。每一类都要给出具体的验证动作,比如查日志、跑旧查询、看报表。
输入示例
可以直接参考的输入材料
下面是一个你实际会粘给 Codex 的材料,包含迁移文件片段和查询代码:
背景:我在订单表 orders 上要加一个 status 字段,但表里已经有 payment_status 和 paid_at,
不确定它们和我要加的关系。请帮我还原这几个字段的演进历史。
迁移文件(按版本排序):
-- 2023-03-01 create_orders.sql
CREATE TABLE orders (
id BIGINT PRIMARY KEY,
customer_id BIGINT,
payment_status VARCHAR(20) DEFAULT 'pending',
paid_at TIMESTAMP NULL
);
-- 2023-09-12 add_refund_status.sql
ALTER TABLE orders ADD COLUMN refund_status VARCHAR(20) DEFAULT 'none';
-- 2024-05-20 add_payment_flow.sql
ALTER TABLE orders ADD COLUMN payment_flow VARCHAR(40) DEFAULT 'legacy';
UPDATE orders SET payment_flow='v2' WHERE payment_status IN ('paid','refunded');
当前查询代码(片段):
// 老退款逻辑
if (order.refund_status === 'none' && order.payment_status === 'paid') { ... }
// 新支付流程
if (order.payment_flow === 'v2') { ... }
请输出:每个字段的引入时间线、当前使用情况、以及我要加 status 时的兼容建议。提示词
可复制使用的提示词
你是资深数据库工程师。请基于我提供的迁移历史、schema 快照和查询代码,还原目标表字段的演进,并给修改建议。
要求:
1. 按迁移时间线输出每个字段的首次引入、每次变更和废弃/兼容标记。
2. 区分活跃使用、仅兼容、疑似废弃三类字段,并给出依据(迁移语句或代码引用)。
3. 针对我要做的改动,说明哪些能直接改、哪些要先加兼容、哪些改动后必须验证什么。
4. 只依据我给的证据,不要编造迁移或代码里没有的内容;证据不足的标注“需人工确认”。
5. 输出用表格,最后给一张“改动风险与验证清单”。
我要做的改动:{{在这里写你的目标改动}}
迁移文件:{{粘贴上面整理好的材料}}输出样例
AI 应该输出到什么程度
Codex 可能给出类似下面的结果:
字段演进时间线:
- payment_status:2023-03-01 引入,默认 pending,是老订单状态主字段;至今仍被老退款逻辑读取。
- paid_at:2023-03-01 引入,记录支付时间;报表依赖,属于活跃使用。
- refund_status:2023-09-12 引入,默认 none;仅用于老退款流程,新流程不再写入。
- payment_flow:2024-05-20 引入,标记 v2 支付流程;新支付链路活跃使用,老订单为 legacy。
分类:
- 活跃:payment_status、paid_at、payment_flow(v2)
- 仅兼容:refund_status、payment_flow(legacy 值)
- 疑似废弃:无,但需进一步确认 refund_status 是否仍被历史报表读取
你的改动建议:
加 status 建议用 payment_flow 作为判断依据,而不是新建一套状态;若必须新建,上线后要跑一次老订单的兼容查询,确认 refund_status 分支不受影响。人工验收
人要怎么检查和改到可用
拿到 AI 结果后,按下面几点核对:
- 逐条对照迁移文件:Codex 说“字段在 2023-09-12 引入”,你要回到那个迁移确认确实有这条 ALTER,不能只看它的结论。
- 核对代码引用:它说的“老退款逻辑在读 refund_status”,要确认代码路径确实存在且还在执行,而不是被删掉的死代码。
- 区分“没人写”和“没人读”:一个字段可能没人写但老报表还在读,这类是兼容字段,不能直接删。
- 补上 AI 看不到的信息:字段的实际语义、历史业务规则、以及公司里只有老员工知道的坑,这些 AI 无从得知,必须人工确认。
- 改动前把兼容验证写成清单:哪些查询、报表、导入脚本要回归,逐条打勾。
失败反例
这些失败反例要提前避开
**反例 1:让 Codex 直接猜字段用途。** 不给迁移历史,只给表结构,Codex 只能根据字段名和类型瞎猜,得出的“哪个有用”不可信。必须把时间线证据喂进去。
**反例 2:把无关迁移全丢给它。** 把整个库几百个迁移文件都粘给 Codex,它被淹没,反而漏掉目标表的关键迁移。先按表筛选再排序。
**反例 3:只看“是否被代码引用”就删字段。** 一个字段代码里没引用,但历史报表、导出脚本、外部系统还在读。引用判断必须覆盖所有消费方,不能只看应用代码。
**反例 4:改了字段不验证老逻辑。** 只跑新功能自测,没回归老退款、老报表路径,上线后才暴露兼容问题。每次改动都要把兼容验证清单逐条跑一遍。
**反例 5:把 AI 的历史结论当事实。** Codex 还原时间线基于你给的证据,但可能漏掉注释或理解错语义。所有关键结论都要回到原始迁移和代码里人工复核。
主题边界
它和相邻主题的区别
这篇只处理“通过迁移历史还原字段演进并判断改动风险”,不涉及数据流分析、索引优化或表结构设计。与读项目结构、找错误根因等主题不同,它聚焦数据库字段的历史包袱和兼容性;与直接写迁移改字段也不同,它先做风险判断再动手。
教程正文
更进一步:怎么把这张时间线用起来
拿到字段演进时间线和风险表之后,真正的价值在于把它变成团队可复用的资料。建议把每张表的“字段演进时间线”存成一个简单的 markdown 或文档,放进项目里和迁移目录放一起。这样下一次有人要改这个表,不用再从头把迁移读一遍,直接看这份资料就知道哪些字段能碰、哪些只能兼容。
另一个值得做的动作,是把“哪些字段疑似废弃”单独列一张清单,和负责人确认。数据库里的死字段往往没人删,但留着会让新人不明所以。确认后要么加注释、要么安排清理,前提是先跑一遍消费方检查,确保没有任何查询、报表、导入脚本还在读它。
教程正文
常见失败反例补充
**反例 6:只改 schema 不查消费方。** 以为删了代码里没引用的字段就安全,却没查报表 SQL 和导入脚本,结果上线后报表报错。凡是删字段,必须把所有读它的入口都过一遍。
**反例 7:把兼容逻辑当废弃。** 看到 `payment_flow='legacy'` 就以为是死值,想直接清理,结果老订单的兼容分支还在用。要区分“历史数据值”和“废弃字段”,两者处理方式完全不同。
可直接套用的流程
1. 先写清楚任务目标:这次要让 AI 帮你完成什么工作,而不是泛泛地问一个问题。
2. 再给资料边界:哪些背景、数据、约束、口径必须被使用,哪些内容不能编。
3. 最后规定输出格式:用清单、表格、方案、话术还是复盘报告,并保留人工检查。
本文属于专题「读项目与上下文」
本专题第 3 篇 / 共 7 篇