我正在为我的服务类编写 JUnit 测试用例。 我创建了虚拟数据来了解我的方案。
@Service
MainClass {
@Autowired
C c;
public void someServiceMethod(){
ResultClass someResult = c.getResult(string,string, int, int, List<String>,boolean);
}
}
@Service
public class C {
@Autowired
SomeRepository someRepository;
public ResultClass getResult(string,string, int, int, List<String>,boolean){
ABC returnSomeClassObject = someRepository.getSomeData(String,int,int);
}
}
@Test
MainClassTest {
@MockBean
SomeRepository someRepository;
when(someRepository.getSomeData(anyString(),anyInt(),anyInt())).thenReturn(SomeRepository);
//calling MainClass method
MainClass.someServiceMethod();
}
类 C 的 getSomeData() 方法返回 ABC 类对象,该对象为 NULL,后来设置为另一个相同的类类型对象。 设置值后,我得到 NULLPointerException,因为 ABC 是 NULL。 有人知道我哪里出错了吗?
编写模拟语句时未返回预期对象
@Service
public class C {
@Autowired
SomeRepository someRepository;
public ResultClass getResult(string,string, int, int, List<String>,boolean){
ABC returnSomeClassObject = someRepository.getSomeData(String,int,int);
//Your return type should be ResultClass
// Where your return statement
// What is ABC?
}
}
@Test
MainClassTest {
@MockBean
SomeRepository someRepository;
when(someRepository.getSomeData(anyString(),anyInt(),anyInt())).thenReturn(SomeRepository);
// Why are you returning SomeRepository, This Should return object of ABC
@MockBean
ABC mockResultClass
when(someRepository.getSomeData(anyString(),anyInt(),anyInt())).thenReturn(mockResultClass);
//calling MainClass method
MainClass.someServiceMethod();
}
您正在调用MainClass.someServiceMethod()
而又调用类 C 的 getResult 。你应该嘲笑C类,如果你的目的是测试Main
类someServiceMethod()
,你应该嘲笑C类,并在C类getResult()
上使用when-thenReturn。Autowired
在这里不起作用,因为这是一个单元测试,因此 Main 类中 C c 的实例将为 null。 如下所示:
@MockBean
C c;
when(c.getResult(anyString(), anyString(),anyInt(),anyInt(), any(List.class), anyBoolean()).thenReturn(someResult);
c.getResult(string,string, int, int, List<String>,boolean);
因此,首先,我们需要明确您到底在进行单元测试。如果您尝试在MainClass
内部对someServiceMethod
进行单元测试,那么这意味着您不应该也测试someRepository
的功能。这个想法是,每个单元测试应该只测试一个代码单元。因此,为此,我们需要使用存根作为替代,以反映调用其他类拥有的方法时实际发生的情况。然后,我们将编写一个不同的单元测试,只是为了someRepository.getSomeData()
确认它也按预期工作。这样,当以后出现错误时,我们将确切地知道我们在哪里遇到问题。
我看到的另一个问题是C
中getResult()
的返回类型明显不匹配。该方法说它返回一个ResultClass
,但是当你调用getSomeData
时,你期待一个ABC
对象。要么你省略了将对象转换回ResultClass
的细节,要么这是一个错误。除非你另有说明,否则我将假设前者。
考虑到这一点,让我们编写我们的测试。以下是我编写测试的方式:
@RunWith(SpringRunner.class)
public class MainClassTest {
@Mock
C c;
@InjectMocks
MainClass mainClass;
@Test
public void testSomeServiceMethod {
ResultClass resultClass = new ResultClass(); //relevant constructor details here, mockbean, etc. you get the idea
//set any desired data for resultClass here
Mockito.when(c.getResult(anyString(), anyString(),
anyInt(), anyInt(), any(List.class), anyBoolean()))
.thenReturn(resultClass);
ResultClass newResult = mainClass.someServiceMethod();
//relevant test assertions here
}
}
如您所见,我们正在测试中创建一个ResultClass
,并告诉 Mockito 在调用getResult
时返回该,而不是您通常期望它返回的内容。虽然功能现在看起来可能有限,但这是首选,因为我们只测试MainClass
而不是其余的方法调用。
除此之外,我们可以(并且应该)在C
中为getResult
编写测试,并在SomeRepository
中getSomeData
。我会留给你来编写这些测试。
编辑:不小心发布得有点早,现在修复。