给项目选验证码,我调研了一个周末
事情是这样的——我有个 side project 需要加验证码。一开始的想法很简单:找个滑块方案,引入,完事。
然后我就打开了 GitHub。
三个小时之后,我发现自己陷进去了。字符验证码、滑块、旋转、点选、PoW 工作量证明、对抗 AI Agent……一个我以为半天能搞定的活,变成了整个周末的深坑。不过踩完回头看,验证码这个领域确实比大多数人以为的要有意思。
所以这篇就来聊聊我这一个周末到底看了些什么。
CAPTCHA 的全称巨长——“Completely Automated Public Turing test to tell Computers and Humans Apart”。说人话就是:用机器出的题来分辨答题的是人还是机器。
这玩意从 2000 年左右到现在,大概经历了三个阶段,每个阶段背后都是攻防双方在较劲。
第一波:扭曲字符。 把文字拧成麻花、加干扰线、加噪点。逻辑很朴素——人眼能认出来,当时的光学字符识别(OCR)认不出来。reCAPTCHA v1 是这代的代表,Google 甚至用它来数字化旧书(让你认的那些歪七扭八的单词,其实是从扫描版旧书里抠出来的)。但现在这套基本废了——深度学习+OCR 的组合拳,扭曲字符已经拦不住谁了。
第二波:行为验证。 滑块、旋转、点选文字——不再考你"看到了什么",而是考你"怎么操作的"。鼠标怎么动的、拖动速度怎么变的、中间有没有停顿——这些行为特征比图像识别难伪造,因为机器模拟的轨迹往往太"完美"了。极验 Geetest 和 reCAPTCHA v2 大概 2015 年前后火起来,国内很多网站现在还在用这代方案。
第三波:PoW 工作量证明。 这代思路完全变了——不收集用户数据,不让你拖滑块,也不让你点红绿灯。用户访问页面的时候,浏览器后台默默算一个 SHA-256 哈希难题,算出来就自动通过。对真人毫无感觉,但对脚本攻击者来说,每个请求都要真金白银地烧 CPU。Cloudflare Turnstile、hCaptcha,还有后面会聊到的 Cap、mCaptcha,都是这个路子。
正在来的第四波:对抗 AI Agent。 这个是今年我觉得最值得关注的变化。如果攻击者用的不是 curl 脚本,而是一个能看懂网页截图、会操作鼠标、还能根据反馈调整策略的 LLM Agent——那前面说的行为分析还扛得住吗?
我按类型把开源方案分了三档,从传统字符类到行为验证类再到前沿 PoW 类。
如果只是想要个"简单能用"的验证码,这一档够用了。
easy-captcha(原 kaptcha 分支):Java 生态的老牌库,支持 GIF 动图、中文汉字、算术题等多种类型。Spring Boot 项目引个 starter 就能跑,适合不想折腾的快速集成。我之前有个内部管理后台用的就是它,配一下字体和干扰线参数,五分钟搞定。
@tuzhanai/captcha:Node.js 生态的轻量字符验证码生成库,支持难度分级。前端同学如果想在自己的 Express/Koa 项目里加验证码,这是个很直接的选择。
witlark/captcha:这个项目挺有意思——字符 + 算术 + 滑动三合一,Java 实现,代码量不大,结构清晰。如果你想了解验证码生成的基本原理,这个项目的源码很适合拿来读。别指望直接上生产,但作为学习材料很值得推荐。
这里是我投入时间最多的一档——如果你的项目有真实的用户体验追求,挑一个合适的方案挺重要的。
tianai-captcha 是 dromara 社区出品的,Java 生态里目前最完整的行为验证码项目,支持四种模式:滑块、旋转、滑动还原、文字点选。
流程不复杂:
前端 JS/TS SDK 渲染交互区域 → 收集轨迹、时间、鼠标事件
↓
后端 Spring Boot Starter 接收数据
↓
做三件事:位置校验、轨迹分析、时间窗口判定
↓
存储层可插拔(内存/Redis/自己实现)前端把用户在滑块上的操作数据打包发回来。后端拿到之后:
- 位置对不对——滑块到了正确位置没?旋转角度在容差范围内不?
- 轨迹像不像人——机器拖滑块一般是匀速直线,或者很规律的正弦曲线。真人的拖动一定有卡顿、有变速、有小幅抖动。后端会提取加速度方差、停顿点分布、路径平滑度这些特征,用规则引擎打分。
- 时间合不合理——0.1 秒拖完肯定不是人,10 秒才拖完也不太对。
轨迹分析是灵魂。我本地跑了它的 demo,滑块手感不错,文档也算齐。Java 项目想上行为验证码的话,tianai 是目前最值得认真评估的。
go-captcha 是 Go 生态的同类选手,点选、滑动、拖拽、旋转都支持。
它的点选模式有点意思:服务端生成底图,在上面标记几个"正确答案区域";前端渲染后用户依次点击;服务端比对坐标。核心校验逻辑是容差——人不可能精确点到一个像素,所以允许偏移。但有意思的是,这个偏移量本身也是校验信号:机器点击往往像素级精确(它直接拿到了答案坐标),人类的点击天然有偏差。
Go 技术栈的项目不用为了个验证码跑 Java sidecar,go-captcha 是个直接的选择。
anji-plus/captcha 之前叫 AJ-Captcha,国内开源行为验证码里算最早那批了。
核心流程和 tianai 差不多:前端收集滑动轨迹,后端分析+校验。但它有个差异化优势——自带后台管理界面:验证码配置、数据统计、黑白名单管理都有。这对运维来说是实打实的方便。
接入文档也丰富,Spring Boot、Vue、React、Uni-App 都有现成案例。想快速上线又需要管理后台的话,anji-plus 是个稳妥的选择。不过注意它默认依赖 Redis 存状态,不想要额外中间件的话得自己适配。
传统验证码再怎么做,都是在"出题考用户"。PoW 方案换了个思路:不考你,让你用算力自证清白。
Cap(tiagozip/cap):基于 SHA-256 工作量证明,体积只有 hCaptcha 的 1/250。原理很简单——服务端发一个 challenge,客户端算出满足难度条件的 nonce,算完自动通过。
几个我特别买账的点:
- 零追踪:不记录用户行为,不存 Cookie,不采浏览器指纹
- Apache 2.0:随便商用
- Docker 一行命令自托管:不用注册任何第三方服务
- 用户无感:SHA-256 在 Web Worker 里后台跑,1-3 秒搞定,用户啥也不用做
流程大概这样:
用户打开页面
↓
前端 JS 拿到 challenge
↓
Web Worker 后台算 nonce(大概 1-3 秒)
↓
结果跟表单一起提交
↓
服务端验证 nonce 难度够不够普通浏览器算一次 SHA-256 PoW 几乎没感觉,但脚本攻击者要海量计算——成本一下就上去了。
mCaptcha:也是 PoW,但用 Rust 写的,性能明显更强。架构上搭配 Redis 做 challenge 分发和结果缓存,高并发扛得住。后端是 Rust 的项目天然适配。
ALTCHA:PoW 家族里主打合规的那个。GDPR 合规、WCAG 2.2 AA 无障碍标准。面向欧洲用户或者甲方有无障碍合规硬性要求的场景,能省很多沟通成本。
Prosopo Procaptcha:定位是 reCAPTCHA/hCaptcha/Turnstile 的零数据收集替代品。它在搞"去中心化验证"——多个验证者共同裁决一个请求,而不是信任单一服务商的判断。这个方向还早,但思路挺野的。
opencaptcha:还太早期,关注一下就行,别往生产上放。
传统验证码的假想敌一直是"脚本"——curl、Selenium、OCR。行为验证码出来之后攻击门槛高了不少,但也没到攻不破的地步。
真正让人心里咯噔一下的,是 LLM Agent。
一个接入了视觉能力的 Agent——比如 Claude 的 computer use、OpenAI 的 Operator——能把网页截图看懂,找到滑块在哪,理解"请旋转图片到正确方向"是什么意思,然后生成带有人类特征的轨迹数据来模拟拖动。一次不过还能调整策略重试。
轨迹分析在 LLM Agent 面前开始失效了——因为 Agent 完全可以生成符合人类行为模式的轨迹。这不是我危言耸听,2025 年就已经有人用 GPT-4V 跑通了自动破解行为验证码的 PoC,成功率还在涨。
FCaptcha 是专门针对这个方向设计的。它不是靠一两个信号判断,而是40 多个行为信号一起上:
- 浏览器是不是无头模式
- 有没有 Puppeteer / Playwright / Selenium 的痕迹
- 鼠标键盘事件是不是来自真实硬件
- 页面渲染有没有被 CDP(Chrome DevTools Protocol)劫持过
- JS 执行环境有没有被篡改
这些东西单独拿出来都不新鲜——无头检测、CDP 检测早就有了。FCaptcha 的做法是把所有信号放一起打分,加权投票。你绕过了一个信号没事,后面还有 39 个等着。
思路其实很朴素:不赌单点,赌覆盖。当一个验证码从"做对一道题"变成"通过一整套安检",攻击的成本曲线就完全不一样了。
FCaptcha 现在还算早期,文档和案例比不上成熟方案。但它代表的方向我个人很看好。
2024 年 Google 干了一件事,当时讨论不多,但影响不小。
reCAPTCHA 的免费额度被砍了 99%:
- 以前:每月 100 万次
- 现在(reCAPTCHA-Lite):每月 1 万次
- 超出部分:每千次约 1 美元
- 标准版:每月 8 美元,可用到 10 万次
一个月 1 万次什么概念?一个日访问量两三百的小站,轻轻松松就超了。
这是 2023 年宣布、2024 年正式执行的策略调整,不是临时的。Google 的意思很清楚——验证码服务不再是免费公共品了。
对国内开发者还有个额外麻烦:reCAPTCHA 在国内得走 recaptcha.net 镜像,连接稳定性看运气。
Cloudflare Turnstile 倒是一直免费、不限量,但国内访问不稳定是硬伤——依赖 Cloudflare 全球网络,墙内用户加载失败是常事。主力用户在国内的话,别把它当核心方案。
总之,2026 年选验证码,别再想都不想就上 reCAPTCHA 了。
腾讯云天御:新用户有点试用额度,之后按量 ¥0.03-0.05/次。要实名或企业认证。
阿里云验证码 2.0:按量付费,¥0.05/次(量大阶梯价)。同样要实名/企业认证。
极验 Geetest:老牌了。个人开发者能申请免费版,但要审核。国内大厂用得不少,产品很成熟。
云服务在产品稳定性和 SDK 覆盖上确实比开源省心。但账单是实打实的——访问量大一点,一个月几百上千跑不掉。个人开发者不交企业资质还可能被卡。而且一旦绑定了某家,前后端都跟它耦合了,换起来麻烦。
个人项目和中小团队的话,自托管开源方案在成本和自主权上的优势很明显。
我自己的结论是:看场景来。
内部后台 / 低流量: easy-captcha 够了。简单图形验证就能拦住绝大多数无效请求,不值得花时间搞复杂的。
对外的 Web 应用,Java 栈: tianai-captcha 或者 anji-plus/captcha。前者代码和文档更现代,后者自带管理后台,各有各的好。
Go 栈: go-captcha,尤其是点选模式。
对隐私有要求或者面向海外用户: Cap 或者 ALTCHA。PoW 方案不碰用户数据,合规风险低,一个 Docker 就跑起来了。
不想让用户看到验证码: Turnstile(海外用户为主)或者 Cap(自己托管)。前者免费但国内不稳定,后者完全自己掌控。
需要同时防脚本和 AI Agent: FCaptcha 方向值得盯着。现在还不太适合跑核心业务,但多信号检测的思路很对。
折腾完这一圈,我最大的感觉是——验证码这种二十多年的老技术,被 AI 这么一逼,反而活泛起来了。以前选验证码基本就是"用 reCAPTCHA 还是极验",现在开源这边的选项多了不是一点半点,而且不再默认"用隐私换安全"。
挺好的。