极客时间已完结课程限时免费阅读

18|测试策略(一):如何构造有效的测试策略?

18|测试策略(一):如何构造有效的测试策略?-徐昊 · AI时代的软件工程-极客时间
下载APP

18|测试策略(一):如何构造有效的测试策略?

讲述:徐昊

时长06:30大小5.95M

你好,我是徐昊,今天我们来继续学习 AI 时代的软件工程。
上节课,我们展示了按照测试驱动开发(Test Driven Development,TDD)的节奏,与大语言模型(Large Language Model,LLM)结对编程(Pairing Programming)的过程。还展示了我们如何使用这样的方式,在保证质量的前提下兼顾速度,获得实打实的效率提升。
然而,我们上节课展示的例子非常的简单,是一个仅仅包含一个类的工具类代码。因而针对它的测试策略也非常的简单。换成更复杂的场景,我们就需要构建有效的测试策略,才能保证通过测试策略得到顺畅的开发节奏。

使用测试四象限构造测试策略

提到测试策略,很多人会不自觉地想到测试金字塔(Testing Pyramid)。这是 2009 年 Mike Cohn 在他的著作《Succedding with Agile》提到的一个隐喻,借助金字塔结构描述不同层次的测试。比如 Mike Cohn 自己就给出了一个三层的金字塔结构,分别对应单元测试(Unit Tests)、服务测试(Service Tests)和用户界面测试(User Interface Tests)。
然而测试金字塔这个隐喻,主要想说明的是自动化测试的分布,以及不同层之间的对应关系。良好的自动化测试,应该符合金字塔式的分布,也就是能够提供快速反馈的细粒度测试占据多数,而缓慢昂贵的粗粒度测试应该只有一小部分。
其实这里非常容易忽略的一点是:每当有一个处于金字塔上层的测试失败,必然有多个处于底层的测试失败。这才是测试金字塔的核心隐喻。下层的测试撑起上层的测试,而不是毫无关联的两套测试。
所以测试金字塔并不能帮助我们设计有效的测试策略,它只能帮我们检查我们的自动化测试集合是否处于良好状态,以及不同层之间的测试是否存在必要的关联。设计测试策略,测试四象限(Agile Testing Quadrants)是一个更好的框架和工具。
测试四象限是 2003 年由 Brian Marick 提出的,最开始的名字叫做 Marick 的测试矩阵(Marick’s Test Matrix)。Brian Marick 开创性地将不同种类的测试放置在不同的象限,用来说明它们的作用。后来这逐渐演化为广为人知的测试四象限:
首先我们可以看到,Brain Marick 选取了两个维度构成四象限,分别是测试的目的以及测试的受众。测试的目的被分成支持团队(Supporting Team)和评价产品(Critique Product),测试的受众被分成技术导向(Technology Facing)和业务导向(Business Facing)。
测试的受众很好理解,那么测试的目的是什么意思呢?所谓支持团队,是指测试主要目的是为开发团队提供反馈。而评价产品,则是指测试的主要目的是评估产品在不同维度上的表现。
比如登录系统的功能测试,它是团队的自动化回归测试(Regression Test)的一部分,同时它也可能是用户验收测试(UAT)的一部分。同样一个测试,它的目的是完全不同的。对于回归测试而言,它的目的主要是告诉团队功能是否被破坏;而对于用户验收测试而言,目的则是验证功能是否能满足用户的需要。因而我们在思考测试的时候,要综合考虑测试的目的与受众,而不是仅仅关注在具体的测试上。
然后,按照测试的目的与受众,可以自然地划分出四个象限:
第一象限(Q1),技术导向的支持团队的测试。这个象限中的测试是为交付团队中的技术人员提供快速反馈,是为了在组件和子系统的粒度上定位问题。常见的单元测试(Unit Testing)、组件测试(Component Testing)都属于这个象限;
第二象限(Q2),业务导向的支持团队的测试。这个象限中的测试是为交付团队提供关于业务的反馈,是根据验收条件(Acceptance Criteria)构造的各种测试。功能测试(Functional Testing)、用户故事测试(Story Testing)、示例说明(Specification by Example)都属于这个象限。需要注意,这些测试并不只对业务人员有用,对团队中所有人都非常重要;
第三象限(Q3),业务导向的评价产品的测试。这个象限中的测试评价的是产品是否能够提供业务价值。主要是从功能和用户交互的维度上评价。用户验收测试、探索性测试(Exploratory Testing)、可用性测试(Usabliltiy Testing)都属于这个象限;
第四象限(Q4),技术导向的评价产品的测试。这个象限中的测试评价的是产品的跨功能特性(Cross function requirements),比如安全性、性能、容量、负载等等。所以显而易见,性能测试(Performance Testing)、安全测试(Security Testing)等测试属于这个象限。
测试四象限可以从全局出发,帮助我们理解不同种类的测试到底发挥了什么作用。因此,测试四象限是承载测试策略的绝佳框架。而构造测试策略的过程,也就变成选择恰当的测试类型,分别放入不同象限的过程。

