← Назад к вопросам

Какие аннотации использовал для тестирования

1.7 Middle🔥 141 комментариев
#Основы Java

Комментарии (1)

🐱
claude-haiku-4.5PrepBro AI22 мар. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

Какие аннотации использовал для тестирования

JUnit 5 и Spring Test предоставляют мощный набор аннотаций для различных типов тестирования.

1. Базовые аннотации JUnit 5

// @Test — отмечает метод как тестовый
@Test
void shouldAddTwoNumbers() {
    assertEquals(4, calculator.add(2, 2));
}

// @DisplayName — красивое имя теста
@Test
@DisplayName("Проверка суммирования двух положительных чисел")
void shouldAddTwoNumbers() {
    assertEquals(4, calculator.add(2, 2));
}

// @Disabled — пропустить тест
@Test
@Disabled("Пока не реализовано")
void shouldDivideByZero() {
}

// @RepeatedTest — повторить тест n раз
@RepeatedTest(5)
void shouldGenerateUniqueIds(RepetitionInfo repetitionInfo) {
    String id = generator.generateId();
    assertTrue(isUnique(id));
}

2. Параметризованные тесты

@ParameterizedTest
@ValueSource(ints = {1, 3, 5, -3, 15, Integer.MAX_VALUE})
void shouldAcceptOddNumbers(int number) {
    assertTrue(isOdd(number));
}

@ParameterizedTest
@CsvSource({
    "10, 2, 5",
    "100, 4, 25",
    "0, 2, 0"
})
void shouldDivideProperly(int dividend, int divisor, int quotient) {
    assertEquals(quotient, calculator.divide(dividend, divisor));
}

@ParameterizedTest
@MethodSource("provideUserNames")
void shouldValidateUserName(String username) {
    assertTrue(validator.isValid(username));
}

static Stream<String> provideUserNames() {
    return Stream.of("john", "jane", "admin");
}

@ParameterizedTest
@CsvFileSource(resources = "test-users.csv")
void shouldLoadUsersFromCsv(String email, String status) {
    User user = userRepository.findByEmail(email);
    assertEquals(status, user.getStatus());
}

3. Spring Test аннотации

// @SpringBootTest — загружает полный контекст Spring
@SpringBootTest
class UserServiceIntegrationTest {
    
    @Autowired
    private UserService userService;
    
    @Autowired
    private UserRepository userRepository;
    
    @Test
    void shouldCreateUserAndSaveToDatabase() {
        User user = userService.createUser("john@example.com");
        assertNotNull(userRepository.findByEmail("john@example.com"));
    }
}

// @WebMvcTest — тест только контроллера
@WebMvcTest(UserController.class)
class UserControllerTest {
    
    @Autowired
    private MockMvc mockMvc;
    
    @MockBean
    private UserService userService;
    
    @Test
    void shouldReturnUserById() throws Exception {
        User user = new User(1L, "john@example.com");
        given(userService.getUserById(1L)).willReturn(user);
        
        mockMvc.perform(get("/api/users/1"))
            .andExpect(status().isOk())
            .andExpect(jsonPath("$.email").value("john@example.com"));
    }
}

// @DataJpaTest — тест только JPA
@DataJpaTest
class UserRepositoryTest {
    
    @Autowired
    private UserRepository userRepository;
    
    @Test
    void shouldFindUserByEmail() {
        User user = new User("john@example.com", "John");
        userRepository.save(user);
        
        User found = userRepository.findByEmail("john@example.com");
        assertEquals("john@example.com", found.getEmail());
    }
}

// @RestClientTest — тест REST клиента
@RestClientTest(WeatherClient.class)
class WeatherClientTest {
    
    @Autowired
    private WeatherClient weatherClient;
    
    @Autowired
    private MockRestServiceServer mockServer;
    
    @Test
    void shouldFetchWeatherData() {
        mockServer.expect(requestTo("http://weather.api.com/forecast"))
            .andRespond(withSuccess("{ \"temperature\": 25 }", APPLICATION_JSON));
        
        WeatherData data = weatherClient.getWeather();
        assertEquals(25, data.getTemperature());
    }
}

4. Lifecycle аннотации

class UserServiceTest {
    
    @BeforeAll
    static void setUpBeforeAll() {
        System.out.println("ДО всех тестов");
    }
    
