单元测试编写

我对最近的博客“您应该测试什么”有很多React,有些人出于各种原因与我达成一致,另一些人则认为建议某些类可能不需要单元测试是完全危险的。 已经处理了什么测试,今天的博客涉及为什么要编写单元测试,而今天的示例代码是基于一个真实的故事:只有姓名,日期和事实已经改变。

一位客户最近请求紧急释放一些代码,以出于法律原因在其网站的相应页面上在屏幕上显示一条消息。

方案是,如果数据库中存在一条信息,则应在屏幕上显示该信息–这是一个非常简单的方案,可以通过几行简单的代码行就可以覆盖。 但是,在急于编写代码的过程中,开发人员没有编写任何单元测试,并且代码中包含一个直到补丁到达UAT才发现的错误。 您可能会问到错误是什么,这是我们在职业生涯中某个时候都已经完成的事情:添加不需要的分号';'。 到一行的结尾。

我将使用我以前的“测试技术”博客中使用的AddressService场景来演示代码的重新编写的特技双重版本,如下UML图所示:

在此演示中,功能已更改,但是逻辑和示例代码结构基本上保持不变。 在AddressService领域中 ,逻辑运行如下:

  1. 从数据库获取地址。
  2. 如果地址存在,则将其格式化并返回结果字符串。
  3. 如果地址不存在,则返回null。
  4. 如果格式化失败,请不要担心,并返回null。

重新编写的AddressService.findAddress(…)看起来像这样:

@Component
public class AddressService {private static final Logger logger = LoggerFactory.getLogger(AddressService.class);private AddressDao addressDao;public String findAddressText(int id) {logger.info("In Address Service with id: " + id);Address address = addressDao.findAddress(id);String formattedAddress = null;if (address != null);try {formattedAddress = address.format();} catch (AddressFormatException e) {// That's okay in this business case so ignore it}logger.info("Leaving Address Service with id: " + id);return formattedAddress;}@Autowired@Qualifier("addressDao")void setAddressDao(AddressDao addressDao) {this.addressDao = addressDao;}
}

您发现错误了吗? 当我查看代码时,我没有……为了以防万一,我在下面注释了一个屏幕截图:

演示一个琐碎的错误(任何人都可以犯的一个简单错误)的目的是强调编写一些单元测试的重要性,因为单元测试可以发现问题并节省大量的时间和费用。 当然,每个组织都不同,但是发布上面的代码会导致以下事件序列:

  • 该应用程序已部署到开发,测试和UAT。
  • 测试团队检查了修改后的屏幕是否可以正常工作并通过了更改。
  • 其他屏幕经过回归测试,发现不正确。 记录所有失败的屏幕。
  • 提出了紧急的错误报告。
  • 该报告通过各个管理级别。
  • 该报告已传递给我(我想念午餐),以调查可能的问题。
  • 该报告将发送给团队的其他三名成员进行调查(四双眼睛比一只更好)
  • 找到并修复了有问题的分号。
  • 该代码在dev中进行了重新测试,并签入到源代码管理中。
  • 该应用程序已构建并部署到开发,测试和UAT。
  • 测试团队检查修改后的屏幕是否可以正常工作并通过更改。
  • 其他屏幕经过回归测试并通过。
  • 紧急修复程序已通过。

上述一系列事件显然浪费了大量的工时,浪费了大量现金,不必要地增加了人们的压力水平,并破坏了我们在客户中的声誉: 所有这些都是编写单元测试的很好理由。

为了证明这一点,我编写了三个缺失的单元测试,只花了我额外的15分钟开发时间,与浪费的工时相比,这似乎是开发人员时间的一种很好的利用。

@RunWith(UnitilsJUnit4TestClassRunner.class)
public class WhyToTestAddressServiceTest {private AddressService instance;@Mockprivate AddressDao mockDao;@Mockprivate Address mockAddress;/*** @throws java.lang.Exception*/@Beforepublic void setUp() throws Exception {instance = new AddressService();instance.setAddressDao(mockDao);}/*** This test passes with the bug in the code* * Scenario: The Address object is found in the database and can return a* formatted address*/@Testpublic void testFindAddressText_Address_Found() throws AddressFormatException {final int id = 1;expect(mockDao.findAddress(id)).andReturn(mockAddress);expect(mockAddress.format()).andReturn("This is an address");replay();instance.findAddressText(id);verify();}/*** This test fails with the bug in the code* * Scenario: The Address Object is not found and the method returns null*/@Testpublic void testFindAddressText_Address_Not_Found() throws AddressFormatException {final int id = 1;expect(mockDao.findAddress(id)).andReturn(null);replay();instance.findAddressText(id);verify();}/*** This test passes with the bug in the code* * Scenario: The Address Object is found but the data is incomplete and so a* null is returned.*/@Testpublic void testFindAddressText_Address_Found_But_Cant_Format() throws AddressFormatException {final int id = 1;expect(mockDao.findAddress(id)).andReturn(mockAddress);expect(mockAddress.format()).andThrow(new AddressFormatException());replay();instance.findAddressText(id);verify();}
}

最后,冒着自鸣得意的风险,我不得不承认,尽管在这种情况下该错误不是我的,但在我学会编写单元测试之前,我过去曾将类似的错误发布到野外……
可从GitHub上获得源代码:

git://github.com/roghughe/captaindebug.git

参考: 为什么要编写单元测试–来自JCG合作伙伴 Roger Hughes的测试技巧8 ,在Captain Debug's Blog中 。

相关文章 :

