Review mocking techniques and learn how to apply them in the context of test-driven development.
// Basic mocking example @Test void shouldFetchUserAndSendNotification() { // Arrange UserRepository mockRepository = mock(UserRepository.class); NotificationService mockNotificationService = mock(NotificationService.class); User testUser = new User("user123", "user@example.com"); when(mockRepository.findById("user123")).thenReturn(testUser); UserService userService = new UserService(mockRepository, mockNotificationService); // Act userService.notifyUser("user123", "Hello!"); // Assert verify(mockRepository).findById("user123"); verify(mockNotificationService).sendEmail(testUser.getEmail(), "Hello!"); } // Mocking exceptions @Test void shouldHandleUserNotFound() { // Arrange UserRepository mockRepository = mock(UserRepository.class); when(mockRepository.findById("missing")).thenThrow(new UserNotFoundException()); UserService userService = new UserService(mockRepository, mock(NotificationService.class)); // Act & Assert assertThrows(UserNotFoundException.class, () -> { userService.notifyUser("missing", "Hello!"); }); } // Using argument captors @Test void shouldCreateProperNotificationContent() { // Arrange NotificationService mockNotificationService = mock(NotificationService.class); UserService userService = new UserService(mock(UserRepository.class), mockNotificationService); // Capture what gets passed to the notification service ArgumentCaptor<String> contentCaptor = ArgumentCaptor.forClass(String.class); // Act userService.sendSystemNotification("System maintenance"); // Assert verify(mockNotificationService).broadcast(contentCaptor.capture()); String capturedContent = contentCaptor.getValue(); assertTrue(capturedContent.contains("System maintenance")); assertTrue(capturedContent.startsWith("[SYSTEM NOTIFICATION]")); }