前言
小编在的项目组中因为对接第三方服务特别多,系统逻辑也比较复杂,很多场景难以构造,影响到了自动化测试的进度和覆盖率。在做接口自动化的时候就遇到了以下3个问题:
1. 第三方系统不稳定,返回数据不满足自动化case需求;
2. 某些依赖的接口、方法还未开发完成,但需要提前准备自动化case;
3. 有些场景不易模仿、构造代价较高(如: 访问频次限制、重要数据删除等);
解决方法调研
后来小编调研发现了unittest库中集成的mock模块。应用后发现可以有效提高组内接口自动化的测试效率和测试覆盖率。
在Python 2的时候,mock还是单独的一个库,需要用pip去安装。到了Python 3,mock模块已经被整合到了unittest中,不再需要单独安装了,在unittest中就能找到mock.py。
下面小编以两个场景为例,讲一下怎么用mock去模拟接口返回做自动化,怎样用mock思维覆盖难以构造的测试场景。
01
场景一
接口/方法还未开发完成,或者某个接口/方法依赖的第三方服务无法正常使用,这时候就没办法用传统流程提前准备自动化case,也没办法后期对这类接口进行自动化验证了。
例如,有个接口/removeData,这里为了演示先准备了一个发送请求的函数。
代码语言:javascript复制def sendRequest():
# 接口为伪接口,无法访问
url = "http://127.0.0.1/removeData"
return requests.get(url=url)
直接调用发送请求访问接口是会报错的,无法访问。
代码语言:javascript复制response = sendRequest()
print(response)
此时如果想提前准备case,就可以用到unittest.mock。
代码语言:javascript复制sendRequest = Mock(return_value={"code": 0, "msg": "删除成功"})
response = sendRequest()
print(response)
再次执行就有期望的返回结果了。
然后再设计自动化的case就可以了。另外unittest.mock也支持构造异常情况。
代码语言:javascript复制sendRequest = Mock(side_effect=AssertionError('系统错误'))
response = sendRequest()
print(response)
如上,就通过side_effect参数和AssertionError异常类构造了一个“系统异常”的场景。
02
场景二
某些功能在自动化过程中难以模拟/执行成本过高,如访问频次限制、重要数据删除等,下面以一个删除C盘目录的方法为例。
代码语言:javascript复制def remove_dir(self, path="c:/"):
try:
shutil.rmtree(path)
return 'success'
except IOError:
return 'error'
return 'fail'
如果每次跑自动化case都去清空C盘目录,这个代价太大了。这时候就可以通过mock,来把这个方法替代掉。
代码语言:javascript复制a = remove()
# 通过mock替换该方法
a.remove_dir = Mock(return_value='success')
print(a.remove_dir())
03
写在最后
mock思想对于测试来说是十分重要的,通过mock实践能够达到并行工作、模拟那些无法访问的资源、构造异常场景、提升测试覆盖率等目的。小编这里只介绍了unittest中的mock模块的入门用法,更多花式用法可以阅读官方文档,落地到项目的自动化测试中进行使用。
另外,除了本文中unittest中的mock模块,还有很多mock落地的工具、平台值得学习&结合项目使用。例如easymock、api-mocker等mock平台,Mockito、jMock等单元测试mock工具。
官方文档地址:
https://docs.python.org/3/library/unittest.mock.html