Java 当返回值为枚举类型时,函数不返回null
我正在为Java 当返回值为枚举类型时,函数不返回null,java,mockito,Java,Mockito,我正在为TestClass中的函数编写一个单元测试,它检查org.apache.hadoop.hbase.Cell的内容并返回枚举类型。枚举如下所示: public enum Enum_1 { SKIP, EXIT_1, EXIT_2 } 下面是函数: public ENUM_1 check (Cell cell, String str, int someInt) { String cellValue = new String(cell.getValueArray(), Sta
TestClass
中的函数编写一个单元测试,它检查org.apache.hadoop.hbase.Cell
的内容并返回枚举类型。枚举如下所示:
public enum Enum_1 {
SKIP,
EXIT_1,
EXIT_2
}
下面是函数:
public ENUM_1 check (Cell cell, String str, int someInt) {
String cellValue = new String(cell.getValueArray(), StandardCharsets.UTF_8);
if(//case 1, doesn't fall here) {
/.../
return SKIP;
}
else if(//case 2, doesn't fall here neither){
/.../
return EXIT_1;
}
//100% sure falls in this case
else {
Long long1 = getLong(str, someInt);
Long long2 = Long.parseLong(cellValue);
if(long1 > long2) {
return EXIT_2;
}
}
return SKIP;
}
在单元测试中,我使用mockito使函数getLong(str,someInt)
返回特定的值。单元测试代码如下所示:
@Test
public void test1() {
TestClass testClass = mock(TestClass.class);
Cell mockCell = mock(Cell.class);
String str = "str";
int someInt = 1;
when(mockCell.getValueArray()).thenReturn("500".getBytes());
when(testClass.getLong(same(str), same(someInt)).thenReturn(Long.valueOf(400));
TestClass.ENUM_1 result = testClass.check(mockCell, str, someInt);
assertEquals(result, TestClass.ENUM_1.SKIP);
}
但是,当我运行测试时,这是由于result
为null
同样,我100%确定函数check()
中的else{}
案例中传递的值
问题是:为什么从返回值为ENUM类型的函数中获取null
?莫基托有什么我做错的吗?感谢您的帮助
为什么我从返回值为ENUM类型的函数中获取null
由于调用的方法返回null,因此将获得null。枚举不是这方面的特殊类型;枚举引用可以为null,就像任何其他对象引用可以为null一样
这是我对莫基托做的错事吗
对
看起来你模拟了你正在测试的类,这几乎肯定不是你想要做的(因为你没有在真实的类中测试代码)。然后,您为getLong()
方法定义了一个存根返回,但没有告诉mock关于check()
方法的任何信息
因此,当您调用testClass.check(mockCell,str,someInt)
时,mock采用了默认行为,即返回null
要解决这个问题,只需不要模仿它TestClass
!构造它的一个实例,这样您的check()
调用将调用第二个代码块中显示的实际方法
为什么我从返回值为ENUM类型的函数中获取null
由于调用的方法返回null,因此将获得null。枚举不是这方面的特殊类型;枚举引用可以为null,就像任何其他对象引用可以为null一样
这是我对莫基托做的错事吗
对
看起来你模拟了你正在测试的类,这几乎肯定不是你想要做的(因为你没有在真实的类中测试代码)。然后,您为getLong()
方法定义了一个存根返回,但没有告诉mock关于check()
方法的任何信息
因此,当您调用testClass.check(mockCell,str,someInt)
时,mock采用了默认行为,即返回null
要解决这个问题,只需不要模仿它
TestClass
!构造它的一个实例,这样您的check()
调用将调用第二个代码块中显示的实际方法。请竖起大拇指@Andrzej只是带来更大的图景。
通常,联合测试执行测试一小段代码,通常是一种方法。 因此,预计要测试的方法不会被模仿。因此,有一个概念:<强> Studio即您认为不应该是本单元测试的一部分的代码段。 因此,根据原则
getLong()
,对该方法的依赖性表示类似的责任,或者它在该功能中扮演着必须的角色。如果是这样,那么它应该是私有的如果
getLong()。
不管这些最佳实践如何,您仍然可以这样做,
您只需调用thenCallRealMethod()
,并且要从同一个类调用getLong()
,您必须在TestClass
上执行Spy,它将正常工作
但是我们应该记住,Mockito不允许模仿私有和静态方法是有原因的。
快乐编码 为答案竖起大拇指@Andrzej
只是带来更大的图景。
通常,联合测试执行测试一小段代码,通常是一种方法。
因此,预计要测试的方法不会被模仿。因此,有一个概念:<强> Studio即您认为不应该是本单元测试的一部分的代码段。
因此,根据原则getLong()
,对该方法的依赖性表示类似的责任,或者它在该功能中扮演着必须的角色。如果是这样,那么它应该是私有的
如果getLong()。
不管这些最佳实践如何,您仍然可以这样做,
您只需调用thenCallRealMethod()
,并且要从同一个类调用getLong()
,您必须在TestClass
上执行Spy,它将正常工作
但是我们应该记住,Mockito不允许模仿私有和静态方法是有原因的。
快乐编码 因为你在模拟被测试的类,顺便说一句,这是非常糟糕的做法。正如Seelenvirtuose所说,你不应该模拟需要测试的类,即TestClass
,因为你在模拟被测试的类,这是非常糟糕的做法。正如Seelenvirtuose所说,您不应该模仿需要测试的类,即TestClass
,这是一个很好的答案,谢谢。不过,我没有模拟在其他测试中测试的类,但找不到使函数getLong()返回所需值的方法。我已经找到了一个解决方法,现在我将这个函数实例化为双函数,在测试中模拟它,然后将它注入TestClass实例。@George我认为如果您想/需要调用getLong()
,可能还有另一个问题,但是