FDE·踩坑总账
目录
踩坑总账 模板库 技术基础目录

跨模块踩坑总账

同一个坑踩第二遍的时候,你以为自己在进步,其实只是在重复。
这一页把 23 个真坑 按「死法」分类存成账本 —— 每一条都带现象、根因、对策、预防四段。

项目锚点 · 全部来自一次全盘代码盘点

这一页的每一条都不是「网上看到的技术要点」,是 2026-10-02 用 AI 扫本地 100+ 个子目录的全部代码之后,对着grep 结果和文件实测逐条核对出来的。包括那些让我一度误判自己技术栈的坑 —— 比如我以为有 11 个项目在 tRPC、以为主栈是 MySQL+Drizzle,实测一跑:tRPC 只有 2 个真项目,全盘零 MySQL。

坑库的存在意义:把「我记得有个坑」变成「我知道第 47 号坑长这样」。延伸:基础 19 · 读懂 AI 代码 讲怎么验收 AI 给你的东西,这一页是它的一次完整实战。

01

为什么「踩坑记录」比「经验总结」值钱

经验总结是事后美化的:怎么做成的、有啥心得。踩坑记录是事前置的:下次遇到长这样,直接照着做。

对比经验总结(我以前的做法)踩坑记录(现在)
触发时机项目做完了才写,一半靠回忆当场记,四段齐全
内容粒度「要注意并发问题」「SQLite WAL 下两条写SQL 交叉执行会 BUSY,对策是改事务边界」
能不能复用换个项目就得重新悟复制粘贴,改两行
客户能不能看懂看得出你想得多,看不出你能交付看得出你真干过
面试官买不买账半买半信能追问细节,一问就露馅 vs 一问就答得出
这一页我可以拿给客户看,因为它主动写了自己判断错过、债还欠着。全是好话的知识库没人信;有一页是硬的,整站的可信度才立得住。
02

五个坑区总览:人是怎么被坑死的

按「死法」分类,比按技术栈分类有用 —— 同一个坑区里,现象长得几乎一样,根因却差很远。

坑区典型死法根因模式是否已解决
认知偏差以为自己技术栈是什么,实测不是凭印象写文档,没对过代码✅ 已用代码盘点纠正
认知偏差接受了一个错的「行业惯例」网上通用答案 ≠ 你的场景⏸ 持续补充中
部署与进程服务起不来、端口被占、重启雪崩孤儿进程脱离监管✅ 有标准处置流程
部署与进程中文乱码、证书过期打不开编码没统一 / 证书没续期✅ 有巡检
数据整库读不出来、97% 字段是空的JSON blob 塞行内 + 采集没做⚠️ 部分(债还在)
生产变更改生产系统改出事故没备份、没预览、没只读诊断✅ 制度化了(红线)
AI 协作AI 生成的图结构错、代码没测试没验收标准就采信✅ 四步验收法
AI 协作派出去的 agent 把文件写错目录没给绝对路径 + 没声明目标目录✅ 已有强制约束
03

坑区一 · 认知偏差:你以为的技术栈,和代码里的不一样

这一类最阴,因为它不报错,只是让你在错误的前提上继续决策。

编号现象我当时的判断实测真相对策 / 预防
01「我做了 11 个项目用 tRPC」以为 tRPC 是主力真实只有 2 个(delimao-system、shower-order-p3),其余是 grep 字符串误命中计数必须限定文件类型(ts/tsx)并人工看一眼 package.json
02「主栈是 MySQL + Drizzle」写进了个人简介全盘零 MySQL / 零 PostgreSQL,只有 SQLite 家族 + Drizzle文档栈和实测栈必须分开记,每年代码盘点对冲一次
03「Express 用了 36 个项目」觉得自己很全栈命中 85 个文件,真项目 13 个命中数 ≠ 项目数,要按仓库去重
04「我做过 PostgreSQL 迁移」简历里当亮点只有 schema.ts 末尾的迁移预案注释,一行代码没迁预案和现状要写清楚,承认是预案比含糊过去值钱
05「我有 7 个系统在跑」口头盘点文件实测后只有少数几个有完整链路,其余是脚本集合系统清单从目录结构读,不从记忆读
这一区的总对策就一句话:任何写进「我擅长什么」的结论,必须有 grep 结果或文件内容兜底。尤其是让 AI 帮你盘代码时,AI 也会顺着你的错误前提往下推 —— 它会帮你把「11 个 tRPC」编得更像真的。
04

坑区二 · 部署与进程:服务起来了,然后自己塌了