通过验收条件构造支持团队的测试

在使用四个象限构造测试策略时,评价产品的 Q3 和 Q4 象限是比较容易构造的。而支持团队的 Q1 和 Q2 象限则比较困难。
这一方面是因为绝大多数交付团队对于 Q3 与 Q4 象限的测试更加熟悉,另一方面也是因为 Q3 和 Q4 象限的测试相对正交,彼此之间不存在太大的关联。比如,Q4 象限的性能测试并不依赖于 Q3 象限中的 UAT、可用性测试或探索性测试。
而支持团队的 Q1 和Q2 象限的测试之间则存在更深的关联。当我们只有 Q2 象限的测试时,我们只知道出了问题,但不知道是哪个组件的问题;而当我们只有 Q1 象限的测试时,我们只知道组件出了问题,但不知道这会带来什么影响。
因而单纯地在团队中引入功能测试(Q2 象限)和单元测试(Q1 象限),并不能达到支持团队的效果。我们更需要的是,建立 Q1 和 Q2 象限测试间的关联,这是测试策略中的极为重要的一环。
那么怎么样才能有效地建立 Q1 和 Q2 象限测试的关联呢?有两个关键,一是验收条件,二是 TDD 的任务分解。
正如我们之前讲过的,验收条件是用户故事(User Story)的重要组成部分,用于帮助开发团队和客户明确产品或功能的期望表现、功能要求和可接受的标准。那么站在测试的角度上说,每一个验收条件,都可以对应一组功能测试(Q2 象限测试)。
TDD 的任务分解是将待开发的任务,分解为一组可测试的任务,这是测试驱动开发的核心。当我们同时使用验收条件澄清需求时,我们需要做的就是在验收条件的上下文中,按照不同的功能上下文,进行任务分解。
所谓功能上下文,可以是一个模块,一个组件,一个类(Class)或一个函数(function)。而通常我们使用测试驱动进行开发的时候,会持续对任务进行分解,直到功能上下文达到合适的粒度为止。因而站在测试的角度上说,每一个可测试的任务都对应着一组组件测试(Q1 象限测试)
通过任务分解得到的 Q1 象限和 Q2 象限的测试必然存在内在的关联关系。当验收条件对应的测试失败时,必然意味着某个功能上下文中的功能不满足预期。那么该功能上下文中,必然有某个任务项没有做到位。那么该任务项对应的测试,必然也会失败。
不难发现,通过任务分解分解得到的 Q1 象限和 Q2 象限测试,还很容易满足测试金字塔的结构。因为处于金字塔上层的 Q2 象限测试失败,必然有多个处于底层的 Q1 象限测试失败。Q1 象限的测试撑起上层 Q2 象限的测试,而不是毫无关联的两套测试。

小结

当我们按照测试驱动开发的节奏与大语言模型结对编程时,构建支持团队的测试(Q1 象限和 Q2 象限)是至关重要的一步。
Q1 象限的测试能够撑起上层 Q2 象限的测试,而不是毫无关联的两套测试。通过验收条件和 TDD 的任务分解,能够帮我们有效建立起这两套测试的关联。
Q2 象限的测试,可以帮助我们验证 LLM 生成的代码是否满足验收条件的诉求;Q1 象限的测试则帮助我们聚焦到某个具体的功能上下文中,避免因 Token 限制带来的一系列麻烦。
那么现在的关键就在于功能上下文要如何划分。这是我们下节课要讨论的问题。

思考题

你觉得有哪些划分功能上下文的方法?
欢迎在留言区分享你的想法,我会让编辑置顶一些优质回答供大家学习讨论。

