依赖漏洞检查:发版前5分钟自救清单

18 min read

你以为发版前最危险的是最后一行刚改完的代码,其实很多时候,真正埋雷的是你几个月没看过的依赖。
凌晨一点十七分,功能测过了,支付通了,截图也做好了,连 Product Hunt(国外的产品发布平台)文案都改了两遍。
就差点下“发布”那个按钮时,最容易翻车的,反而是那堆你默认“应该没事”的包。

这事烦就烦在,它不像报错那样当场吼你。依赖漏洞更像装修时埋在墙里的旧电线,平时安安静静,真出事了,火也不是从你刚装好的灯开始烧的。

前阵子我帮老大查一份 AI 工具链资料,原本只想核一下几个开源项目的许可证,顺手翻到依赖公告,结果发现其中一个演示项目卡着一个已经公开很久的漏洞版本。那一刻的感觉很怪:功能明明能跑,demo 也正常,但是你就是知道,这东西一旦真拿去上线,问题不是“会不会”,而是“什么时候”。

我现在越来越觉得,独立开发者发版前最该补的,不是再多加一个小功能,而是5 分钟的依赖漏洞体检。不是为了追求“绝对安全”这种一听就很贵的状态,而是为了做一个很现实的判断:这版能不能发,哪些库必须今天处理,哪些先留账,但别装作没看见。


独立开发者为什么也要做依赖漏洞检查?

因为攻击面不看你团队人数。你只有一个人,只要产品上线、装了第三方包、能接收用户输入,就已经在赌依赖质量了。

独立开发依赖风险链路图 很多人默认“我这就是个小工具,谁会盯上我”。但是现实里,很多漏洞根本不是“有人专门攻击你”,而是扫描器、公开 PoC、自动化脚本一路扫过去,扫到谁算谁。你不需要有一万用户,才配踩这种坑。

更麻烦的是,独立开发者的发版节奏通常很快:今天修个 bug,明天加个登录,后天接个支付。功能推进很有成就感,依赖检查却没有即时反馈,所以特别容易被拖到“下次再说”。交过几次学费之后你会发现,下次往往就是事故之后。


OSV.dev 到底适合拿来干什么?

适合做发版前的第一轮体检:快速查出你项目依赖里有没有已知漏洞,以及这些漏洞影响哪些版本、有没有修复版本可升。

OSV.dev 发版前体检流程 OSV.dev 是 Google 维护的开源漏洞数据库与查询服务,官方地址:https://osv.dev
它的好处不是“功能特别花”,而是足够直接:你给它包名、版本,或者直接给依赖清单,它就告诉你有没有已知问题、受影响范围和修复建议。

如果你现在只想记一句话,可以记这个:

OSV.dev 不是替你做最终决策的裁判,它更像发版前的体检单。 体检单告诉你哪项异常,至于今天能不能跑步、要不要立刻去医院,还得结合症状、部位和风险自己判断。

这个区别很重要。很多人卡在两个极端里:
一种是“查到漏洞就吓得不敢发”;另一种是“反正总会有漏洞,干脆不查”。
这两个都不对。


发版前到底该查什么,不该查什么?

先查“已安装依赖的已知漏洞”,不要一上来就把安全工程做成毕业论文。

发版前三步轻量安全检查流程 对独立开发者来说,发版前最值钱的是一套轻量流程,不是全家桶。你要的不是把 SBOM、SCA、镜像扫描、容器基线、供应链签名一次性全上,而是先把最常见、最容易落地、最可能影响发版的一步固定下来。

我建议先把目标压到这 3 件事:

  1. 查当前项目依赖里有没有已知漏洞
  2. 看清受影响版本和修复版本
  3. 做一次上线决策:立刻修 / 降级风险后发 / 先记录后补

先把这三步跑顺,比装十个安全工具更有用。说白了,你要的是发版前的判断力,不是安全术语收藏夹。


一套 5 分钟能跑完的轻量工具流

我推荐的组合很克制:

轻量发布前漏洞检查流程

  • OSV.dev 官方网站:https://osv.dev
  • OSV-Scanner(官方扫描工具):https://github.com/google/osv-scanner
  • 你项目自身的依赖文件:比如 package-lock.jsonpnpm-lock.yamlpoetry.lockrequirements.txtgo.mod
  • 一张你自己的发布决策表

如果你是 Node.js、Python、Go 这类常见栈,这套已经够用了。
它的核心思路不是“扫得多深”,而是“每次发版前都愿意做”。

💡 轻量原则:先把漏洞检查做成发布动作的一部分,再考虑自动化。手动能坚持,才值得接进 CI。

有一阵子 Discord 里有人问我:“独立开发做安全,是不是一上来就得配很完整?”我当时第一反应就是,不要。不是因为完整方案不重要,而是大多数人死在第一步太重,做了两次就不做了。

安全流程这事,能长期重复,比第一次做得漂亮更重要。你今天愿意花 5 分钟扫一次,通常比你周末花 3 小时搭一套没人再开的系统更有用。


第一步:先用 OSV.dev 网页版看一眼

如果你还没把流程固化,先别急着装工具。网页版适合快速建立判断感。

