区别就体现在:测什么、为什么测、谁来测、何时测、怎么搭环境。
按从内到外的流水线顺序:
第一步:单元测试
测什么:代码里最小的单元,一个函数、一个类、一个方法。
为什么测:保证写的每一行代码(特别是if-else边界、循环临界值)在数学上绝对正确。
谁来测:开发自己(写这段代码的程序员)。这是自保行为,不改完不提交代码。
何时测:编码阶段,鼠标右键点一下运行测试就能跑。
环境怎么搭:不连数据库、不调别人的接口、不写磁盘。所有外部的依赖(比如调第三方支付接口),全部用Mock(模拟替身)顶替。只关心:输入参数A,是不是返回了预期的结果B。
第二步:集成测试
测什么:模块和模块之间的接口,以及数据从一个模块传到另一个模块时有没有水土不服。
为什么测:单元测试都过了,但A模块把字符串123传给B模块,B模块当整型123去算加法,结果直接崩了-集成测试专门抓这种接口协议不一致的Bug。
谁来测:一般是开发主导,或者懂代码底层的灰盒测试人员。
何时测:多个单元模块编译在一起之后,系统测试之前。
环境怎么搭:数据库要用真实测试库(不能Mock内存库了),因为要看SQL语句执行是不是报错;但跨系统的第三方服务(如短信网关)依然可以用Mock,因为这里只重视内部衔接是不是通畅。
第三步:系统测试
测什么:整个软件包安装好后,端到端的全部功能、性能、安全、UI界面。
为什么测:不看代码,只看业务需求。用户点注册到底能不能收到短信?1000个人同时下单服务器会不会卡死?
谁来测:专职测试团队QA。他们不管代码怎么写的,只按鼠标模拟用户操作。
何时测:集成测试通过后,准备上线给用户之前。
环境怎么搭:硬件、网络带宽、数据库主从备份、第三方真实接口,都尽量跟生产环境一模一样。基本不用Mock,全是真实调用。
关于为什么系统测试不能取代集成测试?
因为视角不同。系统测试看到的是页面报错500,但为什么报500?是因为数据库字段超长?还是因为Redis连接超时?系统测试只知道结果挂了,而集成测试能准确定位到哪两个模块之间的数据线断了。两者是上下游关系,谁也替不了谁。
关于修复成本的断崖式差距。
一定要记住这个1-10-100法则:单元测试发现一个Bug,程序员当场改,成本是1分钟;集成测试发现这个Bug(因为要排查链路),成本是10分钟;要是等系统测试甚至上线后用户发现这个Bug,开发要倒查日志、还原数据、紧急发补丁,成本就是100分钟甚至1天。这也是为什么大厂现在疯狂强调单元测试包括率必须达标-越左移,越省钱。
如果是刚入行的开发建议是:把单元测试当成说明书来写。当发现一个复杂函数很难写单元测试需要Mock一大堆东西,那大概率是你的函数设计得过于臃肿了,这时候重构设计比硬着头皮写测试更重要。