【质量实践】微服务架构下的软件测试探索

随着微服务架构流行,公司开发平台从传统平台向基于微服务架构的云原生平台迁移,软件测试测试方法和工具也必须相应调整,才能更好提高测试效率,尽早发现bug,保证产品质量。

微服务架构下,一个应用由多个相互独立的服务组成,每个微服务对外暴露接口,一个微服务通常还会去调用其它微服务,鉴于这些特点,微服务架构下的测试与单体架构测试即有相同之处,又带来新的测试挑战。

根据 Martin Fowler 的测试理论,测试应该遵循如下测试金字塔组合:测试金字塔最底层是单元测试,然后是接口测试、集成测试,继而是面向应用程序服务层的中间层测试,最高层是面向用户的手工进行业务逻辑测试。

微服务架构下的软件测试,遵循如上原则的同时,又有新的挑战。不同服务间有依赖性,不同服务可能会在不同环境下运行,涉及多个服务还可能互相干扰,如果手动回归测试将不堪重负。

在微服务架构中,自动化是必须采用的方法,能够自动化的尽量自动化。

1.1 微服务下单元测试

微服务架构下,单元测试是保障代码质量的第一道关口,也是最重要的关口。

1.1.1 使用Junit进行单元测试

以往开发过程中,虽然强调单元测试的重要性,但单元测试一般是进行手工测试,不可重复使用。

优秀的单元测试要求符合自动化、独立性和可重复的AIR原则,用断言而非人工介入检查,这样才能尽早发现缺陷,降低开发成本。不论是单体项目还是向微服务迁移的项目,通过单元测试,开发才可以放心地重构代码,提高重构成功率。

JUnit 是一个 Java 语言的单元测试框架。基本常见开源框架都对JUnit 有相应的支持,使用JUnit可以书写一系列的测试方法,对项目所有的接口或者方法进行单元测试。每个单元测试用例相对独立,由JUnit启动,自动调用。不需要添加额外的调用语句。 JUnit可以自动化测试并判断执行结果, 不需要人为的干预。 只需要查看最后结果,就知道整个项目的方法接口是否通畅。

1.1.2 自动化统计代码覆盖率

单元测试的覆盖率度量统计,可在在MAVEN加JaCoCo插件来完成。

JaCoCo是款JAVA代码主流开源覆盖率工具,可以方便地嵌入到Maven中,并且和主流持续集成工具(如Jenkins)和静态代码检查工具(如Sonar)都有很好的集成。

开发人员本地的IDE工具中也可以安装JaCoCo覆盖率插件,当本地开发完单元测试用例并构建后,即可看到覆盖率信息,进而可以快速补充用例,达到覆盖率要求。

1.2 微服务下的接口自动化测试

接口测试属于集成测试范畴,是单元测试的扩展和延续。

接口测试的关注点是内部接口功能实现是否完整,逻辑是否正常,异常处理是否正确。它是单元测试和契约测试的过渡。

1.2.1 接口自动代测试要求

接口文档是接口测试案例设计的依据,接口文档的全面性和准确性决定了接口测试是否正确有效。因此要求接口文档及时、正确、全面。

接口用例设计要考虑全面,不漏测,也不重复测试。除了正常入参外,要考虑边界、异常、特殊值等。接口用例设计应进行评审

接口测试覆盖率应达到100%

需求或接口变更时,接口测试用例也同步变更

定时进行接口回归测试,回归通过率应达到100%

1.2.2 接口自动化测试工具

经过对常用接口自动化测试工具调研比较,我们采用了Python+Jmeter进行接口自动化测试。

经过Python开发和封装,进行接口测试案例编写时,不需要写代码,只需在EXCEL表中加入接口URL,参数,请求方式, 预期返回数据等。调EXCEL表即可进行接口自动化测试。

这样做的好处是:整个测试团队只需要一位开发型测试进行Python开发,其它人员只需要在excel中输入入参值和期望结果,即可进行接口自动化测试。

为方便与开发共享自动化测试代码,自动化测试案例可以导出为Jmeter自动化测试脚本。

1.2.3 KDOP/Jenkins部署自动化测试脚本,提交测试报告

自动化测试脚本不仅供测试使用,也会放在公共的环境下供大家一起使用。

可以将在KDOP/Jenkins上部署,定期自动化运行测试任务。

自动化接口测试报告以web页面方式展示,在Jenkins中,自动邮件发送。这样,通过自动化接口测试,接口的质量变动情况会定期可视化反馈。

1.3 基于消费者契约的API测试