编号现象(线上长什么样)根因对策预防
06PM2 里几十个 God Daemon,内存吃光,应用全部 PPID=1(孤儿)早期反复 pm2 start 且没 --save,重启后进程树错乱先 kill 掉重复 daemon,再 pm2 resurrect 从 dump 恢复启动时必带 --save;改配置前先看 pm2 list
07端口 address already in use,服务无限崩溃重启孤儿进程仍占着端口,新进程抢不到先按 PID 查是哪个进程占端口,杀掉再起(不要再 try 重启)部署脚本启动前先做端口占用探测
08站能打开但 https 000 / 301 → 死链宝塔签发的 Let's Encrypt 证书过期,nginx SSL 握手失败宝塔面板续签,或 certbot renew 后 nginx -t 再 reload证书到期前 7 天巡检一次
09中文文件名/中文内容乱码Windows 下 shell 传中文路径编码不一致文件名一律 ASCII;需要中文内容时走文件写入工具不走 shell 传参部署文件命名规则:全 ASCII
10子站 SPA 全站打不开、爬虫不收录证书过期连锁 + 纯 JS 渲染,服务端无正文证书修复 + 预渲染静态正文块见坑 15
11传了 14 个文件上服务器,线上还是旧版只传了 html 没传 css,浏览器缓存旧样式传完立刻 curl 量字节数对比;css 版本化或加 query部署后必跑 curl 校验,见坑 20
05

坑区三 · 数据:系统能跑,数据不能信

