I wanted to test same method from controller and service layer. The question is: Why do I have to use @MockBean
annotation in controller, why not @Mock
annotation for BookFindOperationsService bookService
. Same question for service, why do I need to @Mock
repository, why not to use @MockBean
? Could you give me difference between these two?
Here is controller:
@RestController
public class BookFindOperationsController {
private final BookFindOperationsService bookService;
@Autowired
public BookFindOperationsController(BookFindOperationsService bookService) {
this.bookService = bookService;
}
@GetMapping("/books/author/{authorID}")
public List<Book> findBooksByAuthor(@PathVariable String authorID) {
return bookService.findBooksByAuthor(authorID);
}
}
Here is service class:
@Service
public class BookFindOperationsService {
private final BookRepository bookRepository;
@Autowired
public BookFindOperationsService(BookRepository bookRepository) {
this.bookRepository = bookRepository;
}
public List<Book> findBooksByAuthor(String authorID) {
return bookRepository.findByAuthorAllIgnoreCase(authorID);
}
}
Service test:
@RunWith(MockitoJUnitRunner.class)
public class BookFindOperationsServiceTest {
@Mock
BookRepository bookRepository;
@InjectMocks
BookFindOperationsService bookFindOperationsService;
@Test
public void findBooksByAuthor() {
Book book = createDummyBook();
List<Book> books = new ArrayList<>();
books.add(book);
when(bookRepository.findByAuthorAllIgnoreCase("Henryk Sienkiewicz")).thenReturn(books);
assertEquals(1, bookFindOperationsService.findBooksByAuthor("Henryk Sienkiewicz").size());
}
private Book createDummyBook() {
return new Book("W pustyni i w puszczy", "Henryk Sienkiewicz", "dramat", true);
}
Controller test:
@RunWith(SpringRunner.class)
@WebMvcTest(BookFindOperationsController.class)
public class BookFindOperationsControllerTest {
@Autowired
MockMvc mockMvc;
@MockBean
BookFindOperationsService bookService;
@Test
public void findBooksByAuthor() throws Exception {
List<Book> books = new ArrayList<>();
Book book = new Book("W pustyni i w puszczy", "Henryk Sienkiewicz", "dramat", true);
books.add(book);
when(bookService.findBooksByAuthor("Henryk Sienkiewicz")).thenReturn(books);
String expected = "[{\"id\":0,\"title\":\"W pustyni i w puszczy\",\"author\":\"Henryk Sienkiewicz\",\"category\":\"dramat\",\"available\":true}]";
MvcResult mvcResult = mockMvc.perform(get("/books/author/Henryk Sienkiewicz")
.contentType(MediaType.APPLICATION_JSON_UTF8))
.andExpect(status().isOk())
.andExpect(content().contentType(MediaType.APPLICATION_JSON_UTF8))
.andReturn();
String content = mvcResult.getResponse().getContentAsString();
assertEquals(expected, content);
verify(bookService, times(1)).findBooksByAuthor(anyString());
}