ARTICLE DETAIL

资讯详情

深耕编程入门与网站建设的一线实战洞察。

从需求拆解到用例落地:功能测试用例设计全流程实践指南

从需求拆解到用例落地:功能测试用例设计全流程实践指南 1. 拿到需求别急着开写用例设计的第一步其实是读懂系统功能测试用例到底该怎么设计我发现很多刚入行的测试新人最喜欢干的一件事就是打开Excel照着需求文档的字段列表一个输入框一个输入框地写用例。输入用户名一条输入密码一条点击登录按钮一条……写了几十条下来看着挺充实一评审就被老测试几句话问住登录失败之后有提示吗连续输错五次会锁账号吗锁了之后什么时候解锁这些用例你写在哪了这其实就是典型的用例设计思路没建立起来的表现。测试用例不是需求文档的字段翻译器它是你对整个系统的一次模拟推演——你得在脑子里先把功能跑一遍再把跑法具象化成一条条用例。所以我不太喜欢直接用设计思路这个词来讲这件事我更愿意把它拆成四个环节读懂需求、拆解场景、组织表达、持续维护。这篇文章就沿着这条线把我这些年实际走下来的思路完整过一遍希望能给正在为用例写不好、评审总挨批发愁的朋友一点实在的参考。1.1 需求澄清阶段用例设计者应该坐的位置先说一个我自己的亲身体会用例设计真正开始的时间不是需求文档交到你手上那一刻而是产品经理开始讲需求的那一刻。我见过太多测试同事需求宣讲会上从头到尾不吭声等文档发下来才逐字逐句读。结果读到一半发现一堆模糊地带这里的列表排序规则是什么这个字段必填吗超时时间设多少——这些问题如果在会上问一分钟就能得到答案拖到写用例的时候再回头找产品往往就得等半天而且很容易出现需求变更了但你还在按旧逻辑写的情况。所以在需求澄清阶段我会强迫自己干三件事第一带着问题去听。需求文档没到手之前先跟产品经理要一页纸的功能概述哪怕是口头说的都行。我要搞清楚三个最基本的问题这个功能给谁用解决什么问题操作路径是什么这三个问题搞不清楚后面所有用例都是空中楼阁。第二现场把业务规则顶清楚。产品经理讲到任何一条规则时我都会追问它的边界情况。比如订单超过30分钟未支付自动取消我会立刻问那第29分59秒支付成功了呢第30分钟整呢自动取消的同时用户正在支付怎么办取消之后库存还恢复吗这些问题不是抬杠而是把规则从文字描述变成可执行的逻辑。第三把需求当代码一样做静态走查。我会在拿到需求文档之后对照历史功能列一张变更影响清单——这次改了什么、新增了什么、删除了什么、有没有动到之前的老逻辑。很多重大故障都出在我只是加了一个字段没想到牵动了旧逻辑这种地方。说个真实案例。我们之前做过一个后台的批量导入功能需求文档里写得很清楚支持Excel批量导入单次不超过1000条。我看完之后问了一句如果导入的文件里有50条数据格式正确、30条格式错误、20条重复系统会怎么处理产品说逐条校验错误的跳过正确的导入。我又问那错误和重复的记录要不要给用户反馈反馈在哪看要不要生成一个失败清单产品当场愣了一下说这个细节他还没想好。结果这个没想好的细节后来成了整个功能最复杂的模块——因为失败清单要展示具体行号、错误原因、并且允许用户下载修正。测试人员如果在需求阶段不问这一句等用例写完、开发做完了才发现返工成本就是十倍百倍。所以别觉得自己只是写用例的你要把自己当成第一个运行这套系统的人——你在纸上跑不通的逻辑开发写完大概率也跑不通。1.2 业务规则拆解从需求描述翻译成逻辑清单需求澄清做完接下来这一步非常关键也是很多测试同学跳过去的把需求文档里的自然语言逐条翻译成如果-那么的逻辑清单。为什么要干这件事因为自然语言是有歧义的。用户点击提交后系统将订单状态更新为待审核——这句话看起来没毛病但点击提交之前发生了什么表单校验不通过怎么办网络异常超时怎么办服务器返回500怎么办这些在自然语言里全是隐含逻辑你要做的就是把它们全部显式化。我常用的做法是画一张业务规则清单表每一行就是一条独立业务规则列包括编号、触发条件、系统动作、异常分支、备注。比如拿一个最简单的登录功能来说编号触发条件系统动作异常分支R01用户名和密码均正确登录成功跳转首页无R02用户名正确密码错误提示密码错误记录失败次数R03用户名不存在提示用户名不存在无R04连续失败5次锁定账号30分钟锁定期间即使密码正确也不放行R05锁定期满后首次登录解锁并允许登录重置失败计数这套规则清单整理完你会发现两件重要的事第一用例还没开始写你已经能看出产品逻辑的漏洞了比如R04和R05之间的竞态条件第29分59秒用户试了一次错的算不算锁定期内第二后面写用例的时候完全可以一条规则对应至少两条用例——一条走正常分支、一条走异常分支覆盖率和逻辑完备性一下子就上去了。这块我还有个心得规则清单要尽量落到可判定的程度。什么叫可判定比如密码错误这四个字你得搞清楚是前端先校验格式还是发到后端校验错误提示的文案是什么输入框要不要标红光标要不要定位回密码框这些虽然不是每条都要写进用例但它们是你的测试观察点——没有观察点的用例执行完你也分不清到底算通过还是算失败。2. 用例设计的工具箱不是每种方法都要硬套得知道在什么场景用哪把功能测试用例设计方法论市面上讲得很多等价类划分、边界值分析、场景法、判定表、因果图、正交实验、错误推测……书上都写过但我在实际项目里发现一个普遍问题很多测试同学把方法当成了模板拿到任何功能都从等价类开始套结果把最简单的东西做复杂了把最复杂的东西又做简单了。所以这一节我不打算按教科书的方式把每个方法讲一遍而是想聊聊我实际使用这些方法时的选型逻辑——什么场景下用什么方法最划算什么情况下可以大胆地把方法组合起来用。2.1 输入类功能等价类和边界值谁在先其实有讲究等价类划分和边界值分析是测试用例设计的基础中的基础几乎所有跟输入框、下拉框、日期控件有关的功能都能用上。但这两者谁先谁后很多人没想过。我的习惯是先做等价类划分再做边界值补充最后用错误推测来加菜。为什么这个顺序因为等价类解决的是覆盖面问题边界值解决的是精准度问题错误推测解决的是真实感问题。你不可能一上来就精确定位某个边界你得先把大区域分出来把有效数据和无效数据划清楚再去看边界上的那两三个值。举个例子一个库存管理系统的入库数量输入框要求是大于0小于等于10000的正整数。等价类怎么划有效等价类有三个1到10000之间的整数、大于0的任意整数这只是理论上说实际上还是要落到具体值无效等价类有一堆0、负数、小数、非数字字符、超过10000的整数、空值。边界值分析怎么做就是取边界旁边的值0和1下边界两侧、10000和10001上边界两侧。注意这里有一个新手常犯的错误——边界值不是只取边界本身而是要把边界两侧的值都取到而且要结合有效类取一个、无效类取一个。比如1是有效下边界0是无效下边界两个都要测。但是光这样还不够。我还会问一句这个输入框有没有输入法限制能不能粘贴复制粘贴一个1000有没有可能输入 1 带空格算不算通过这些用等价类和边界值划分不出来因为它们属于真实用户在操作时可能出现的输入方式——这就是错误推测法发挥作用的地方了。错误推测法听起来很玄学好像全靠个人经验其实也有套路基于你过去犯过的错和见过的bug去推测当前系统可能存在的问题。我有个习惯新项目开始前会专门去翻一下过往同类模块的缺陷报告把高频bug列成一张失效模式清单——比如日期格式在不同浏览器解析差异、金额计算浮点精度丢失、大量数据下分页按钮失效、快速双击提交按钮产生重复订单……这些清单每到一个新功能就拿出来过一遍能命中不少问题。2.2 流程类功能场景法才是主线别再用功能点罗列代替用户旅程输入类功能好处理真正让很多测试头疼的是流程类功能——用户从开始操作到结束中间可能跨页面、跨状态、跨数据变更。比如电商下单、审批流、订单退货流程这类功能光靠等价类和边界值是远远不够的你需要的是场景法。场景法的核心思想是用基本流和备选流把用户的操作路径走一遍。但我在工作中看到的普遍现象是大家用场景法用得特别粗糙基本流就是需求文档里的happy path备选流就是随便挑几个报错场景——这样下来整个流程的完整性还是覆盖不到。我自己的做法是把场景法和状态转换法结合着用。第一步先把系统的核心状态画出来比如一个订单的状态可能有新建、待支付、已支付、待发货、已发货、已完成、已取消。第二步画状态之间的合法转换边新建可以到待支付发起支付待支付可以到已支付支付成功待支付可以到已取消用户取消已支付可以到待发货支付完成进入备货……第三步把导致状态转换的动作逐条列出来。第四步用这些合法转换边推导基本流用非法转换边和异常情况推导备选流。这么做的好处是你会发现有些虽然流程上合法但产品经理没写清楚的状态组合。比如已发货之后还能不能申请取消如果订单已经出库了用户取消申请系统是拦截还是走逆向流程已支付但是支付回调没收到订单卡在中间态系统有没有对账机制这些问题如果等到执行阶段暴露出来要么是需求漏洞要么是开发实现没考虑——而你现在在用例设计阶段就发现了等于提前帮项目排了雷。场景法写出来的用例还有个好处就是可读性强。我评审别人的用例时最怕看到那种点击A按钮验证跳转到B页面点击C按钮验证D字段显示的碎片化用例——你根本不知道用户在干什么也说不清这条用例验证的是哪个业务目标。场景法用例就不一样它们的名字本身就带着业务含义用户支付超时后重新发起支付订单状态最终应为已支付并恢复库存扣减——评审人一眼就能看出这条用例的业务价值和验证点。2.3 多条件组合判定表、因果图、正交试验到底用哪个流程类功能处理完还有一个场景经常让人头大当一个动作的结果同时受多个条件影响时用例数量会失控。比如优惠券计算用户是否登录、是否会员、订单金额是否满足门槛、优惠券是否在有效期内、是否可叠加使用——五个条件两两组合就是32种情况全写出来用例数爆炸不写吧又怕漏掉关键组合。这种场景下不同的方法各有适用场景。判定表适合条件个数不多一般不超过4~6个且条件和动作都是离散取值的情况。因果图是判定表的图形化表达适合你在跟别人沟通逻辑时用实际写用例时还是转化为判定表更直接。正交试验法我个人觉得是最适合条件多、组合多、但全测不现实的场景——它用正交表取有代表性的组合用最少的用例覆盖两两组合的完整度很适合参数组合测试。不过我得给一句忠告正交试验法在真实项目中的应用没有教科书里那么乐观。因为正交试验假设所有条件之间是相互独立的而真实业务逻辑里条件之间往往有强关联——用户是会员和用户未登录这两个条件不可能同时为真。所以正交试验算出来的用例组合里经常会有一些逻辑上不可能的搭配你需要人工把这些排除掉。我的建议是先用判定表把业务规则的核心逻辑理清楚再用正交试验的思路处理那些理论上可以组合、但没必要穷举的次级参数两者结合才能既保证核心逻辑覆盖又控制用例规模。3. 如何判断用例够了从覆盖维度到优先级排序的完整框架用例写完了评审的时候最怕被问一个问题用例全了吗——全这个字是没法量化的。你不能拍着胸脯说全覆盖了你得有一套判断框架。3.1 功能点之外的隐形维度数据、状态、权限、环境、异常很多测试同学判断覆盖率的时候只看功能点——需求文档里写了几个功能点我就写几条用例。这是远远不够的。我在工作里总结了一套多功能维度检查法每次用例评审之前用这套维度清单做一次自查第一个维度是数据维度同样的操作不同数据状态下结果是否一致比如列表页有0条数据、1条数据、1000条数据时的分页展示比如搜索功能关键词为空、单字、长文本、带特殊符号时的表现。这些不写用例你心里就没底。第二个维度是状态维度上文已经说过流程类功能一定要画出所有状态和状态转换。很多bug其实就藏在状态动作的矩阵里——比如已取消订单重新支付这种操作需求文档根本没写但用户真的能到达这个页面历史订单里点了一个旧链接。这种从不该出现的入口进入的用例恰恰最能发现问题。第三个维度是权限维度同一功能对不同角色、不同数据范围应该有不同的可见性和操作性。前台用户能不能看到后台的删除按钮普通员工能不能看到所有人的薪资A部门经理能不能修改B部门的数据权限维度最容易出的是越权漏洞这类用例在安全测试里也是重点。第四个维度是环境维度不同浏览器、不同操作系统、不同网络环境下功能表现是否一致这不仅仅是兼容性测试的事——有些隐藏的js报错、样式错乱、接口超时只在特定环境下才会触发。我见过一个项目开发在自己Chrome上测得好好的用户用Safari打开直接白屏就是因为有个API在Safari下不被支持。第五个维度是异常维度这是我最看重的维度。包括外部接口异常、依赖服务超时、数据库连接失败、消息队列积压等。很多团队把异常测试扔给联调阶段去碰运气但真正的异常场景需要提前设计——比如支付回调延迟2分钟到达系统怎么处理第三方短信服务挂了注册流程是继续还是报错这些不是联调能碰出来的得专门写用例去验证。用这套维度自查完你会发现功能点全覆盖只是一个及格线。真正的好用例是能让这些隐形维度里的深层问题浮到水面上来的。3.2 优先级排序高风险、高频次、高影响三者合一的先测用例数量永远不可能无限膨胀所以在用例设计阶段就得学会做减法。我的排序逻辑就一句话风险高低、使用频次、影响范围三者综合打分分数高的优先级就高。这不是什么高深理论但真正落地的团队不多。具体怎么操作我给每条用例标三个维度分每个维度1到5分风险维度是这个功能出错的可能性——逻辑越复杂、耦合越深、越容易出问题分越高频次维度是用户实际使用这个功能的频率——高频功能出错影响面最大影响维度是出错后的后果严重程度——数据不可恢复、资金损失、权限泄露都是5分级别的。然后计算综合分风险乘以频次乘以影响或者简单相加看你团队习惯。分高的用例放在冒烟测试和回归测试的核心集里分低的放在扩展回归里。这里有个容易被忽视的tip冒烟测试用例集一定要从高优先级用例里选而不是从功能点里平均选。因为冒烟测试的目的是用最少的时间确认系统没崩只有把高风险高频的功能覆盖到了这个目标才成立。4. 用例表达与文档化字段怎么设计、步骤怎么写才算一份能直接用的用例设计好用例思路之后表达层面的问题就来了。很多团队用例写了不少一执行才发现前置条件没写清楚、测试数据没准备好、预期结果模糊不清——执行人员拿到用例根本没法跑。这一节我专门聊聊怎么把脑子里想好的用例落成一份别人能直接照着执行的文档。4.1 用例字段设计从最小集到完整集哪些字段必不可少功能测试用例模板不同公司差别很大。有些公司一个Excel里就五六个字段用例编号、模块、标题、步骤、预期结果。有些公司特别讲究从测试环境、测试阶段、前置条件、测试数据、步骤描述、预期结果、实际结果、缺陷编号、执行人、执行时间、备注十几个字段一个不少。我的观点是字段不是越多越好但有几个字段绝对不能省。省掉那些字段用例的可执行性和可追溯性都会大打折扣。首先是前置条件这个字段重要性极高但也是被省略得最多的。前置条件写清楚执行人员才知道这条用例的起点是什么——需要哪些数据已存在、哪个环境已准备好、登录的是哪个账号。我见过很多用例步骤第一条就写点击个人中心但个人中心入口在哪需要登录吗数据是空还是有历史记录全没写执行人员只能靠猜。第二步测试数据字段也很关键。比如测试搜索功能你得写明搜索关键词是什么期望返回哪些结果测试转账功能你得写明转账金额、账户余额、手续费规则。没有明确测试数据的用例不同人执行可能得出不同结论——你说验证通过我说数据不对吵半天最后发现是各自拿的数据不一样。第三步预期结果字段一定要写到可观察可判定。不要写系统正常运行这种废话要写页面右上角提示保存成功列表第一行显示新记录记录状态为草稿。预期结果越具体用例执行的判定就越容易即使换一个新人来执行也不会因为理解偏差而出错。第四步用例编号要有规则。很多项目的用例编号就是流水号用例多了之后完全没法追溯。我习惯的编号规则是模块缩写-阶段-序号比如LOGIN-SM-001代表登录模块冒烟测试第1条、ORDER-EXT-023代表订单模块扩展测试第23条。这样做的好处是从缺陷编号里直接能反查到用例编号用例编号又能定位到模块和阶段——需求变更的时候改起来也有索引可循。4.2 步骤描述操作、输入、预期逐行对应一段白话胜过十行术语用例步骤怎么写我非常看重可执行性。我见过最差的写法是输入正确账号密码点击登录验证页面跳转。——正确账号密码是哪个账号哪个密码跳转到哪个页面验证什么什么都不明确。我自己的写法偏好是每个步骤都包含三要素操作位置、操作动作、输入数据如有。每个步骤的预期结果单独成行紧跟其后。比如登录用例可以这样写打开登录页访问地址https://xxx.com/login测试环境输入用户名test_user01该账号在测试库中已存在输入密码Test123456点击登录按钮预期结果页面跳转至首页右上角显示test_user01首页接口请求均返回200这么写看起来很啰嗦但一个从没接触过这个项目的执行人员照着这个步骤就能完成测试。这才是用例该有的样子——用例是给人看的执行手册不是给自己看的思维导图。另外还有一个细节用例步骤里应该写数据而不是写任意有效数据。因为任意有效不知道怎么构造你说随便填一个执行的人随手填了个123456然后发现报错说密码格式不对白白浪费时间排查是不是环境问题。4.3 从功能用例到自动化前置设计阶段就要留的自动化接口随着测试团队逐步引入自动化比如用Playwright这套工具链做Web端端到端测试功能用例的设计思路也要跟着升级——最核心的变化是用例设计阶段就要考虑这条用例将来能不能被自动化复用。我在日常工作中有一个习惯每写一条手工用例都会在脑子里过一遍如果自动化来做这条用例的步骤是否可脚本化。有些用例天生适合自动化固定的操作路径、明确的输入输出、确定的页面跳转——这些可以按Playwright的Page Object模式来拆解把页面元素定位和业务操作封装成Page对象用例脚本只做点击和断言两层。有些用例不适合自动化需要人工视觉判断的样式问题、需要连第三方硬件的场景、大量随机数据驱动的探索性测试——这些留在手工用例里更理智。所以在用例模板里我会额外加一列自动化适配性高/中/低/不适用并在步骤描述中尽量把元素的稳定标识id、name、data-testid等记录下来。这样做有一个实际好处等真正开始搭自动化框架的时候你手头已经有一批按自动化标准组织过的用例了不用再回头重新梳理需求。我见过太多团队功能测试用例是一套Excel自动化脚本是另一套Script两边各写各的维护成本翻倍。从一开始就在用例设计阶段对齐后面能省很多事。5. 用例评审和维护好的用例是改出来的不是写出来的用例写完了评审做完了是不是就结束了不是。用例的生命周期是从评审会之后才开始的。我见过太多项目的用例库版本还停留在半年之前新需求加了一堆旧用例没删改动的逻辑也没同步——这样的用例库执行价值接近于零。5.1 评审会看什么业务正确性、逻辑完备性、表达可执行性用例评审这个环节不同团队做法差别很大。有的团队评审就是测试组自己人过一遍有的团队会叫产品、开发、测试三方一起过——后者才是我觉得靠谱的做法因为三方看用例的角度完全不同三个角度合起来才能把问题暴露全。产品经理看什么看用例是否真实反映了业务需求——有没有遗漏商业规则有没有把某种边界情况处理得跟业务预期不符。开发人员看什么看用例是否符合系统实现——某个功能其实是调了第三方接口的你的预期结果里得体现异步等待某个状态其实是定时任务刷新的你的用例步骤里得留出触发时机。测试人员自己看什么看表达可执行性——前置条件清不清楚测试数据有没有给全预期结果可不可判定评审会上我最常问的三个问题是第一个这条用例的失败怎么定义如果预期结果是页面提示保存成功那如果页面没有提示但数据确实存进去了算通过还是失败这类判定标准必须在评审时定清楚否则执行时一定打架。第二个这个场景的数据从哪里来很多用例需要特定数据支持比如测试用户已购买过该课程。执行人员要去哪找这个用户是自己注册一个新账号买一遍还是测试环境里已经有预置数据评审的时候不把这个链路走通执行阶段就开始到处求人。第三个这条用例和那条用例之间有无依赖关系用例的执行顺序有没有讲究比如新增用户这条必须在查询用户列表之前执行。如果有依赖关系要么在用例里写明前置用例编号要么在Excel里把用例排好序。移动端的用例尤其依赖执行顺序——你不可能在没有安装App的情况下测试启动App后的闪屏页。评审会的产出不只是通过不通过的结论而是一份修改意见清单。我把每个意见标记为阻塞性必须改和建议性可以不改阻塞性的比如业务规则理解错误、遗漏关键场景、测试数据不可用必须当场改完建议性的比如步骤描述可以更精简、字段顺序调整会后统一处理。5.2 变更驱动的用例维护新增、修改、删除三条线并行系统上线之后需求变更不可避免。每一次需求变更都是用例库的一次手术。我建议团队里指定一个用例库Owner维护者每次变更走一条标准流程第一步需求变更分析。拿到变更需求后先评估影响范围——涉及哪些模块、哪些状态、哪些数据规则。影响分析做得越细用例改动范围就越准。第二步用例新增。新增的特性写成新用例这部分逻辑跟从0到1设计用例一样不再赘述。但要注意新增用例的编号不要插到旧编号中间去用新模块前缀加新序号保持编号体系稳定。第三步用例修改。这个最容易被偷懒——很多测试同学在旧用例上直接把预期结果改了也不管步骤描述、前置条件、测试数据是否需要同步调整。我见过一个经典事故需求把注册时手机号必填改成了注册时手机号可选填测试同学只改了预期结果另一条却不知道手机号必填这条用例在另外两个模块如忘记密码模块、安全设置模块里也有同样的断言三个地方全要同步改——漏改的直接后果就是后面回归测试误报了一堆bug开发查了半天发现根本不存在。第四步用例删除。删除旧用例也是学问不要直接用物理删除建议在用例状态列标记为废弃——保留可追溯性。因为出了问题要回溯时你可能需要知道当年这个地方为什么不再测试了——可能是功能下线了也可能是策略调整了。5.3 覆盖率评估从点数人头到需求-用例映射最后聊聊覆盖率这个指标。很多人一提覆盖率第一反应是代码覆盖率——行覆盖率、分支覆盖率多少多少。但这个对功能测试用例来说并不直接适用。功能测试用例设计更关心的是需求-用例映射覆盖率。我的做法是每个功能需求点建立一张需求项-用例编号映射表。比如需求项用户注册-手机号校验对应用例REG-001、REG-002、REG-003需求项用户注册-密码强度校验对应REG-004、REG-005。评审时把映射表打开从上往下逐条打勾看看哪些需求项还没有对应用例或者有了用例但没覆盖关键分支。这张表的维护成本不高但它的价值在于让你的用例库从一堆Excel变成了一张可审计的网络——每一个需求点都有据可查每一条用例都有责任归属。这套需求-用例映射的另一个价值是在需求变更时快速定位影响面。回头再看5.2节说的同步修改问题如果你有映射表一条需求变更过来直接查表就知道哪些模块下的哪些用例需要看不用靠记忆去翻Excel。到这里我把功能测试用例设计从读懂需求到表达落地到持续维护的完整思路都过了一遍。这一套东西看着挺多但落到日常工作中核心就是一句话用例设计不是写出来的是拆出来的——把需求拆成规则、把规则拆成路径、把路径拆成步骤、把步骤拆成断言。你把这个拆字吃透了用例自然就有血有肉了。
返回列表