Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/389.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/unit-testing/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java Mock ClassLoader.getSystemClassLoader().loadClass与Powermockito_Java_Unit Testing_Powermockito - Fatal编程技术网

Java Mock ClassLoader.getSystemClassLoader().loadClass与Powermockito

Java Mock ClassLoader.getSystemClassLoader().loadClass与Powermockito,java,unit-testing,powermockito,Java,Unit Testing,Powermockito,我正在尝试测试一个实用方法,该方法检查特定类是否在类路径上,如果是返回trueelse返回false 我这样做的原因:我必须创建扩展同一个类的独立类,并且其中只有一个在类路径上。如果类路径上有一个特定的对象,则需要执行特定的操作 使用下面的方法检查特定类是否在类路径上。 此检查仅在第一次请求后执行一次。 我也检查了Class.forName(),但决定采用下面的方法 我的实用方法如下所示: public static boolean isMyClassOnClassPath() { tr

我正在尝试测试一个实用方法,该方法检查特定类是否在类路径上,如果是
返回true
else
返回false

我这样做的原因:我必须创建扩展同一个类的独立类,并且其中只有一个在类路径上。如果类路径上有一个特定的对象,则需要执行特定的操作

使用下面的方法检查特定类是否在类路径上。 此检查仅在第一次请求后执行一次。 我也检查了
Class.forName()
,但决定采用下面的方法

我的实用方法如下所示:

public static boolean isMyClassOnClassPath() {
    try {
        ClassLoader.getSystemClassLoader().loadClass("com.MyClass");
        return true;
    } catch (ClassNotFoundException ex) {
        return false;
    }
}

检查
false
条件很容易,因为特定类不是类路径。 我正试图为正面场景编写
Junit
,此时此方法将返回
true

@Test
public void isMyClassOnClassPathShouldReturnTrueWhenMyClassIsOnClassPath() throws Exception{
    PowerMockito.mockStatic(MyClass.class);
    ClassLoader classLoader = PowerMockito.mock(ClassLoader.class);
    PowerMockito.mockStatic(ClassLoader.class);
    PowerMockito.when(ClassLoader.getSystemClassLoader()).thenReturn(classLoader);

    //trying to mock classLoader.loadClass, below way is incorrect
    //PowerMockito.when(classLoader.loadClass("com.MyClass")).thenReturn(Class<java.lang.Object.class>);
    Assert.assertTrue(MyClassUtil.isMyClassOnClassPath());
}
@测试
当CyclassionClassPath()引发异常时,public void IsCyclassonClassPath应返回True{
mockStatic(MyClass.class);
ClassLoader ClassLoader=PowerMockito.mock(ClassLoader.class);
mockStatic(ClassLoader.class);
当(ClassLoader.getSystemClassLoader())。然后返回(ClassLoader);
//试图模拟classLoader.loadClass,下面的方式不正确
//PowerMockito.when(classLoader.loadClass(“com.MyClass”))。然后返回(Class);
Assert.assertTrue(MyClassUtil.isMyClassOnClassPath());
}

那么,可以模拟
classLoader.loadClass()
方法吗

老实说:不要想做那样的事

简言之,你就像一个坐在树上的人,开始随意切割他所坐的树的枝干。意思:这是JVM的核心部分。假设您的模拟可以工作:然后该方法的每个调用方都将收到您的模拟加载程序!所以,当您的测试用例本身想要加载一些类时,它会运行到您的模拟中

和往常一样,当人们声称“我需要为xyz使用Powermock”时,你真正的问题就不同了:你创建了不稳定的代码。通过在那里进行静态调用,您可以阻止自己测试代码

对于初学者,您可以看看如何编写可测试代码。但如果您想知道如何修复您的设计:

class ClassPathChecker {
  private final ClassLoader classLoader;
  ClassPathChecker() { this(ClassLoader.getSystemClassLoader()); }
  ClassPathChecker(ClassLoader classLoader) {
   this.classLoader = this.classLoader);
  }

  boolean canClassBeLoaded(String className) {
    try {
      classLoader.loadClass ...
上面使用依赖注入插入一个模拟的类加载器;这让你可以完全控制正在发生的一切。根本不使用Powermock


出于好奇:你为什么把自己限制在系统类加载器上?像
Class.forName(“yourclass”)
这样的简单调用不会告诉你同样的情况吗

是的,这似乎是更好的方法。谢谢:)。关于Class.forname(),我已经更新了这个问题。