微服务架构下,API测试的最大挑战来自于庞大的测试用例数量,以及微服务之间的相互耦合。我们采用基于消费者契约的方法来应对这两个难题。

微服务架构下,一个应用由很多相互独立的微服务组成,每个微服务都会对外暴露接口,同时这些微服务间存在级联调用关系,也就是一个微服务通常会去调用其它微服务。

在传统单体架构时代,API测试策略是根据被测API输入参数的各种组合调用API,并验证结果的正确性,测试目标是保证覆盖率达到既要求。

采用微服务架构时,原本的单体应用被拆分成多个独立的服务,每个服务对外暴露API接口,如果仍然采用传统API测试策略,测试用例数量会非常多,过多不必要的测试也会消耗大量测试资源

为了即保证API质量,又减少测试用例数量,采用消费者契约的API测试。其核心思想是:只测试那些真正被实际使用到的API调用,如果没被使用到,就不去测试。

对于基于 HTTP 的微服务来说,它的契约就是指 API 的请求和响应的规则。对于请求,包括请求URL,参数,请求头,请求内容等;对于响应,包括状态码,响应头,响应内容等。

1.4 微服务架构下的UI自动化测试

采用Python+selenium实现。

基于微服务架构的UI自动化测试分三步走,第一阶段先实现主要页面正常用例自动化,第二阶段实现主要页面异常处理自动化,第三阶段实现全面自动化。

同样,经过Python开发和封装,进行UI测试案例编也使用excel表整理用例,进行UI在EXCEL表中加入URI、path、输入值、返回位置、预期返回数据等。使用Python+Selenium调excel表,进行UI自动化测试。

自动化测试结果以图文形式输入,仍可集成到Jenkins。

1.5 微服务架构下的安全保证

1.5.1 需求、开发、测试、运维各阶段保证系统安全

微服务架构下,相对松散独立的服务,可能不同的部署方式等都有可能带来安全陷患,这就需要整个团队配合,在各个阶段保证安全

需求:要有明确的安全需求

设计和开发:进行安全设计、有安全开发规范

测试:进行安全扫描和渗透测试

运维:安全部署,避免在维护和更新过程中引入缺陷

1.5.2 常规安全问题与微服务下特有的安全问题

OWASP应用安全风险TOP10:

注入

失效的身份认证和会话管理

XSS(跨站脚本攻击)

不安全的对象直接引用

跨站请求伪造(CSRF)

安全配置错误

限制URL访问失败(缺少功能级访问控制)

未验证的重定向和转发

应用已知漏洞的组件

敏感信息暴露

微服务下,特有的安全问题:

未对用户登录凭证检查

缺少资源从属关系检查

缺少API速率限制

敏感信息泄露

1.5.3 安全扫描与渗透测试

安全测试采用自动化安全扫描工具扫描与人工渗透测试结合的方法。

安全扫描工具:

​ Appscan 安全扫描

渗透测试:

渗透测试是指测试人员模拟黑客,从可能存在的位置对系统进行攻击测试,在真正黑客入侵前找到安全漏洞并提交修复,从而达到保护系统安全的目的。

基于OWASP应用安全风险TOP10和微服务特有安全漏洞,总结出web环境常见的漏洞和测试方法,在渗透测试中,针对这些漏洞,使用不同的工具来完成测试。

比如,为保证数据库安全,针对sql注入攻击,使用sqlmap自动进行sql注入和数据库接入。

针对重放攻击,使用Burp Suite抓取请求数据包,在repeater中做重放测试,看服务器是否对重放的数据包做出反应。

不同的漏洞有不同的漏洞方法,这里不做详细叙述。

在对微服务架构下的安全测试,需要特别注意避免由于微服务而凸显的安全问题

1.6 持续测试

在DevOps实践中,采用小步快跑的交付模式,以持续集成和持续部署为基础来优化产品开发、测试、系统运维等环节。

DevOps强调将流程自动化,测试作为其中一个重要环节,势必要大规模实现自动化。

理想中的持续测试是全链路自动化测试,包括:

测试环境自动化部署

单元测试自动化

接口测试自动化

UI测试自动化

性能测试自动化

流水线与测试相关的部分实践中,通过工具实现各阶段自动化测试

如图中显示,这个过程任何一个环节有问题,就会报警并通知相关人员解决。

随着微服务技术发展,基于微服务架构的软件测试也面对新的挑战。文中只是在微服务测试上的初步实践与学习,希望在接下来的实践中,摸索出适宜于微服务架构的最佳测试实践。