我正在尝试为我的春季启动应用程序进行测试,我有一个很大的问题。这就是我的错误的样子:
org.mockito.exceptions.misusing.WrongTypeOfReturnValue:
WorkItem cannot be returned by findById()
findById() should return Optional
我正在遵循教程,每个人都在使用findOne()
,但对我来说,这是行不通的。我的IDE显示:
"针对类型参数's'的推断类型不在其界限内;应扩展'com.java.workitemservice.model.workitem"
这就是为什么我以另一种方式尝试并使用了findById()
,但后来又有另一个错误。
{
@RunWith(SpringRunner.class)
@SpringBootTest
public class WorkitemServiceApplicationTests {
@Mock
private WorkItemRepository workItemRepository;
@InjectMocks
WorkItemsController workItemsController;
@Before
public void init() {
MockitoAnnotations.initMocks(this);
}
@Test
public void testGetUserById() {
WorkItem workItem = new WorkItem();
workItem.setId(1L);
//old version
//when(workItemRepository.findOne(1L)).thenReturn(workItem);
when(workItemRepository.findById(1L).orElse(null)).thenReturn(workItem);
WorkItem workItem2 = workItemsController.getWorkItemById(1L);
verify(workItemRepository).findById(1L).orElse(null);
assertEquals(1L, workItem2.getId().longValue());
}
}
我的存储库:
@Repository
public interface WorkItemRepository extends JpaRepository<WorkItem,
Long> {
Optional <WorkItem> findWorkItemBySubject(String subject);
}
我的服务方法:
public WorkItem getWorkItemById(Long id) {
return this.workItemRepository.findById(id)
.orElseThrow(() -> new
ResourceNotFoundException("WorkItem", "id", id));
}
我的控制器方法:
@GetMapping("/workItems/{id}")
public WorkItem getWorkItemById(@PathVariable(value = "id") Long
workItemId) {
return this.workItemService.getWorkItemById(workItemId);
}
}
作为错误指出,您没有返回方法签名声明为返回类型(即Optional<WorkItem>
)
只返回
Optional.of(workitem)
而不是workItem
,即:
when(workItemRepository.findById(1L).orElse(null)).thenReturn(Optional.of(workitem));
我在评论中看到您尝试过的:
when(workItemRepository.findById(1L).orElse(null)).thenReturn(Optional.of(workitem));
应该有效。我认为问题是从您的" Orelse"电话开始的。
确切地说,这是:
的方法public static <T> OngoingStubbing<T> when(T methodCall) {
return MOCKITO_CORE.when(methodCall);
}
所以我认为使用" olelse"防止't'被推断出来。
我的问题是为什么使用" Orelse"?您正在使用该方法。
您可以使用"任何串"匹配任何参数。
欢呼
尝试以下:
when(workItemRepository.findById(1L)).thenReturn(Optional.of(Optional.of(workitem).get()));
它为我殴打
orElse()
方法不是 jpa 的一部分,但它是从文档中看到的Optional<T>
类的方法。
为了清楚这个清楚,让我们从服务方法更改以下代码
return this.workItemRepository.findById(id)
.orElseThrow(() -> new
ResourceNotFoundException("WorkItem", "id", id));
to
Optional<WorkItem> workItem = this.workItemRepository.findById(id);
return workItem.orElseThrow(() -> new
ResourceNotFoundException("WorkItem", "id", id));
因此,这意味着orElse
方法不必在存储库方法调用中包含。由于orElseThrow
方法在可选的WorkItem上调用,因此创建了两个条件路径。因此,它需要两个测试用例,对于存在的工作项目和测试用例不存在工作项目。
测试用例一个
public void testGetWorkItemById_whenWorkItemDoesExist_returnWorkItem() {
...
when(workItemRepository.findById(1L)).thenReturn(Optional.of(workItem));
...
assertEquals(1L, workItem2.getId().longValue());
}
测试案例两个
@Test
public void testGetWorkItemById_whenWorkItemDoesNotExist_returnNull() {
...
when(workItemRepository.findById(1L)).thenReturn(Optional.empty());
...
assertEquals(null, workItem2);
}