- 浏览: 210219 次
最新评论
-
jin8000608172:
Profiler类是自己写的还是开源jar里面的,如果是开源j ...
isInfoEnabled究竟多有用? -
u011358822:
www.baidu.com
实战Concurrent -
u011358822:
[url][img][list][*]引用[/list][/i ...
实战Concurrent -
water_lang:
这本书我买了一本,但是我还是没找到该怎么解决事务这块,mong ...
《MongoDB实战》译者序 -
DREAM_UTOPIA:
每周推荐非常好,观点独到,涉及面广,谢谢
每周推荐阅读2013Q2汇总
在SOA环境中,系统不可避免地要与其他系统进行交互,可以是基于SOAP的Web服务,基于RESTful Web服务,基于消息队列,甚至是基于RPC远程调用。随着系统依赖的增长,对单个系统进行测试也变得越来越困难,如何有效地隔离各个系统,对系统进行单独的测试呢?
本文会给大家介绍一个简单的测试方法——基于Mock进行测试 !
开发过程中常用的测试有单元测试与集成测试,下面也分成两部分来做说明。
一、单元测试中的Mock
单元测试本身就要求将被测试类与它的依赖隔离开来,仅测试被测类本身的逻辑,此时可以选择一些Mock工具对接口进行模拟。是否进行了合理的设计也会影响单元测试的编写,例如,应该遵循“面向接口编程 ”的最佳实践。
Java中常用的Mock框架包括:
- jMock(http://www.jmock.org/ )
- EasyMock(http://www.easymock.org/ )
- mockito(http://mockito.org/
)
可以根据个人喜好选择一个合适的框架。本文以jMock为例,进行说明。Web服务的接口定义如下:
package mock.sample; /** * 用作范例的接口 */ public interface SampleService { String operate(String str); }
项目代码Operator类中引用了该服务,需要取得返回值进行后续操作。
package mock.sample; /** * SampleService的调用类 */ public class Operator { private SampleService sampleService; /** * 调用sampleService * 1、如果返回值result长度小于等于5,返回str+result * 2、如果返回值result长度大于5,返回result */ public String operate(String str) { String result = sampleService.operate(str); if (result != null && result.length() <= 5) { result = str + result; } return result; } public void setSampleService(SampleService sampleService) { this.sampleService = sampleService; } }
在编写单元测试时,为SampleService模拟一个对象注入Operator。关于jMock的使用,请参考jMock的《Getting Started 》或者《Cheat Sheet 》。jMock主要是使用录制-回放 的方式,通过预先设定期望的输入与输出实现Mock。
package mock.sample; import static org.junit.Assert.assertEquals; import org.jmock.Expectations; import org.jmock.Mockery; import org.jmock.integration.junit4.JMock; import org.jmock.integration.junit4.JUnit4Mockery; import org.junit.Test; import org.junit.runner.RunWith; @RunWith(JMock.class) public class OperatorTest { private Mockery context = new JUnit4Mockery(); @Test public void testOperate() { Operator operator = new Operator(); final SampleService sampleService = context.mock(SampleService.class); operator.setSampleService(sampleService); context.checking(new Expectations() { { oneOf(sampleService).operate("hi"); will(returnValue("HelloWorld!")); oneOf(sampleService).operate("hello"); will(returnValue("world")); } }); assertEquals("HelloWorld!", operator.operate("hi")); assertEquals("helloworld", operator.operate("hello")); } }
单元测试中直接通过编码的途径用jMock模拟了外部系统的逻辑,业务代码并不关注究竟是调用了真是的Web服务,还是Mock对象。同样的,对于DAO等依赖也可以使用同样的方式进行模拟。
二、集成测试中的Mock
集成测试时同样可以通过编程的方式实现Mock,比如在Spring上下文中加载Mock的Bean而非通过XFire(或其他Web服务框架)引入的客户端。但这种做法未免过于繁琐,而且在希望改变Mock类返回结果时,可能需要修改代码重新编译发布。更有甚者,上线时如果忘记从测试的配置换回生产配置,就会出大问题。
当然,你可以选择部署一台真实的服务提供方,但有时出于种种原因,这并不是一个很好的选择。
相信在测试Web服务时,不少人都是用过soapUI ,但仅限于使用soapUI调用Web服务,其实强大的soapUI还可以Mock服务,根据事先的配置(Groovy脚本、XPath匹配、顺序、随机等方法)返回不同的结果。其实现原理简单地说就是根据给定的WSDL模拟Web服务,接受请求后根据配置解析请求,随后返回预先设定的结果,这里的请求和响应都是标准的SOAP报文。
简单实现步骤如下:
- 创建一个新的soapUI项目,在“New soapUI Project”对话框中输入WSDL地址,随后选中“Create MockService”。
- 在“Generate MockService”对话框中选中要模拟的操作,Path和Port尽量和真实的目标服务器保持一致。例如,发布WSDL的路径可能是http://xxx:8080/services/sampleService?wsdl,那么Path就是/services/cardInfoService,Port为8080。
- 编辑应答SOAP报文及返回逻辑。
在MockService的各个方法上点右键可以进入MockOperation Editor或者直接创建新的MockResponse。MockService创建时,每个操作都会有个Response,没有设定规则时,这就是默认应答。
可以仅使用一个Response,多次调用需要不同结果时手工修改,但这样一点都不“自动化”,可以通过soapUI的分派机制自动根据规则返回对应结果。
soapUI支持的分派机制(详见MockOperations and Responses )有:
- SCRIPT,使用Groovy脚本。
- SEQUENCE,按照MockResponse添加的顺序逐个返回。
- QUERY-MATCH,基于请求内容选择合适的结果返回。可以指定XPath路径及该节点的期望值,如果匹配的话返回对应Response。
- XPATH,与QUERY-MATCH类似,XPath节点的值就是要返回的MockResponse的名字。
- RAMDOM,随机返回。
个人认为XPATH和QUERY-MATCH这两种分派机制在复杂情况下比较好用,如果再复杂,可以考虑SCRIPT。以XPATH为例,假设请求报文如下:
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:fac="http://sample.mock.SampleService"> <soapenv:Header/> <soapenv:Body> <fac:operate> <fac:in0>hi</fac:in0> </fac:operate> </soapenv:Body> </soapenv:Envelope>
可以设置两个MockResponse,名字分别为“hi”和“hello”,在编辑器中选择“XPATH” ,设置如下XPATH:
declare namespace fac='http://sample.mock.SampleService' //fac:in0
当//fac:in0的值是“hi”时就会返回名为“hi”的MockResponse。“hi”MockResponse内容:
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:fac="http://sample.mock.SampleService"> <soapenv:Header/> <soapenv:Body> <fac:operate> <fac:out>HelloWorld!</fac:out> </fac:operate> </soapenv:Body> </soapenv:Envelope>
如果使用QUERY_MATCH,除了填写XPath,还要再填写“Expacted Value”,比如“hi”或者“hello”,然后“Dispatch to”中选择合适的MockResponse。
在项目中只需要把Web服务的Endpoint地址做成可配置的,就可以方便地调整测试与生产环境的Endpoint,实现Mock与真实服务器的切换。
使用Mock可以大大降低测试的成本,工欲善其事必先利其器,选择一个合适的Mock工具,可以帮助你更好的进行测试。So,行动吧~
发表评论
-
那些你该了解的Spring子项目
2013-03-20 14:39 1421去年年底,Spring Framework正式发布了3.2G ... -
《实战HotSpot JVM GC》分享Slides
2012-06-22 12:09 1718前阵子在QClub上海站做了一个与JVM GC优化相关的分享, ... -
代码中的坏味道
2011-01-07 04:09 1365最近InfoQ上连载了郑烨 ... -
isInfoEnabled究竟多有用?
2010-06-28 15:08 14489前段时间,公司里组织了一次代码检查,其中有一条检查项让我有些费 ... -
一个关于基于注解的Spring MVC的简单介绍
2009-05-26 17:52 2853前段时间给同事们做了一个关于Spring MVC的分享,简单介 ... -
实战Concurrent
2009-04-08 13:51 3894编写多线程的程序一直都是一件比较麻烦的事情,要考虑很多事情,处 ... -
关于表单防重复提交一些东东
2009-03-13 22:27 2329前阵子弄了些表单防重复提交的东西,想整理整理,免得下次要用时再 ... -
Eclipse对JDK说“不”了
2008-09-30 21:21 1956最近开始翻译Spring Recipes了,既然是讲Sprin ... -
自己写的第一段AOP代码。
2005-04-13 22:36 1572代码1:使用安全的rand() ... -
FIFO、LRU、OPT的三个简单实现
2005-04-28 16:11 31911.利用随机数产生一个指令序列,共320条指令。其地址按下述原 ... -
JMeter小实验——JSP性能简单测试
2006-04-17 16:56 2448首先要做的当然是到Apache的站点下在一个最 ... -
利用缓存提高小型站点性能
2006-04-23 16:11 1215最近结束了 ... -
都是JDBC-ODBC惹得祸
2006-09-23 11:23 1165前阵子的一个项目需要 ... -
Fedora下瞎折腾了一个半小时,还是Sun的虚拟机可靠
2007-03-23 22:00 1194今天早上跑去了网络学院做技术支持, 他们碰到的问题是一个web ... -
一个泛型Hibernate DAO实现
2007-08-06 11:58 1720自己四处参考,写写抄抄折腾出来的一个泛型Hibernate D ... -
自己出的几道关于Spring和Hibernate的面试题
2008-02-29 16:49 2483很简单的题目,随便出着玩的,如果你是高手就请直接跳过,若有雷同 ... -
Spring MVC快速上手教程
2008-04-01 22:00 3055Spring Framework可以被使用在很多场合之中,考虑 ... -
一些关于Liferay的使用心得
2008-01-07 15:58 2141Liferay是一个出色的Java开源Portal产品,其中整 ...
相关推荐
简单的使用ServerSocket模拟下,Tomcatweb服务器。
java ServerSocket 实现的简单web服务器 参考http://blog.csdn.net/hzaccp3/article/details/12589651
通过完成端口简单模拟webservice的收发原理
Mockaccino 是一个简单 Node(和 Express.js) 服务器,可以快速模拟 Web 服务响应。示例代码:{ ... "queryStringParam": "tc", "mockResponses": { "default": { "/test1": { /* behaviour...
模拟简单的网上购物的过程,使用到了web服务,客户端来调用其中的方法
简单的模拟Web服务 简单模拟Web服务(SimpleMock)提供RESTful Web服务,用于模拟目的,可在使用AJAX调用的任何JavaScript框架中使用。 背景 SimpleMock最初受管理的启发, 通过使用node.js提供了用于模拟Web服务的...
将socket封装,模拟简易web服务器。
也可以下载fiddler工具进行更全面的模拟测试! 1、支持GET/POST方法 2、支持CGI 3、支持错误返回 4、支持chunked数据的解析 缺点: 1、支持的方法不够全面 2、CGI实现不够科学,可以尝试使用FASTCGI 3、不支持https...
(牛客网C++课程)Linux 高并发Web服务器项目实战(带定时检测代码) 技术框架: 1. 线程池 + 非阻塞 socket + epoll + 事件处理的并发模型 2. 状态机解析HTTP请求 3. 心跳机制 4. 简易日志系统 主要内容: 1. ...
主要目标是更有效地模拟Web服务器的功能。 依赖项/库的使用: 我使用的库是以下库: import socket import request import Thread 运行与调试 Web服务器 要调试/运行Web服务器,请按照以下步骤操作: 1º-运行...
该系统主要实现了模拟在线考试功能,其使用方法如下 软件安装 1、 安装Oracle9.0.2 (1) 创建数据库: 操作方法:根据提示安装,一般的步骤点击下一步即可,在创建数据库时输入数据库名称,例如dbhouse; (2) ...
WebService Mock是用于模拟WebServices的非常简单但功能强大的工具。 为什么要使用WebService模拟? 通过非侵入性方式实现模拟,甚至无需编写任何代码行,这意味着无需模拟服务存根。 可以用于对应用程序进行压力...
计算机二级《Web程序设计》模拟及答案 2016计算机二级《Web程序设计》模拟及答案 1、当前主要的WEB数据库访问技术有哪些? 答:到目前为止,WEB数据库访问技术主要分为两大类: (1)公共网关接口技术(CGI); CGI是WEB...
被广泛应用的是针对Web服务的那些工具。然而,这些工具中有许多只是简单的HTML/SOAP生成器,它们模拟许多客户机连接,并因此对Web服务器生成高负载。这些工具对基本的压力测试比较有用,但它们经常是仅仅扩展功能...
java web模拟的简单的一个网络硬盘 上传下载
鹦鹉模拟网该项目提供了一个简单的模拟服务器,可与Chrome插件。 支持: 将页面(xhr / jsonp / fetch)的请求转发到真实的Web服务器,或者只是模拟列出所有转发的请求配置不同请求的模拟规则不支持: Cookie敏感...
根据作物生长发育模型特点,提出了计算机模拟系统的结构设计方案,并采用ASP.NET技术规范和Visual C#程序语言,初步实现了一个基于Web技术远程调用的温室作物生长发育计算机模拟系统,该系统目前可对番茄和黄瓜等...
计算机网络原理\实验\WebServer.java,一个重要的web服务器程序,模拟web服务器的编程。
如果你在构造一个为大量用户服务的应用,搞清楚你的产品配置能够承受多大的负载非常重要。如果你在构造一个小型的Intranet网站,测试能够暴露出最终会导致服务器崩溃的内存漏洞以及竞争情况。 无论是哪种情形,花些...
客户端文件续传上传到服务端,客户端http协议上传文件,客户端webserver上传文件,客户端续传,分割上传到服务器,模拟百度网盘文件上传 由于项目的需要一个客户端用来上传文件的,所以今天做了一个简单的例子