编号现象根因对策预防
12整库读不出来,所有查询报空collections 表是单行 JSON blob,一个字段写坏整行 JSON 解析失败,库没坏但数据全丢可读性拆行 + 关键字段独立成列;导入前先做 JSON 合法性校验热点数据不许塞 JSON blob,这是设计红线
13统计出来「型号匹配 96.6%、客户匹配 0%」分母不一致:型号有值,客户 ID 压根没关联上三个口径分开统计:有单 / 有字段 / 有价格覆盖率永远报「分子/分母」,不报裸百分比
14400 单里 97% 的 spec 是 null 或「否」门店下单时尺寸靠口头传,没进系统先做采集(让录入必填关键字段),再谈算法见坑 13 的配套:数据不够就报「算不了」
15官网 84 个 URL 给爬虫只返回 3120 字节空壳React SPA 纯客户端渲染,服务端 HTML 里没正文预渲染静态块(#root 外持久 h1 + meta + OG + JSON-LD)robots.txt 早就配对了,根因不在 SEO 配置——差点白白改错地方
16玻璃图纸导出中文渲染成方块服务器无中文字体,或渲染引擎字体路径没指定服务端装字体 + 渲染时显式指定 font-family导出功能上线前用中文字符串跑一遍
17报价算出一个「看起来很精确」的错价空字段被默认值填平了:没客户 ID 就按「平均客户」算校验函数三态:算得出 / 算不出要补数据 / 数据本身错「算不了」是合法输出,不许猜
坑 17 是这一区里最该记住的一条。AI 天生爱补全,你给它一个缺口,它会给你一个填平的数字,而且看起来很合理。给客户算错价的代价,比算不出来大十倍。
06

坑区四 · 生产变更:改之前先看,不看就改

编号现象根因对策预防(已制度化)
18「我先改一下看看」→ 生产库被改坏,回滚都难没有备份、没有预览、直接上手备份 → 精确替换 → 预览 → 确认 → 生效生产变更先只读是红线第三条
19部署技能里「只传变动文件」跳过 css,导致样式没更新缓存判定靠文件时间戳,跨机器不同步变动文件 + 依赖文件一起传;传输后核对字节数部署 skill 里固化「传完必校验」
20传完 14 个文件,不确定线上是不是新版scp 返回成功 ≠ 内容一致curl -o /dev/null -w "%{http_code}:%{size_download}" 逐个量每次部署后必跑,见 模块 01 · 服务器托管
三条红线(写进每一篇知识库页面尾部的贯穿红线)
  1. 数据说真话:覆盖率就报覆盖率,不拿 3 个样本说事;缺数据报「算不了」
  2. 真实,不用 AI 冒充:真实客户/门店/产品物料禁用 AI 生成假场景图
  3. 生产变更先只读:改生产系统前先备份、先预览,不确认不改动
07

坑区五 · 和 AI 协作:AI 会顺着错的前提,编得更像真的

编号现象根因对策预防
21派 4 个 agent 写文档,全部写进了错误的工作区prompt 里没给绝对路径,agent 用默认工作目录prompt 必写目标目录绝对路径 + 显式声明「写入 X」派发清单里,「写到哪个目录」和「写什么」同等权重
22新页面出现两个 class="on",导航高亮错乱agent 复制基准页时把兄弟页的选中态一起抄了交付前 grep class="on" 计数,必须恰好 1写进验收脚本,见 基础 19
23顺手就能改的 skill / lock 工具调用失败,卡住整个流程工具在当前环境不可用,没降级方案降级:把方法写进工作记忆,用文件持久化代替任何依赖外部工具的动作,先想好「工具废了怎么办」

坑 21 让我掉了一次大坑:4 篇文档写到了别的目录,最后靠 cp 合并才救回来。这次之后,我给 agent 的每条 prompt 里,「目标绝对路径」是强制项,不是建议项。

08

坑库怎么用:新增一个坑的四个字段

一条坑只有写全这四段,下次才救得了你。缺一段,就退化成「我记得有件事」。

标准坑条目模板
字段要写什么反面例子
现象线上当时长什么样,越具体越好(报什么错、字节多少、几个进程)「并发有问题」
根因落到机制层:为什么会发生,不是「因为没注意」「因为我不小心」
对策当时怎么救的,可执行步骤「重新部署一下」
预防下次产出前自动带上的动作(写进 skill / 红线 / 校验脚本)「下次注意点」

完整可复制版本在 交付物模板库 · 坑库条目模板。

09

还没踩完的坑(诚实节)

一个坑库只写「已解决」是广告,写「还没解决」才是账本。

坑状态为什么还没修什么时候会修
JSON blob 崩库(坑 12)⚠️ 设计债拆表要重跑历史数据 + 改写入路径,得腾一个完整窗口等下一个改库窗口,或接手新项目时顺带重构
MySQL / PostgreSQL(坑 02)⏸ 只写了预案SQLite 单机扛得住当前数据量,换库是纯成本出现「多台机器要读写同一库」时才换
测试几乎为零(坑 26 后续)⏸ 已知短板一个人的项目优先级永远是交付,测试排不进节奏按「先补出过事的地方」推进,见 技术短板 · 测试从 0 到 1
图表库为零(坑 28 后续)⏸ 已知短板现阶段用服务端出静态图够用,引前端图表库反而是负担要做「客户能自己筛选」的看板时再补
诚实节的意义不在于自曝,在于证明你有账本。有账本的人会记,会记的人交付才稳。
10

面试怎么答(这一页的问法)

面试官:「你说你懂部署,线上出过什么事故?」
「最多的一次是 PM2 雪崩:几十个重复 daemon 吃光内存,应用全部变成孤儿进程,PPID=1 脱离监管,还占着端口导致无限重启循环。我当时的处置顺序是先杀重复 daemon 再 resurrect,不是无脑重启 —— 无脑重启会一直卡在同一个端口上。现在我们的规则是启动必带 --save,改配置前先看 pm2 list。」
「你怎么保证交付到线上的东西是对的?」
「分三层。第一层,部署完立刻 curl 量 HTTP 码和字节数,scp 返回成功不等于内容一致;第二层,页面级自检,比如每个 HTML 里 class="on" 必须恰好一个,多一个就说明导航错了;第三层,内容级自检,禁用词和真实数字对不对。这三层都写在部署流程里,不靠记性。」
「你的项目数据质量怎么样?」
「不好,而且是诚实的不好。400 单里 97% 没有尺寸字段,全量 33,176 单/387 经销商/2,799 型号里,型号匹配 96.6%、厚度 95.2%,但尺寸覆盖只有 29%、客户匹配 0%。所以报价引擎我建议现在别上,先做数据治理。我的产品观是:算不了是合法输出,拿默认值填平算出来的错价才是事故。」
「AI 生成的代码/图,你怎么验收?」
「四步验收法:一查来源(这个文件是不是我指定的目标),二看结构(数量对不对,比如栅格类门的竖框数要等于门扇数),三跑最小样例(拿一条真实数据走通全链路),四留痕(变更前后各存一份)。危险信号有十条,最常见的两个:路径不是我给的、以及它顺手把兄弟文件的选中态也改了。」
「你用 AI 做项目,最大的失控点在哪?」
「目标目录。我派 agent 写文档时没写绝对路径,它写进了默认工作区,四篇全废,最后靠 cp 合并救回来。现在的硬规矩:给 agent 的 prompt 里,目标目录绝对路径和任务内容同等权重。第二个失控点是它没有全局观,会照抄基准页的状态,所以我要求交付前 grep 自查关键字唯一性。」
接着看

← 基础 19 · 读懂 AI 代码 · 交付物模板库 · 坑库条目模板 · 基础 16 深入 · 数据库存东西