OSV.dev 漏洞初筛流程与误区对照 你可以直接在 OSV.dev 搜索包名,或者输入生态和版本信息。重点看 3 个字段:

  • 漏洞影响的版本范围
  • 修复版本在哪
  • 漏洞描述里提到的触发条件

这里有个常见误区:看到 CVE 编号或者高危字样就直接慌。
先别急。很多漏洞虽然存在,但只在非常特定的调用方式、部署环境或功能入口下才会被利用。你真正要问的是:我这个项目有没有走到那条路径?

举个很典型的判断方式:

你看到的信息先别急着下结论正确动作
某依赖有高危漏洞不等于你的项目一定中招先看你是否使用相关功能
有修复版本不等于能直接无脑升级先看是否会引入破坏性变更
没有修复版本不等于必须停发看是否可通过配置、禁用入口或替换库规避
漏洞描述很抽象不等于风险小去看官方公告和受影响条件

这一步的目标不是解决问题,而是先把“有没有坑”看清楚。


第二步:用 OSV-Scanner 扫你的锁文件

网页版适合单个包判断,真正发版前更省事的方式,是直接扫项目依赖文件。

OSV-Scanner 官方项目地址:
https://github.com/google/osv-scanner

如果你用的是锁文件驱动的项目,这一步很顺手,因为它会按你当前安装的实际版本来查,而不是只看一个模糊的依赖范围。

Mac / Linux

先安装工具。常见方式之一是用 Homebrew:

bashbrew install osv-scanner

进入项目目录后,直接扫描当前目录:

bashosv-scanner scan source -r .

Windows

如果你用 Scoop,可以先试:

bashscoop install osv-scanner

然后在项目目录里运行:

bashosv-scanner scan source -r .

如果你的环境没有现成包管理器,也可以去官方 GitHub Releases 页面下载二进制文件。下载完后,把可执行文件放到系统 PATH,或者在当前目录直接运行。

做对了会看到什么?

你应该会看到类似这几类信息:

  • 发现了哪些依赖漏洞
  • 每个漏洞对应的生态和包名
  • 受影响版本范围
  • 修复版本或参考链接

如果结果是空的,不代表你永远安全,只代表当前这次扫描没发现已知漏洞。这个区别得拎清。安全这事最怕一句“没报错应该就没事”。


扫出来漏洞后,哪些必须立刻修?

最简单的判断,不看“高危”两个字,先看这 5 个维度。

下面这张表,就是我建议你直接塞进发布流程里的决策框架。

维度你要问的问题满足时倾向
严重性漏洞本身影响大吗?分数高、影响广 → 更偏向立刻修
受影响范围你当前版本是否落在受影响区间?在区间内 → 继续评估
是否可利用你的项目是否真的会走到触发路径?用户可直接触发 → 更偏向立刻修
修复路径有没有明确可升版本或替代方案?能安全升级 → 优先修
上线决策现在发版是否会放大风险?新版会扩大暴露面 → 暂缓发版

你会发现,这套表故意没有让“严重性”一票否决。因为现实里很多问题并不是“高危 = 立刻停工”,而是“高危 + 可被你当前场景触发 + 暴露在公网”,这才危险。

说实话,这里面也没有一种永远正确的尺子。有些漏洞描述写得很吓人,但你项目根本没走到那条路径;也有些看起来评级不算顶格,结果正好卡在公开接口上。安全判断最怕的不是不懂,而是把“分数”误当成“结论”。


什么情况属于“马上修,不要拖”?

直接说结论:只要漏洞可被外部输入触发、位于公网入口、且已有修复版本,通常就别带着它发版。

比如这些场景:

  1. 依赖在你的登录、上传、富文本、模板渲染、文件解析这些入口上
  2. 这个功能已经对外开放,用户能直接打到
  3. 官方已经给出修复版本,你升级成本可控
  4. 新版本发布会扩大使用量或暴露面

这类情况就别玩“先上线再说”。因为你不是在赌漏洞会不会存在,而是在赌别人会不会正好撞上。

有时候最坑的不是漏洞本身,而是你明明有机会在发版前 5 分钟发现它,结果因为赶进度跳过去了。这个锅,事后复盘起来会特别难受。


什么情况可以先记录,再继续发版?

也有。不是所有漏洞都值得为它停版。

下面这些情况,通常可以考虑先记录、加备注、排进近期修复:

  • 受影响的是开发依赖,不参与线上运行
  • 触发条件很苛刻,而你的项目根本没用到那段功能
  • 当前没有稳定修复版本,强升反而会引发更大兼容风险
  • 你能通过配置、关闭入口、限制权限,暂时把暴露面压住
  • 这次发版是紧急修复,而且和该漏洞无关

但注意,“先记录”不等于“算了”。
它应该长这样:有漏洞编号、有影响范围、有暂缓理由、有预计处理时间。
不然所谓的“记录”,最后通常只是遗忘。


这一步最容易犯的错是什么?

把“查到漏洞”和“理解漏洞”当成一回事。

扫描工具很擅长报出问题,不擅长替你理解上下文。
你看到一串包名、一段版本区间、一条修复建议,很容易产生两种错觉:

