Spring Controller Test с использованием реальных данных во время проверки бина - PullRequest
0 голосов
/ 30 марта 2020

У меня есть метод контроллера для создания пользователя, как показано ниже.

@Secured({RoleNames.ADMIN})
@PostMapping(value = "/users/create")
public ResponseEntity<UserDto> createUser(@Valid @RequestBody CreateUserCommand command) {
    UserDto userDto = userService.create(command);
    return ResponseEntity.ok().body(userDto);
}

Мне нужно проверить CreateUserCommand (с данными формы хранения, поступающими из внешнего интерфейса). Например, существует ли электронная почта в базе данных.

Я создал валидатор, как показано ниже:

public class UserEmailExistsValidator implements ConstraintValidator<UserEmailExists, CreateUserCommand> {

@Autowired
private UserService userService;

public UserEmailExistsValidator(UserService userService) {
    this.userService = userService;
}

@Override
public boolean isValid(CreateUserCommand command, ConstraintValidatorContext constraintValidatorContext) {
    UserDto userDto = userService.getByEmail(command.getEmail());
    return userDto == null;
}
}

Моя проблема заключается в следующем: когда я пытаюсь запустить Controller Test для этого «users / create» конечная точка, она проверяет фактическую базу данных (не тестовую базу данных), существует ли электронная почта этого пользователя. Таким образом, если электронная почта этого пользователя существует в базе данных, проверки не пройдены и, следовательно, тесты не пройдены.

РЕДАКТИРОВАТЬ

Это мой класс тестирования контроллера

@RunWith(SpringRunner.class)
@ApplicationMvcTest(controllers = UserController.class)
public class UserControllerTest extends AbstractControllerTest {

    @Autowired
    private MockMvc mockMvc;

    @MockBean
    private UserService userService;

    @MockBean
    private Principal principal;

    @Before
    public void setup() {
        when(principal.getName()).thenReturn("user");
    }

    @Test
    public void shouldSaveUser_withValidRequestBody() throws Exception {
        mockMvc = getMockMvcWithAuthorities(RoleNames.ADMIN);

        mockMvc.perform(
                post(RestEndPoint.BASE_URL + "/users/create")
                        .contentType(APPLICATION_JSON_UTF8)
                        .content(new JSONObject()
                                .put("username", "John Doe")
                                .put("email", "test@test.com")
                                .put("gender", "M")
                                .toString())
        )
        /* MockMvc.perform is failing (Returns status 400) due to validator class returns false... */
        ........
    }
}


@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
@WebMvcTest
public @interface ApplicationMvcTest {
    @AliasFor("controllers")
    Class<?>[] value() default {};

    @AliasFor("value")
    Class<?>[] controllers() default {};

    boolean useDefaultFilters() default true;

    ComponentScan.Filter[] includeFilters() default {};

    ComponentScan.Filter[] excludeFilters() default {};

    @AliasFor(
            annotation = AutoConfigureMockMvc.class,
            attribute = "secure"
    )
//            Change default to false
            boolean secure() default false;

    @AliasFor(
            annotation = ImportAutoConfiguration.class,
            attribute = "exclude"
    )
    Class<?>[] excludeAutoConfiguration() default {};
}

Я использую Spring Boot 2.1.8, Mockito3.0.0.

1 Ответ

0 голосов
/ 30 марта 2020

Если вы не хотите, чтобы go передавалось в базу данных, то, где бы вы ни взаимодействовали с базой данных, этот класс должен быть подвергнут насмешке. Так что, если вы используете репозиторий, вы должны смоделировать это и позволить ему вернуть ожидаемое значение. Если это UserService, то смейтесь над этим, и когда будет вызван вызов для поиска электронного письма, верните значение.

when(userService.getByEmail(anyString())).thenReturn(null);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...