  • 测试技巧–不编写测试
  • 端到端测试的滥用–测试技术2
  • 您应该对什么进行单元测试? –测试技术3
  • 常规单元测试和存根–测​​试技术4
  • 使用模拟的单元测试–测试技术5
  • 为旧版代码创建存根-测试技术6
  • 有关为旧版代码创建存根的更多信息–测试技术7
  • 一些定义–测试技术9

翻译自: https://www.javacodegeeks.com/2011/12/why-you-should-write-unit-tests-testing.html

单元测试编写

单元测试编写_为什么要编写单元测试-测试技巧8相关推荐

  1. 软件测试测试用例编写_不要先编写所有软件测试-只需编写一个

    软件测试测试用例编写 Test Driven Development (TDD) is sometimes described as "writing tests first". ...

  2. java单元测试内存数据库_基于内存数据库的单元测试

    背景: 当我们在进行单元测试时,对于关系型数据库(例如mysql)和非关系型数据库(例如redis)的处理,有的小伙伴通过mock的方式制作出假的数据进行测试,有的小伙伴会连到开发环境操作数据库.而连 ...

  3. java 单元测试 异步_使用Moq模拟单元测试的异步方法

    我正在测试一个用于进行Web API 调用的服务的方法 . 如果我还在本地运行Web服务(位于解决方案中的另一个项目中),则使用普通 HttpClient 可以正常进行单元测试 . 但是,当我签入我的 ...

  4. javascript编写_如何通过编写自己的Web开发框架来提高JavaScript技能

    javascript编写 Have you ever asked yourself how a framework works? 您是否曾经问过自己框架是如何工作的? When I discovere ...

  5. python学号怎么编写_用python编写学生管理系统

    #该程序在设计返回值时用了flag(标志)和i(标识下标): #之前在travers()函数的编写中for循环中缺少一个return导致在传递参数时会有错误: # 主要体现在修改和删除首个元素时!值得 ...

  6. python hello world程序编写_用Python编写一个简单程序

    按照软件行业传统习惯,当你学习一种新的编程语言如Python时,首先编写一个"Hello World! "程序. 请执行以下步骤,以创造你的"Hello World!&q ...

  7. pythonmacd指标编写_利用python编写macd、kdj、rsi、ma等指标 -

    # -*- coding: utf-8 -*- \ Created on Thu Dec 15 13:57:32 2016 @author: four \ import pandas as pd #获 ...

  8. 单元测试编写_编写详尽的单元测试

    单元测试编写 As software developers we all know how important it is to unit test the code that we write. S ...

  9. 为什么要编写单元测试–测试技巧8

    我对最近在"您应该测试什么"上的博客有很多反应,有些人出于各种原因同意我的想法,另一些人则认为建议某些类可能不需要单元测试是非常危险的. 已经处理了什么测试,今天的博客涉及为什么要 ...

最新文章

  1. nodejs 中间件 反向代理 接口转发
  2. 图灵奖得主Yann LeCun万字访谈:DNN“史前文明”、炼金术及新的寒冬
  3. SQL Server-聚焦NOT IN VS NOT EXISTS VS LEFT JOIN...IS NULL性能分析(十八)
  4. 以太网未识别的网络win10_工业以太网典型应用、常见故障、冗余网络技术及实例...
  5. ALV中调用Excel inplace时没能传递数据实例解决
  6. Appcan跨域交互
  7. android 动态label,Android仿抖音实现动态壁纸
  8. 终极之战!TensorFlow与PyTorch谁最适合深度学习
  9. vue-beauty UI库
  10. Java注解全面解析
  11. 精通SpringBoot---整合RabbitMQ消息队列
  12. 正则表达式学习笔记011--贪婪和懒惰的匹配
  13. java B2B2C Springboot电子商城系统-路由网关(zuul)
  14. python 回溯法 子集树模板 系列 —— 17、找零问题
  15. 关于eclipse中引入项目报错或者没有JRE System Library问题(jre报错)或者jre1.7(8)改为jre1.8(7)等问题...
  16. Android判断世界各国手机号码合法性
  17. TCP/IP五层模型
  18. 微信发红包案例测试场景
  19. 电脑插入耳机后没反应怎么办?
  20. Error opening data file Tesseract-OCR\tessdata/eng.traineddata问题 解决

热门文章

  1. java实现遍历树形菜单方法——OpenSessionView实现
  2. html画等边三角形,前台面试:使用CSS画一个等边三角形
  3. php 输出01,php基础01_thinkphp输出Hello World-Go语言中文社区
  4. idea无法启动Tomcat
  5. 最新开发android版本,Android版本检测升级
  6. Access restriction: The type 'BASE64Encoder' is not API 的解决方法
  7. Mybatis3(3)动态 SQL
  8. 大数据 java 代码示例_功能Java示例 第7部分–将失败也视为数据
  9. oracle连接外部数据库_使用Oracle验证外部数据
  10. 谷歌 recaptcha_在Spring Boot应用程序中使用Google reCaptcha