`

Jmockit 入门

阅读更多

在单元测试中,经常需要进行一些mock操作。现在已经有了一些比较不错的框架在做这些事情,比如:EasyMck,他在大多数情况下运行良好,但是对于某些结构的设计却显得无能为力。

EasyMock等众多的mock框架仅能mock一些public,non static or final的方法,在大多数情况下这并没有什么问题,他可以处理大多数的问题,但是当测试的代码包含了一些静态方法,可能就让问题变得难以解决,有一种选 择即是重构他(过多的静态方法可能预示着这并不是一个很好的设计),但是当你使用外部引用库所提供的方法,问题又该如何解决呢?

JMockit是一个能帮我们解决以上问题的轻量级框架,他允许你动态的改变已有的方法,这主要基于java 1.5的Instrumentation框架,这样便可以使得JMockit能够适应几乎所有的设计。他允许你重定义private,static and final方法,甚至是no-arg constructors都能够并轻易的重定义。

在实际的项目中有些方法可以重定义而有些不行,为了更好的说明如何对方法进行重定义,下面有一个简单的类和对应测试代码的demo,他尽可能考虑到了几乎所有的情况,供大家方便的学习。(理解不透的地方,希望大家指正)

package jmockit;

public class ClassToMock {
	private String memberToSet = "";
    private static String staticMember;
    
    static {
        staticMember = "Static initialized";
    }
    
    public ClassToMock() {
        this.memberToSet = "Member set by original constructor";
    }
    public ClassToMock(String value){
    	this.memberToSet = value;
    }
    public String publicMethod() {
            return "Original public method";
    }
    protected String protectedMethod() {
            return "Original protected method";
    }
    String defaultMethod() {
            return "Original default method";
    }
    public String methodThatUsesPrivateMethod() {
            return privateMethod();
    }
    private String privateMethod() {
            return "Original private method";
    }
    public String getMemberToSet() {
            return memberToSet;
    }
    public String getStaticMember() {
            return staticMember;
    }
}

 
package jmockit;

import static org.junit.Assert.assertEquals;
import mockit.Mockit;

import org.junit.Before;
import org.junit.Test;

public class ClassToMockTest {

private ClassToMock mockedClass;

public static class Replacement {

static {
}

public Replacement() {
}

public Replacement(String test) {
}

public String publicMethod() {
return "Replaced public method";
}

public String protectedMethod() {
return "Replaced protected method";
}

public String defaultMethod() {
return "Replaced default method";
}

public String privateMethod() {
return "Replaced private method";
}
}

@Before
public void setUp() throws Exception {
Mockit.redefineMethods(ClassToMock.class, Replacement.class);
mockedClass = new ClassToMock("test");
}

protected void tearDown() throws Exception {
Mockit.restoreAllOriginalDefinitions();
}

/**
* Public methods can be replaced
*/
@Test
public void testReplacePublic() {
assertEquals("Replaced public method", mockedClass.publicMethod());
}

/**
* Protected methods can be replaced.
* The replacement method should be declared public however
*/
@Test
public void testReplaceProtected() {
assertEquals("Replaced protected method", mockedClass.protectedMethod());
}

/**
* Package accessable methods can be replaced
* The replacement method should be declared public however
*/
@Test
public void testReplaceDefault() {
assertEquals("Replaced default method", mockedClass.defaultMethod());
}

/**
* Private methods can be replaced
* The replacement method should be declared public however
*/
@Test
public void testReplacePrivate() {
assertEquals("Replaced private method", mockedClass
.methodThatUsesPrivateMethod());
}

/**
* Non-default constructors can be replaced
* Your mock definition must have a default constructor however
*/
@Test
public void testReplaceConstructor() {
assertEquals(null, mockedClass.getMemberToSet());
}

/**
* Default constructors <b>can't</b> be replaced
*/
@Test
public void testReplaceDefaultConstructor() {
mockedClass = new ClassToMock();
assertEquals("Member set by original constructor", mockedClass
.getMemberToSet());
}
/**
* Static initializers <b>can't</b> be replaced
*/
@Test
public void testReplaceStaticBlock() {
assertEquals("Static initialized", mockedClass.getStaticMember());
}
}
 注意要导包。
 官方文档:https://jmockit.dev.java.net/tutorial.html
分享到:
评论
7 楼 solviv 2010-08-24  
疯狂的草儿 写道
solviv 写道
大哥,使用你的方式进行了测试,可能使用的版本不正确,总是提示确认JVM是否已经启动:
Caused by: java.lang.IllegalStateException: JMockit has not been initialized. Check that your Java 5 VM has been started with the -javaagent:D:\jmockit\lib\jmockit.jar command line option.

jmockit的jar包路径是没有问题的,通过命令行执行的时候总是提示类未定义:
Caused by: java.lang.ClassNotFoundException: junit.framework.TestSuite
这几个类都是可以找到的,我使用的junit-4.8.2.jar.

在IDE中配置了jvm参数后执行提示:
java.lang.VerifyError: (class: org/junit/runner/notification/RunNotifier, method: addFirstListener signature: (Lorg/junit/runner/notification/RunListener;)V) Illegal constant pool index
这个错误google了好久没找到解决办法.

而且jmockit更新为最新版本的jar包以后,示例中提到的方法已经没有了,学习了下,还没头绪,不知道你使用过程中是否有遇到类似问题,还请指教下,谢谢.



我这边有jmockit的jar包,你下载一下。
我的MyEclipse7.0 我的junit版本是4.4.5的
这个例子已经是好久的了 我刚开始用的时候就是采用这个列子的
现在也几乎不这样用了
直接用 @Mocked 去注解你要mock的对象,然后再在 new Expectations中去 指定mock的方法和返回值 等等


OK,搞定.环境更新后(jdk1.6,junit4.7,jmockit-0.999.1),按你的方式处理,可以正常对静态方法进行替换了.
之前不太确定是否jdk版本的问题,有空再研究下,多谢了!
6 楼 疯狂的草儿 2010-08-24  
solviv 写道
大哥,使用你的方式进行了测试,可能使用的版本不正确,总是提示确认JVM是否已经启动:
Caused by: java.lang.IllegalStateException: JMockit has not been initialized. Check that your Java 5 VM has been started with the -javaagent:D:\jmockit\lib\jmockit.jar command line option.

jmockit的jar包路径是没有问题的,通过命令行执行的时候总是提示类未定义:
Caused by: java.lang.ClassNotFoundException: junit.framework.TestSuite
这几个类都是可以找到的,我使用的junit-4.8.2.jar.

在IDE中配置了jvm参数后执行提示:
java.lang.VerifyError: (class: org/junit/runner/notification/RunNotifier, method: addFirstListener signature: (Lorg/junit/runner/notification/RunListener;)V) Illegal constant pool index
这个错误google了好久没找到解决办法.

而且jmockit更新为最新版本的jar包以后,示例中提到的方法已经没有了,学习了下,还没头绪,不知道你使用过程中是否有遇到类似问题,还请指教下,谢谢.



我这边有jmockit的jar包,你下载一下。
我的MyEclipse7.0 我的junit版本是4.4.5的
这个例子已经是好久的了 我刚开始用的时候就是采用这个列子的
现在也几乎不这样用了
直接用 @Mocked 去注解你要mock的对象,然后再在 new Expectations中去 指定mock的方法和返回值 等等
5 楼 solviv 2010-08-23  
大哥,使用你的方式进行了测试,可能使用的版本不正确,总是提示确认JVM是否已经启动:
Caused by: java.lang.IllegalStateException: JMockit has not been initialized. Check that your Java 5 VM has been started with the -javaagent:D:\jmockit\lib\jmockit.jar command line option.

jmockit的jar包路径是没有问题的,通过命令行执行的时候总是提示类未定义:
Caused by: java.lang.ClassNotFoundException: junit.framework.TestSuite
这几个类都是可以找到的,我使用的junit-4.8.2.jar.

在IDE中配置了jvm参数后执行提示:
java.lang.VerifyError: (class: org/junit/runner/notification/RunNotifier, method: addFirstListener signature: (Lorg/junit/runner/notification/RunListener;)V) Illegal constant pool index
这个错误google了好久没找到解决办法.

而且jmockit更新为最新版本的jar包以后,示例中提到的方法已经没有了,学习了下,还没头绪,不知道你使用过程中是否有遇到类似问题,还请指教下,谢谢.


4 楼 疯狂的草儿 2010-08-13  
rocket 写道
不错,其实jmockit最强的是对静态方法和构造函数的模拟,直接改jvm启动时候的classloader。楼主有没有时间把jmockit的所有用法出个手册出来,我一直想做,没有时间搞啊,或者我们两个一起做一个manual来方便大家

Good idear.My qq is 55652199.
但是jmockit的官方资料实在不全,并且上面的例子 也十分复杂。
我做单元测试用的最多的也就是
new NonExpectations(){{}};.....
希望可以合作。
3 楼 rocket 2010-08-12  
不错,其实jmockit最强的是对静态方法和构造函数的模拟,直接改jvm启动时候的classloader。楼主有没有时间把jmockit的所有用法出个手册出来,我一直想做,没有时间搞啊,或者我们两个一起做一个manual来方便大家
2 楼 疯狂的草儿 2010-06-07  
不会的啊 报的什么错

是不是环境没有搭建好
导包的时候 先导junit 再导 jmockit
1 楼 airpeng 2010-06-02  
怎么跑不起来啊??

相关推荐

    jmockit jmockit jmockit jmockit

    JMockit是一款强大的Java测试工具,它主要用于模拟和测试Java代码中的依赖,特别是在进行单元测试时。这款开源库使得开发者可以更容易地创建测试桩(stubs)和模拟对象(mocks),无需修改被测试代码,甚至在无法...

    jmockit

    JMockit是一个流行的Java测试工具,它主要用于模拟和断言对象的行为,特别是在进行单元测试时。这个工具使得开发者能够在不修改源代码的情况下,对复杂的依赖关系进行模拟,从而简化测试过程。下面将详细介绍JMockit...

    JMockit教程.pdf

    开源社区有许多优秀的Java单元测试框架,JMockit是其中之一。正如其名,在单元测试时,CUT(Code Under Test ,被测试代码)可能会依赖其他代码,可以使用JMockit API来mock被依赖的代码,从而进行隔离测试。 ...

    jmockit-1.6.zip

    《JMockit 1.6:提升JUnit测试的利器》 在软件开发过程中,单元测试是一种重要的质量保证手段,它能够帮助我们确保代码的正确性和稳定性。JUnit作为Java领域广泛使用的单元测试框架,极大地简化了测试工作。然而,...

    jmockit官网文档整理

    **JMockit官方文档整理** JMockit是一个强大的Java测试框架,它允许开发者在单元测试中模拟复杂的系统行为,包括静态方法、构造函数、final类和方法,甚至平台依赖的API。这个框架使得测试变得更加灵活,能更好地...

    jmockit\jmockit-0.999.2.jar

    jmockit-0.999.2.jar

    jmockit总结

    JMockit 是一款 Java 语言的测试框架,主要用于模拟(mocking)和验证对象的行为,以便在单元测试中隔离被测试代码。它支持行为和状态的测试,这使得测试更加灵活和全面。以下是对 JMockit 的关键知识点的详细解释:...

    jmockit-例子和jar.rar

    《JMockit:一个强大的Java测试工具》 在软件开发领域,测试是不可或缺的一部分,它确保了代码的质量和稳定性。JMockit是一个优秀的Java库,专门用于进行单元测试和模拟对象,尤其在处理复杂的依赖关系时表现突出。...

    jmockit-1.7.jar

    jmockit-1.7.jar JMockit最新工具包

    jmockit-coverage

    《JMockit Coverage:深入解析单元测试覆盖率工具》 在软件开发过程中,单元测试是确保代码质量的关键步骤。而衡量单元测试覆盖率则是评估测试完善度的重要指标。JMockit Coverage,作为一款强大的Java测试覆盖率...

    jmockit中文教程

    ### jmockit中文教程 #### 简介 JMockit是一款用于Java应用程序的高级单元测试框架,它提供了丰富的API来帮助开发者创建高质量的单元测试。JMockit的核心能力在于其能够模拟(Mock)和伪装(Stub)Java类中的方法...

    JMockit教程.zip

    JMockit是一款强大的Java测试工具,它允许开发者在单元测试中模拟任何Java代码,包括静态方法、构造器、final类和方法以及系统类。这款工具的出现极大地简化了Java应用程序的测试过程,尤其是对于那些难以测试或者有...

    2020-11-15 JMockit中文网在github上的示例代码|jmockit_cn.zip

    JMockit是一款强大的Java测试工具,它允许开发者模拟和验证对象的行为,特别是在进行单元测试时。这个"2020-11-15 JMockit中文网在github上的示例代码"压缩包包含了JMockit相关的示例代码,旨在帮助初学者更好地理解...

    JMockit基础教程

    **JMockit基础教程** JMockit是一款强大的Java单元测试框架,它允许开发者模拟复杂的依赖关系,以便在测试中隔离代码。本教程将详细介绍JMockit的基础知识,包括录制期望、执行测试和验证结果。 ### **录制期望** ...

    jmockit使用例子

    JMockit是一款强大的Java测试工具,它允许开发者在单元测试中模拟任何类或接口的行为,包括静态方法和构造函数。这个“jmockit使用例子”很可能会涵盖如何利用JMockit进行测试的基本步骤,以及如何改变静态方法的...

    jmockit-1.2

    **JMockit 1.2:一款强大的Java测试工具** JMockit是一款广泛使用的Java单元测试框架,尤其在模拟和mocking对象方面表现卓越。它提供了简洁、灵活且高效的API,使得开发者能够在测试代码中轻松地模拟任何Java类或...

    Jmockit用法示例

    **Jmockit详解:单元测试中的模拟神器** Jmockit是一款强大的Java库,主要用于单元测试,尤其是模拟(mocking)和验证(verifying)对象的行为。它提供了灵活且易于使用的API,使得测试复杂的代码变得更加简单,...

    jmockit测试例子

    Mockup always comes to us when we try to ... Now, jmockit comes to us. "Tests can easily be written that will mock final classes, static methods, constructors, and so on. There are no limitations.

    jmockit框架所使用jar包

    jmockit框架所使用jar包,在写单元测试的过程中我们会发现需要测试的类有很多依赖,这些依赖的类或者资源又会有依赖,导致在单元测试代码里无法完成构建,我们应对的方法是Mock。简单的说就是模拟这些需要构建的类...

    jmockit jar包

    jmockit jar包

Global site tag (gtag.js) - Google Analytics