第一种错觉是“既然工具报了,那我肯定很危险”。
第二种错觉是“这玩意我看不懂,先忽略”。

实际上,真正值钱的是中间那一步:把漏洞放回你的业务路径里看。它到底在不在用户请求链路上?是在服务端、前端、构建期,还是本地开发环境?有没有认证门槛?有没有替代入口?这些决定了它是今天就得修,还是先挂账。

这一步有点像开车时看仪表盘。警示灯亮了,当然不能装没看见;但也不是所有灯一亮就必须当场熄火。你得知道哪盏灯是“立刻靠边”,哪盏灯是“今天去修理厂”。


可直接复制的发版前漏洞检查模板

下面这份模板,你可以直接放进 Notion、飞书、GitHub PR(代码提交审核)模板,或者发版清单里。

text【依赖漏洞检查 - 发版前清单】

1. 扫描时间:
2. 项目版本:
3. 扫描工具:
   - OSV.dev 网页版 / OSV-Scanner
4. 是否发现漏洞:
   - 无 / 有

若“有”,逐条记录:

- 漏洞编号:
- 受影响依赖:
- 当前版本:
- 受影响版本范围:
- 修复版本:
- 严重性:
- 是否在线上运行:
- 是否暴露给外部输入:
- 我们是否使用到相关功能路径:
- 是否已有公开利用方式或官方强提醒:
- 修复成本:
  - 低 / 中 / 高
- 当前决策:
  - 立刻修复后再发
  - 加缓解措施后发版
  - 记录风险,按计划补修
- 决策理由:
- 负责人:
- 计划处理时间:

这份模板最值钱的地方,不是格式整齐,而是它强迫你把“感觉危险”变成“有依据的上线判断”。


能不能把它压缩成真正的 5 分钟流程?

能。给你一个够用版:

  1. 打开项目目录,跑一次 OSV-Scanner
  2. 如果没结果,记录“本次未发现已知漏洞”,继续发版
  3. 如果有结果,先筛线上依赖,忽略纯开发依赖
  4. 对剩下的每条漏洞,回答两个问题:
    • 它会不会被当前产品路径触发?
    • 有没有低风险修复路径?
  5. 把结论写进发布记录:立刻修 / 加缓解后发 / 记账后发

这段话我单独写得自包含一点,方便你以后抄进自己的流程文档里:

独立开发者发版前做依赖漏洞检查,最省事的方法是用 OSV-Scanner 扫当前项目的锁文件,再用 OSV.dev 核对受影响版本、触发条件和修复版本。真正的关键不是“有没有漏洞”四个字,而是把漏洞分成三类:会影响线上入口且可修的,先修再发;影响有限但暂时难修的,写明理由后继续发;只在开发环境或未使用路径出现的,记录并排期处理。这样你用几分钟就能把“安全焦虑”变成可执行的发布决策。


要不要接进 CI,变成自动拦截?

要,但别第一天就把自己卡死。

比较稳的做法是分两阶段:

阶段一:先人工执行

先把上面的 5 分钟流程跑顺。你会知道自己项目里最常见的几类告警是什么,也会慢慢形成判断标准。

阶段二:再接进 CI

等你确认这套规则不会误伤正常发版,再把扫描接进 GitHub Actions、GitLab CI 这类流程里。让它先做“提醒”,再逐步升级成“阻断”。

很多人一开始就想全自动:高危就 fail、发现漏洞就不让发。听起来很硬核,最后往往是大家学会了绕过规则。那就尴尬了。

⚠️ 别一步到位上阻断:如果你的项目依赖多、历史包袱重,先让 CI 报告问题,不要直接卡住所有发布。不然你会先把自己逼成规则黑客。

我建议你今天就补上的最小动作

今天别研究太多安全框架。
就做三件事:

  1. 给当前项目跑一次 OSV-Scanner
  2. 把上面的模板存成你的发版清单
  3. 以后每次上线前,固定留 5 分钟做依赖体检

很多“功能明明没问题却上线翻车”的事故,问题根本不在功能。
它藏在你很久没碰、但一直跟着项目跑的那些依赖里。

你不需要先成为安全专家,才配做这一步。
你只需要先养成一个习惯:发版前,先看看墙里的电线。

如果你愿意,下一次准备上线时别急着点发布,先跑一遍扫描,然后问自己一句很具体的话:这次发现的漏洞,到底是在我的用户路径上,还是只是报告里的一行字?很多时候,真正拉开发版质量差距的,就是这 5 分钟。

FAQ

Q: OSV.dev 能替代所有安全扫描工具吗?
A: 不能。它更适合做已知依赖漏洞的快速检查。对独立开发者来说,先把这一步做稳定,收益已经很高。

Q: 扫描结果为空,是不是就绝对安全了?
A: 不是。它只表示当前没查到已知漏洞,不代表没有未知问题,也不代表你的配置和权限设计没风险。

Q: 查到漏洞但暂时升不了版本,怎么办?
A: 先判断是否在线上可触发,再看能否通过关闭入口、限制权限或替换依赖降低风险,同时把处理计划写进发版记录。