先给结论:不要试图写一个“通用组件验收样例”覆盖所有页面。正确做法是先把差异归因到页面上下文还是组件自身状态,再按归因结果选择两种不同的样例构造方式。如果同一组件在A页面正常、B页面异常,而两页传入的数据结构一致,问题多半在页面环境(样式作用域、父容器、脚本加载顺序);如果两页数据形态不同,问题多半在组件对输入的容错边界。前者要构造“环境对照样例”,后者要构造“输入边界样例”,两者不能混用。
在动手写验收样例前,先用最小成本收集证据,避免样例方向选错。
这三组证据的价值在于:它们指向的验收样例结构完全不同。DOM差异对应环境样例,输入差异对应边界样例,时序差异对应加载顺序样例。若三组都无明显差异,才考虑组件内部状态残留,此时样例要加入“同页多次渲染”的重复调用。
当两页传入数据一致、只有表现不同时,验收样例应固定数据、只变化环境。具体动作是:
如果差异跟着包裹结构走,说明问题在页面环境,验收样例就应长期保留这两种包裹结构作为回归项。如果差异不跟着走,说明环境不是主因,应转向输入边界样例。这个动作的结果直接决定下一步方向,所以不要跳过。
假设某列表组件在“资讯列表页”显示正常,在“产品详情页”的推荐位出现高度塌陷。两页传入的数组长度相同。按上述动作替换包裹结构后,塌陷跟着详情页的父容器走,那么验收样例就固定为“同一组件 + 两种父容器”,而不是去改组件内部样式。这里的前提是两页数据确实一致,若数据不一致,这个结论不成立。
当两页数据形态不同时,环境对照样例会误导你。此时验收样例应固定页面环境、只变化输入。具体动作是:
这样做的代价是样例数量会明显增加,但换来的是可定位性:一旦线上再次出现差异,你能快速判断是哪个字段的哪种取值触发的。若组件对缺失字段没有兜底,验收样例就应把“缺失字段”列为必测项,并在组件层面补默认值,而不是在每个页面各写一份兼容代码。
环境对照样例适合组件被多个页面复用、数据来源统一的场景,代价是需要维护多套包裹结构,页面改版时容易失效。输入边界样例适合组件接收数据来源分散、字段不稳定的场景,代价是样例数量增长快,执行成本高。若两种差异同时存在,应先做环境对照,再做输入边界,因为环境差异会掩盖输入差异的真实表现。
如果两页初始渲染一致,只在点击、滚动或切换标签后出现差异,上述两种样例都不够用。此时应构造“交互序列样例”:记录从初始状态到异常状态之间的操作步骤,并在两个页面上执行同一序列。若序列一致但结果不同,问题在页面级事件监听或全局状态;若序列本身就无法在两页复现,说明差异来自用户路径而非组件,验收重点应转向路径覆盖,而不是继续加组件样例。
构造验收样例的核心不是穷举,而是让每条样例都能回答“差异来自哪里”。先归因、再选样例类型、最后固定为回归项,这个顺序比样例数量更重要。