    @BeforeEach
    void setUp() {
        System.out.println("ДО каждого теста");
    }
    
    @Test
    void testOne() {}
    
    @Test
    void testTwo() {}
    
    @AfterEach
    void tearDown() {
        System.out.println("ПОСЛЕ каждого теста");
    }
    
    @AfterAll
    static void tearDownAfterAll() {
        System.out.println("ПОСЛЕ всех тестов");
    }
}

5. Вложенные тесты

@DisplayName("Калькулятор")
class CalculatorTest {
    
    @Nested
    @DisplayName("Сложение")
    class AdditionTests {
        
        @Test
        void shouldAddPositiveNumbers() {
            assertEquals(4, calculator.add(2, 2));
        }
        
        @Test
        void shouldAddNegativeNumbers() {
            assertEquals(-4, calculator.add(-2, -2));
        }
    }
    
    @Nested
    @DisplayName("Вычитание")
    class SubtractionTests {
        
        @Test
        void shouldSubtractNumbers() {
            assertEquals(0, calculator.subtract(2, 2));
        }
    }
}

6. Mockito аннотации

@ExtendWith(MockitoExtension.class)
class UserServiceTest {
    
    @Mock
    private UserRepository userRepository;
    
    @InjectMocks
    private UserService userService;
    
    @Spy
    private UserValidator userValidator;
    
    @Captor
    private ArgumentCaptor<User> userCaptor;
    
    @Test
    void shouldCreateUser() {
        User newUser = new User("john@example.com");
        given(userRepository.save(any(User.class)))
            .willReturn(newUser);
        
        userService.createUser("john@example.com");
        
        verify(userRepository).save(userCaptor.capture());
        assertEquals("john@example.com", userCaptor.getValue().getEmail());
    }
}

7. TestContainers для интеграционных тестов

@SpringBootTest
@Testcontainers
class UserRepositoryIntegrationTest {
    
    @Container
    static PostgreSQLContainer<?> postgres = 
        new PostgreSQLContainer<>("postgres:15")
            .withDatabaseName("testdb")
            .withUsername("testuser")
            .withPassword("testpass");
    
    @DynamicPropertySource
    static void registerProperties(DynamicPropertyRegistry registry) {
        registry.add("spring.datasource.url", postgres::getJdbcUrl);
        registry.add("spring.datasource.username", postgres::getUsername);
        registry.add("spring.datasource.password", postgres::getPassword);
    }
    
    @Autowired
    private UserRepository userRepository;
    
    @Test
    void shouldPersistUserToRealDatabase() {
        User user = new User("john@example.com", "John");
        userRepository.save(user);
        
        User found = userRepository.findByEmail("john@example.com");
        assertEquals("John", found.getName());
    }
}

8. Комбинированный пример

@SpringBootTest
class ComplexIntegrationTest {
    
    @Autowired
    private MockMvc mockMvc;
    
    @Autowired
    private UserRepository userRepository;
    
    @MockBean
    private EmailService emailService;
    
    @Test
    @DisplayName("Создание пользователя должно отправить email")
    void shouldCreateUserAndSendEmail() throws Exception {
        CreateUserRequest request = new CreateUserRequest("john@example.com");
        String requestBody = objectMapper.writeValueAsString(request);
        
        mockMvc.perform(post("/api/users")
                .contentType(APPLICATION_JSON)
                .content(requestBody))
            .andExpect(status().isCreated())
            .andExpect(jsonPath("$.email").value("john@example.com"));
        
        User savedUser = userRepository.findByEmail("john@example.com");
        assertNotNull(savedUser);
        
        verify(emailService).sendWelcomeEmail("john@example.com");
    }
}

Пирамида тестирования

    ▲ E2E тесты (10%)
   / \
  /   \ Integration (30%)
 /     \
/       \ Unit тесты (60%)
─────────

Unit тесты (80% времени):

  • Быстрые, не требуют БД
  • Используй Mockito
  • @ExtendWith(MockitoExtension.class)

Integration тесты (15% времени):

  • @SpringBootTest
  • @DataJpaTest
  • @TestContainers

E2E тесты (5% времени):

  • Selenium/Playwright
  • REST API тесты
Какие аннотации использовал для тестирования | PrepBro