在软件测试这个行当里,有一件事我从入行第一天就被前辈反复提醒,到后来带团队,又被我反复讲给新人,那就是“探索性测试”。不是因为它学起来有多难,而是因为它实在太容易被误解。一提起探索性测试,很多人脑子里跳出来的画面是“打开一个网站随便点点,碰运气一样找 bug”;可真正在实践中跑过的人都知道,探索性测试的核心在于同步进行学习、设计、执行、分析这四个动作——系统在测试过程中教给你什么,你就顺势调整自己的测试策略,这可比照着脚本按图索骥高级得多,也复杂得多。
这篇文章适合所有想摆脱“用例机器人”状态的测试工程师,也适合常年在版本发布前抢时间的开发同学,以及想搞清团队测试盲区的测试管理者。下面我会从定位、实操流程、核心技巧、典型问题这四个维度,把探索性测试这件事完整拆开讲一遍,内容涵盖我自己在真实项目里踩过的坑,以及沉淀下来可以直接复用的做法。
1. 探索性测试的核心思路与定位
1.1 它和用例测试的本质区别
把功能测试的日常拆开来看,绝大多数测试团队的任务链条是“需求 → 用例 → 执行 → 回归”。用例测试的优点是足够规范化:相同环境、相同输入、相同步骤,就能得到相同结果,适合验证已知、守卫回归。但它也有一个与生俱来的盲区——只要产品不是打印在纸面上的流程图,用户真实的操作路径就一定会在某个时刻偏离预设脚本。
我举一个自己遇到过的例子。某个业务系统有用户资料编辑页,用例里写得清清楚楚:先填姓名、邮箱、上传头像,最后点保存。但我做探索的时候偏不照这个顺序来:我先生成头像,又马上把头像删掉,再一口气填完剩余字段,最后点保存。结果是什么?前端把旧头像的缓存地址当成了新头像提交,接口直接返回 500,页面白屏。这个场景要是只跑脚本,测十次也触发不了,因为用例里根本没有“删头像后再保存”这个分支。
所以我对两者的定位是这样的:脚本测试的价值是“验证”,探索性测试的价值是“发现”。脚本能证明“用例定义的行为可以正常工作”,却证明不了“那些没被想到的行为一定不会出问题”。而探索性测试恰恰是带着疑问去挑战产品:这个模块有哪些状态组合?字段之间的操作顺序会不会互相影响?什么样的边界输入会让预期失效?
| 对比维度 | 脚本化测试 | 探索性测试 |
|---|---|---|
| 测试过程 | 预先定义步骤与预期,逐步执行 | 边操作、边设计、边修正预期 |
| 主要产物 | 测试用例、执行记录 | 会话记录、bug 线索、风险笔记 |
| 对环境变化的适应 | 脚本需要持续维护更新 | 随时根据当前系统状态调整 |
| 对人员能力要求 | 学习成本低,按部就班即可 | 需要业务理解和技术敏感度 |
| 擅长发现的缺陷 | 已有功能点的回归问题 | 未知组合、边界条件、异常路径 |
我始终认为,这两种测试不是替代关系,而是互补关系。自动化回归守住了已经确定的行为,探索性测试才有空间去处理“尚未被定义”的行为,尤其是那些需求文档压根没提到的状态和组合。
1.2 探索性测试不是“随便点点”
有一种流行误读,把探索性测试等同于无计划、无记录、无时限的自由测试,甚至和“猴子测试”混为一谈。实际上,随意探索和有目的的探索之间差别非常大。我衡量一次测试是不是真正的探索性测试,就看三个东西:有没有明确目标、有没有时间边界、有没有记录产出。
“明确目标”指一条具体的测试任务,也就是探索社区里常说的 charter。哪怕任务单只有一句话,比如“检查退款按钮在订单异常状态下的表现”,它也提供了方向感,让我清楚该从哪里切入、该关注哪些信息。没有目标的“随便看看”,本质上是低效的浏览,而不是测试。
“时间边界”是为了避免探索变成无底洞。没有时限的话,一个大模块能泡一整天,最后汇报的时候却说不出到底产出了什么。时间盒会逼迫我在有限时间内聚焦当前最重要的线索,而不是被某个无关紧要的小问题带走。
“记录产出”则让探索行为变得可回溯、可审计、可交接。探索时节奏很快,不记下来的话,刚刚走过的验证路径两小时后就想不起来了。至少要把关键步骤、观察现象和怀疑点记下来,配合截图或录屏,这样别人接手也能理解你在做什么。
我之前带过一个新人,他一开始听说探索性测试,就直接打开系统乱点,半小时后跑过来跟我说“不知道在测什么”。我给了他一张任务单,限他二十分钟,要求最后记录三个发现,他很快就找到了一个验证码时效设置不生效的 bug。这说明探索性测试不是“高人专用”,而是“方法支撑下的有意识测试行为”,方法对了,任何人都能上手。
2. 探索性测试的实操流程与会话设计
2.1 会话式测试:给探索设定边界
在实际落地的时候,我最推荐的方式是“基于会话的测试管理”,也就是测试圈常说的 SBTM。它把一次探索拆分成一个个结构清晰的会话,每个会话解决一个子目标,最后有明确产出。一次会话通常由三部分组成:任务单、时间盒、汇报结果。
时间盒我一般建议 45 到 90 分钟。如果是全新的系统,我习惯先做两三个短会话,每个控制在 25 到 30 分钟,用来做快速的地形侦察,而不是直接一次性投入两个小时做深度探索。短会话最直接的收益是避免在错误假设上浪费太久。我见过同事在“购物车优惠金额显示不正确”这个怀疑点上深挖了半个小时,最后发现是测试账号本身绑定了过期优惠券——这种损耗完全可以靠短时间盒尽早暴露出来。
会话的推进节奏也很关键:开场先花 3 到 5 分钟确认任务单和内部知识,接着进入执行阶段,用小步快跑的方式不断触发系统行为,观察反馈,发现可疑点就停下来做针对性验证;最后留 5 分钟整理记录,输出一个简短结论。整个循环下来,每个会话都有交付物,而非“测完了但它测了啥”的模糊状态。
我还习惯在每个会话开始时给自己三个问题:这个模块最重要的核心路径是什么?最容易出错的状态切换在哪里?如果我只测三分钟,应该优先覆盖什么?这三个问题非常适合用来快速建立探索方向,尤其在没有完整需求文档的敏捷团队里,它们比翻文档更高效。
2.2 一份好任务单的写法
探索性测试看起来自由,但任务单能把它变成一种可控的智力活动。一份合格的任务单通常包含三个要素:被测目标、前置条件、想要回答的问题。目标指明探测对象,前置条件说明数据、账号或系统状态,问题则决定探索的注意力方向。
我拿登录功能做个对比演示:
| 不合格的任务单 | 合格的任务单 |
|---|---|
| 测试登录功能 | 用测试账号在登录界面连续输入错误密码 5 次,再切换找回密码流程,关注锁定提示与找回邮件是否一致 |
| 验证订单页面 | 模拟下单中途断网并恢复,观察购物车、订单确认页、支付状态之间如何同步 |
区别很明显:后者有清晰的操作范围和对预期问题的定义,它让探索过程有抓手,而不是一上来就面对整个系统。有人可能会觉得任务单限制了自由发挥,但我的体会恰恰相反——如果把整个系统比作一座迷宫,任务单不是告诉你只能走哪条路,而是告诉你“我们今天先探明这一片区域”,这样反而能更从容地挖掘区域内部的结构性问题。
任务单还可以在过程中不断演化。探索时发现的新线索,如果很有意思,我会顺手把它记到草稿纸上的“后续任务列表”里,等当前任务单的时间结束后再开启一个新会话去跟进。这样既不会丢失灵感,也不会让当前会话变得臃肿混乱。
2.3 会话记录:让发现变成可复现的证据
探索性测试的产出质量,很大程度取决于记录的质量。我现在用的随手记录格式比较简单,一般是一张表,包含这几列:步骤序号、操作动作、观察结果、预期一致与否、线索备注。
| 步骤 | 操作 | 观察结果 | 与预期是否一致 | 备注 |
|---|---|---|---|---|
| 1 | 进入用户列表,筛选最近一个月 | 列表正常展示 20 条 | 是 | 无 |
| 2 | 点击排序“提交时间” | 数据顺序未变化 | 否 | 怀疑排序参数未生效 |
| 3 | 翻到第二页再切回全部筛选 | 第一页数据与历史记录重复 | 否 | 疑似分页 offset 问题 |
记录的目的不是写论文,而是提高复现和思考的效率,所以允许随意,只要自己或接手的人两小时后还能看懂就行。我还有个习惯:会用“事实栏”和“推断栏”两列分开记录。“事实栏”写确定观察到的现象,比如“接口返回 500”;“推断栏”写自己当下的猜测,比如“可能是头像缓存导致”。这样能让分析和事实不被情绪混在一起,后续验证时也不会把“我猜”和“我看到了”搞混。
如果是崩溃类或白屏类问题,我建议先录屏,再补截图。单纯截图经常抓不到瞬时状态,尤其前端偶发问题,录屏能保留完整的操作序列、响应时间和报错上下文。很多“复现不了”的缺陷,根源就在于没有保留操作过程的完整证据链。
3. 真正提升探索能力的关键技巧
3.1 三种高性价比的探索视角
探索性测试没有一个绝对正确的套路,但有些视角长期验证下来非常高效。我自己用得最多的是三种:用户视角、数据视角、状态视角。
用户视角就是把自己当作一个不太熟悉系统的真实用户,从产品入口开始,不按照预设用例路径,而是顺着页面提示和直觉去操作。这里要特别注意那些隐藏在 UI 里的引导文案、图标入口、键盘处理、加载状态,以及移动端的横竖屏切换、息屏唤醒、信号切换等场景。用户视角的价值在于,它能暴露出需求设计时没有考虑到的真实使用习惯,比如“我还没注册,为什么可以直接进邀请页?”这种反流程操作。
数据视角关注的是页面上的信息从哪里来、到哪里去。翻页、筛选、查询、导出、排序,每个动作背后都有数据流转,探索时我会关注同一个数据在不同页面之间是否保持一致。这类问题在业务系统里特别容易遇到,比如订单号在列表页显示的是“20240516 - 001”,点进详情页却又多了一截前缀,明显是接口拼接逻辑不一致导致的。
状态视角适合用在复杂业务流上,尤其是那些有明确状态机的东西:提现单有“待审核 → 审核中 → 打款中 → 已到账 → 失败”,订单有“待支付 → 已支付 → 已发货 → 已完成 → 已取消”。真实用户经常会在状态流转的临界点做出“非法操作”:审核刚通过的同时用户发起撤回,打款中的时候用户修改银行卡,这些并存动作就是状态视角想覆盖的地方,也是最容易出严重 bug 的位置。
3.2 边界状态是怎么被“逼”出来的
我经常看到测试新手把边界测试理解成“输入边界值比较麻烦而已”,其实更关键的边界藏在操作顺序、并发动作和环境变化里。把这个概念拉开之后,探索的深度会立刻不一样。
输入边界是最基础的一层:长度上限、边界值加减一、禁止字符、全角半角、超长内容、空字符串。但操作边界才是探索的灵魂。注册流程走一半突然退回上一页,上传文件完成后立刻取消,列表快速翻到最后一页再反向跨页,这些破坏既定顺序的动作,往往能触发开发完全没有预料到的逻辑分支。我在实际项目中用“先删后改、先退后进、先断后连”这三组动作,命中率非常高。
并发边界也值得专门去做。多开两个浏览器窗口,同一个账号在两个终端同时提交订单、同时修改资料,几乎每次都能在数据库层面发现锁冲突或状态覆盖问题。环境边界则更接近真实世界:弱网、断网、切换 Wi-Fi、存储空间满了再写入、低电量弹窗打断操作,这些干扰因素叠加到核心流程上,才是移动产品最容易翻车的地方。
探索边界的本质,不是想尽办法把系统搞崩,而是通过组合验证去发现系统设计中隐含的假设,比如“开发默认用户一定先把 A 做完再做 B”,或者“开发假设同一时刻只有一个终端在操作”。一旦这些假设不成立,缺陷就会现形。
3.3 用风险清单决定探索顺序
任何人都没有足够时间把所有功能都深挖一遍,所以探索的顺序必须由风险驱动。我通常会先看三个维度:高风险功能、高变更区域、高用户触达入口。
高风险功能包括支付、权限、数据删除、第三方接口同步,这些一旦出问题,影响往往是资金流失或合规事故。高变更区域是这个迭代里开发改动最密集的部分,代码行变动最多、逻辑重构过的模块、新引入依赖的功能,都很值得集中探索。高用户触达入口则是日活最高、用户最常走的路径,比如首页搜索、登录注册、列表筛选,这些路径即使逻辑简单,出错的影响面也大。
| 优先级 | 探索重点 | 理由 |
|---|---|---|
| P0 | 支付链路、权限控制、数据删除 | 一旦缺陷上线,损失不可接受 |
| P1 | 核心交易链路、接口同步、导出报表 | 用户接触频率高,出错体感明显 |
| P2 | 低频设置项、辅助工具、不太起眼的小入口 | 出错影响小,可以后置 |
我发现一个非常有效的输入信息是开发给出来的“变更地图”。在迭代开始时问一问开发:这轮改了哪些文件、哪些状态判断、哪些接口逻辑?哪怕没有拿到精确代码,只听到一句“这轮只改了账户状态的判断逻辑”,探索重点就应该立刻放在“从旧状态到新状态”的路径上。这比拿到几十页用例文档再去翻重点高效得多。
4. 实战中常见的问题与解决思路
4.1 “你测了什么”的汇报难题
探索性测试在团队里经常面临一个灵魂拷问:“你测了什么?怎么证明你测过了?”这类质疑本质上来自产出不透明。传统用例测试有完整记录,而探索性测试如果只凭口头描述,确实难以让评审者放心。
我的解决办法是让每个会话都留下结构化痕迹。汇报时分三块来讲:覆盖范围、发现结果、风险提示。覆盖范围列清楚这次探索覆盖了哪几个功能模块、用了什么数据、走了哪些状态节点;发现结果按严重级别排序,每个 bug 给出触发路径和录屏;风险提示则说明当前还有哪块没有覆盖到、操作里有哪些不确定点,需要进一步验证。
哪怕一次探索只发现一两个问题,也要把它的质量讲清楚:这个问题的触发概率有多高、用户是不是容易遇到、影响面是多大。这套汇报方法帮我在团队里建立起了“探索不是摸鱼”的信任感,也让测试经理能更准确地判断接下来该投入多少资源。
4.2 探索时间被压缩时怎么办
迭代排期永远比想象中的紧,很多测试团队在版本发布前只能挤出一点时间。我在这种条件下会果断把探索切成碎片化的短会话:15 分钟一个,只选一个核心业务动词,比如“取消订单”或“修改配送地址”,把它相关的状态组合全部尝试一遍。短会话的核心不是方法多强大,而是人员带着清晰的思路进入,哪怕只有十分钟,也能比对着用例跑读更有效地发现问题。
还有一个实用做法是把探索技巧嵌进冒烟测试里。每次冒烟测试时,不只验证“流程能走通”,还要顺手做几组非法操作、极端输入、反序点击。这等于把探索变成了日常测试的一部分,而不需要额外申请大段时间。它不增加多少工作量,却能显著提高冒烟测试的含金量。
4.3 多人共同探索时如何避免重复
团队里有多个人同时做探索时,最怕的就是重复劳动。我的处理方式是维护一份共享的“覆盖网格”,横轴是功能模块,纵轴是测试日期和会话编号,谁测过哪个区域、发现了什么问题,都在表里留痕。每轮探索前先看一眼这张表,就能避免自己钻进别人已经扫过的迷宫。
结对探索也非常好用。一个人负责操作和记录,另一个人负责观察和质疑,两个人的思维路径往往能互补,操作的人容易陷进自己的假设,旁观者却能及时打断说“等一下,你刚点的那个按钮其实不在当前页面层级上”。
如果探索过程中发现了一条可能是重要缺陷的线索,我会立刻在现场召集身边同事做一个“视角切换”的快速复验。一个人继续按原路径操作,另一个尝试用不同的数据或状态逼近同一个问题。这样既能确认问题的稳定性,也往往能顺带找到更简单的复现步骤。
4.4 探索性测试与自动化测试的配合
探索性测试和自动化测试不是对头,而是上下游关系。自动化的职责是减少重复劳动,守住回归;探索的职责是发现未知问题,然后把新发现的问题反哺给自动化。
我在项目里常跑的闭环是:探索发现一个严重 bug → 复现并定位原因 → 修复后,把最关键的复现路径固化成自动化用例,加入回归集。这样每轮新版本跑自动化,就相当于有一个“哨兵”在站岗,防止同一个坑被反复踩。自动化把团队成员从重复执行中解放出来,大家才有时间去做更有创造性的探索。
用个生活化的类比:自动化是常驻的哨兵,探索是巡逻的侦察兵。哨兵能挡下已经见过的敌人,侦察兵则负责发现新的风险。两者叠加,才能形成既有防守又有出击的测试体系。
我在实际项目里养成了一个习惯,每次开始探索会话前,先花两分钟把系统里已经存在的功能入口画成一张最简地图,哪怕只是草稿纸角落里的几个方块。这张图不是给任何人看的,而是用来提醒自己此刻探索到哪个位置、下一步该往哪个相邻区域走。坚持几个月下来,你会明显感觉到自己的测试思维从“一个功能一个功能”的散点式,慢慢变成了“一条链路一条链路”的整体式观察,这种思维变化才是探索性测试给人带来的最大成长。