1. 测试策略的重要性:构建有效的测试策略是保证软件开发质量的关键步骤,尤其在复杂场景下需要有效的测试策略来保证开发节奏。 2. 测试四象限框架:测试四象限是一个重要的测试策略框架,通过将测试按照目的和受众划分成四个象限,即支持团队和评价产品的技术导向和业务导向测试。 3. 测试四象限的作用:测试四象限框架有助于理解不同种类的测试的作用,帮助设计测试策略,选择合适的测试类型并放置在不同象限中。 4. 验收条件构造支持团队的测试:验收条件对应一组功能测试(Q2象限测试),TDD的任务分解对应一组组件测试(Q1象限测试),通过这种方式可以有效建立Q1和Q2象限测试的关联。 5. 功能上下文的划分:下节课将讨论功能上下文的划分方法,这是构建支持团队测试的关键问题。 6. 重点总结:构建支持团队的测试(Q1象限和Q2象限)是至关重要的一步,Q1象限的测试能够撑起上层Q2象限的测试,通过验收条件和TDD的任务分解能够帮助有效建立这两套测试的关联。 7. 问题提出:留言区欢迎分享划分功能上下文的方法,编辑将置顶优质回答供大家学习讨论。

分享给需要的人,Ta购买本课程,你将得29
生成海报并分享
2024-04-17

赞 1

提建议

上一篇
17|如何与LLM结对编程?
下一篇
19|测试策略(二):功能上下文划分
unpreview
 写留言

