9

当我创建一个说类Employee的模拟对象时。它不调用 Employee 对象的构造函数。我知道内部 Mockito 使用 CGLIb 和反射,创建一个代理类,将类扩展为模拟。如果它不调用员工的构造函数,如何创建员工类的模拟实例?

4

2 回答 2

7

Mockito 使用 CGLib 生成类对象。但是要实例化这个类对象,它使用 Objenesis http://objenesis.org/tutorial.html

Objenesis 能够使用各种技术(即调用 ObjectStream.readObject 和类似方法)在没有构造函数的情况下实例化对象。

于 2011-01-17T15:38:41.777 回答
2

Mockito 使用反射和 CGLib 通过动态创建的超类来扩展 Employee 类。作为其中的一部分,它首先将 Employee 的所有构造函数公开 - 包括默认构造函数,如果您声明了一个带参数的构造函数,它仍然存在但私有。

public <T> T imposterise(final MethodInterceptor interceptor, Class<T> mockedType, Class<?>... ancillaryTypes) {
    try {
        setConstructorsAccessible(mockedType, true);
        Class<?> proxyClass = createProxyClass(mockedType, ancillaryTypes);
        return mockedType.cast(createProxy(proxyClass, interceptor));
    } finally {
        setConstructorsAccessible(mockedType, false);
    }
}

private void setConstructorsAccessible(Class<?> mockedType, boolean accessible) {
    for (Constructor<?> constructor : mockedType.getDeclaredConstructors()) {
        constructor.setAccessible(accessible);
    }
}

我假设它在创建超类时调用了默认构造函数,尽管我还没有测试过。您可以通过声明私有默认构造函数 Employee() 并在其中放入一些日志来自己测试它。

于 2010-06-30T13:00:52.293 回答