什么是契约测试?

本文首发于 Guanngxu 的个人博客什么是契约测试?

参考文章:
聊一聊契约测试 —— ThoughtWorks洞见
契约测试 —— 米阳
前后端分离了,然后呢? —— 邱俊涛

契约测试全称为:消费者驱动契约测试,最早由 Martin Fowler 提出。契约这个词从字面上很容易理解,就是双方(多方)达成的共同协议,那又为什么需要契约测试这个东西呢?

在当前微服务大行其道的行业背景下,越来越多的团队采用了前后端分离和微服务架构,我们知道微服务是由单一程序构成的小服务,与其它服务使用 HTTP API 进行通讯,服务可以采用不同的编程语言与数据库,微服务解决了单体应用团队协作开发成本高、系统高可用性差等等问题。

但是微服务也引入了新的问题,假设 A 团队开发某服务并提供对应的 API,B 团队也在开发另一个服务,但是他们需要调用 A 团队的 API,为了产品的尽快发布,两个团队都争分夺秒,已经进入联调阶段了,然而出现了下面这样的尴尬情况。

image

随着越来越多的微服务加入,它们的调用关系开始变得越来越复杂,如果每次更改都需要和所有调用该 API 的团队协商,那沟通成本也未免太大了,试想下图的沟通成本。

image

为了保证 API 调用的准确性,我们会对外部系统的 API 进行测试,如果外部系统稳定性很差,或者请求时间很长的时候,就会导致我们的测试效率很低,当调用 API 失败时,你甚至无法确定是因为 API 被更改而导致的失败还是运行环境不稳定导致的失败。

A 团队提供的 API 不稳定,肯定会导致 B 团队效率低下,为了不影响 B 团队的进度,所以构建了测试替身,通过模拟外部 API 的响应行为来增强测试的稳定性和反应速度。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-L2gpRdb2-1601307736300)(https://martinfowler.com/bliki/images/contractTest/sketch.png)]

但是这样做真的就解决问题了吗?当所有内部测试都通过时,能拍着胸脯说真正的外部 API 就一定没有变化?很简单的一个解决方案就是:部分测试使用测试替身,另一部分测试定期使用真实的外部 API,这样既保证了测试的运行效率、调用端的准确性,又能确保当真实外部系统API改变时能得到反馈。

image

感觉剧情到这里就差不多该结束了,实际上真正的高潮部分开刚刚开始。如果外部 API 的反馈周期很长,那增加真实 API 测试间隔时间就又回到了最初的起点。现在我们回顾一下上面的方案。

在上面的场景中,我们都是已知外部 API 功能来编写相应的功能测试,并且使用直接调用外部 API 的方式来达到测试的目的,如此就不可避免的带来了两个问题:

  • API 调用者(消费者)对服务提供方(生产者)的更改是通过对 API 的测试来感知的;
  • 直接依赖于真实 API 的测试效果受限于 API 的稳定性和反映速度。

解决方案首先是依赖关系解耦,去掉直接对外部 API 的依赖,而是内部和外部系统都依赖于一个双方共同认可的约定—“契约”,并且约定内容的变化会被及时感知;其次,将系统之间的集成测试,转换为由契约生成的单元测试,例如通过契约描述的内容,构建测试替身。这样,同时契约替代外部 API 成为信息变更的载体。

前后照应一下,我们现在再来看一下消费者驱动契约测试。它有两个不可或缺的角色:消费者是服务使用方;生产者(提供者)是服务提供方。采用需求驱动(消费者驱动)的思想。契约文件(比如 json 文件)由双方共同定义规范,一般由消费者生成,生产者根据这份契约去实现。

契约测试其中一个的典型应用场景是内外部系统之间的测试,另一个典型的例子是前后端分离后的 API 测试。行业内比较成熟的解决方案是 Swagger SpecificationPact Specification,这里不做展开讨论。

我们同样可以把契约测试的思想用到代码的编写中,契约测试通过一个契约文件来解耦依赖,那么对于需要用户定义很多规则的场景,我们同样可以将这些规则像契约文件一样抽取出来,这样就降低了代码之间的耦合度。

最后敲敲黑板,契约测试不是替代 E2E 测试的终结者,更不是单元测试的升级换代,它更偏向于服务和服务之间的 API 测试,通过解耦服务依赖关系和单元测试来加快测试的运行效率。

  • 4
    点赞
  • 23
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Guanngxu

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值