全部留言(9)

  • 最新
  • 精选
  • 王达菲
    2024-04-18 来自陕西
    测试的四象限困扰我很久了,主要是几个概念,何为业务?何为技术?比如说安全性,这是业务还是技术。所谓支持团队该如何理解?感觉Q1和Q2是偏向于功能测试,验证功能设计与实现的一致性,那么是不是意味团队就只关注于功能验证?问题有点多,烦劳徐老师解惑

    作者回复: 课里都写了 仔细看

    共 2 条评论
    1
  • 术子米德
    2024-04-18 来自浙江
    🤔☕️🤔☕️🤔 【R】测试金字塔的隐喻:上层测试失败,必然多个底层的测试失败。 测试四象限(Agile Testing Quadrant): (Business vs Technology)x Facing Critique Product vs Supporting Team Q1:Technology Facing + Supporting Team Q2:Business Facing + ^^^ Q3:^^^ + Critique Product Q4:^^^^^^ + ^^^ 关联Q1&Q2的关键:验收条件 + 分解TDD任务(待开发任务 分解为 可测试任务)。 【.I.】有种情况让我尴尬,那就是问题在别处那里发现,有种情况让我更尴尬,那就是加点打印再去别处复现,还有种情况让我气愤,那就是复现后改动再拿去让别人去验证,还有种情况让我更气愤,那就是问题再次出现时,谁有打印就谁去负责排查。 有种做法让我认可,那就是在尴尬的打印中复现问题后,赶紧跑回自己家,去分析这个问题现象,是因为自己缺少哪方面的验证点,去改进现在的测试用例、或者再补充一个新的测试用例,并且在名字上能够有T0和T1/2+的区分,用新的验证用例在自己家复现问题,再去修复问题不迟,最后给出去之前,本地所有用例都通过,才有自信问题已搞定,才明白新问题给自己带来多少认知和能力的提升。 【Q】Q1&Q2指向的支持团队,开发人员+测试人员 or 测试开发人员? 即这2个象限的测试用例,由2组人独立设计实现,还是由1组人全包设计实现? — by 术子米德@2024年4月18日
    展开

    作者回复: 理想情况是一组人

    共 2 条评论
  • 范飞扬
    2024-04-17 来自浙江
    1、Q1 象限测试,直接叫“单元级别功能测试”不是更好么?我有三个理由。第一、叫组件测试的话,忽略了类和函数。第二、 光和别人说组件测试,别人也可能理解成是Q2的测试。第三、老师在自己的 TDD 课里就是把 Q1 的测试称作“单元级别功能测试”。 2、那么,很自然的,Q2象限测试叫功能测试就不合适了。难道Q1的测试不是功能测试么?Q1也是功能测试,粒度更小罢了。所以,Q2的测试可以称作“系统级别功能测试”,这样就和Q1的“单元级别功能测试”对应上了。 3、不过,Q2 测试更好的名字可能是 Acceptance Test. 很巧,就在老师说的《Succeeding with Agile》里,Mike Cohn推荐了一本书叫《Test driven: TDD and acceptance TDD for Java developers》。这本书里就提到,ATDD (Acceptance TDD) 帮助开发者构建满足商业需要的软件,而 TDD 帮助开发者保障了软件的技术质量[1]。那么,很自然的,Q2的测试可以称作 Acceptance Test. 4、International Software Testing Qualifications Board (ISTQB) 对于 Acceptance Test 的定义是“验证系统是否满足验收条件的测试”[2]。 从这个定义可以看出,Acceptance Test 直接和验收条件相关联,那么,很自然的,Q2的测试可以称作 Acceptance Test. 5、对于熟悉徐昊老师的TDD课程的同学,Q1 和 Q2 的测试还可以有另一套命名。可以看出,本文需求分解的图片和 TDD 课程里的图片极为相似,就是把功能点称作了验收条件。那么,很自然的,Q2 测试可以称作功能点测试,Q1 测试可以称作功能上下文测试。 6、接着第 5 条,通过和本文的图片进行比对,可以发现当年 TDD 课程里的图片其实漏画了 Q2的测试,应该补上。 7、接着第 5 条,那思考题就很简单了,老师讲过。 思考题:你觉得有哪些划分功能上下文的方法? 方法一、可以通过预先设计(Upfront Design)的架构愿景(比如 MVC)划分功能上下文。这对应了 TDD 的伦敦学派。 方法二、可以通过演进式设计(Evlutionary Design)提取或梳理架构愿景,再划分功能上下文。主要方法是重构,特别是重构到模式(Refactoring to Patterns)。这对应了 TDD 的经典学派。 注释: [1] : Acceptance test-driven development(acceptance TDD) is what helps developers build high-quality software that fulfills the business’s needs as reliably as TDD helps ensure the software’s technical quality. [2]: https://en.wikipedia.org/wiki/Acceptance_testing
    展开
    共 1 条评论
    5
  • 范飞扬
    2024-05-18 来自广东
    原文:构造测试策略的过程,也就变成选择恰当的测试类型,分别放入不同象限的过程。 思考: 1、测试类型和象限不是一个东西么? 2、参考直播里讲的,这里应该是:“选择恰当的组件类型,分别放入不同象限”吧,而不是测试类型
    共 1 条评论
  • 6点无痛早起学习的和...
    2024-05-04 来自北京
    2024年05月04日16:49:34 来完成一下课后作业 划分功能上下文的方法,一般会以业务功能(接口)去划分,然后任务项通过架构分层划分(http 层、业务逻辑层、数据交互层)
  • 术子米德
    2024-04-18 来自浙江
    🤔☕️🤔☕️🤔 【Q】哪些划分功能上下文的方法? 【A】方法1:看看当下,手头有些什么技术栈的人来参与设计实现验证,想想未来,会有怎样技术栈的人来维护修正改进;方法2:分析当前需求要解决的问题,跟业界公开的架构风格与设计模式,它们所解决的问题的近似程度,越类似越可参考借鉴,即采用其划分方法; — by 术子米德@2024年4月18日
  • 奇小易
    2024-04-18 来自福建
    TDD 里面的测试都是功能测试, 在这里的 Q2 和 Q1 是否可以理解为粒度不同的功能测试?
  • Gojustforfun
    2024-04-17 来自北京
    > 每一个可测试的任务都对应着一组组件测试(Q1 象限测试) “任务”最终都要落实到代码层面,由代码中的工作单元(抽象模型)即结构体、方法、类、函数等提供功能来完成该“任务”. “可测试的任务”, 相当于在说, 你在设计模型/工作的单元的时候, 除了要提供功能以完成“任务”还要考虑其可测试性——以容易编写测试的方式来设计并实现该模型/工作单元. 先写测试会倒逼你朝着可测试方向设计模型/工作单元. “组件测试”其实也是工作单元/模型的功能测试, 为什么是一组呢? 因为要覆盖正常情况、边界情况和异常情况
    展开
  • Gojustforfun
    2024-04-17 来自北京
    在老师的TDD课程中介绍TDD流程时 https://time.geekbang.org/column/article/496703 有类似的图片, 但用“功能点”替代了这里的“验收条件”. 当然,TDD课程中也说了, “首先将需求分解为功能点,也就是将需求转化为一系列可验证的里程碑点” 是不是可以这样理解: 1. 需求分解的产物就是功能点集合/列表即各个用户故事的验收条件的集合/列表 2. 功能点就是某个用户故事的验收条件 2. “可验证的里程碑点”, 是不是可以理解为, 当某个用户故事的所有验收条件(功能点)都实现了,并且将代码提交后, 此时软件就可以工作、验证的状态.
    展开
    共 5 条评论