Почему я получаю несоответствие типов для параметра Mock MVC, даже если в реальном запросе на публикацию формы нет этой проблемы? - PullRequest
0 голосов
/ 16 апреля 2020

Я создаю тест JUnit, чтобы проверить, что запрос POST формы создает сущность ('событие'). Размещение формы в приложении успешно создает объект, но для моего теста один из параметров вызывает ошибку несоответствия типов. Поле «место» и указатель на объект «Место», несоответствие типов между строкой и местом. Я не понимаю, как это не проблема для обычного запроса, но для искусственного теста JUnit, и я не могу найти ничего в сети ...

Это мой тест (не выполняется '. is2xxSuccessful () ')

@Test
public void postEvent() throws Exception {
    ArgumentCaptor<Event> arg = ArgumentCaptor.forClass(Event.class);

    MultiValueMap<String, String> params = new LinkedMultiValueMap<String,String>();
    params.add("name", "Test event");
    params.add("date", "2100-04-04");
    params.add("time", "12:00");
    params.add("venue", "1");

    mvc.perform(MockMvcRequestBuilders.post("/events").with(user("Rob").roles(Security.ADMIN_ROLE))
            .contentType(MediaType.APPLICATION_FORM_URLENCODED)
            .param("name", "Test event")
            .param("date", "2100-04-04")
            .param("time", "12:00")
            .param("venue", "1")
            .accept(MediaType.TEXT_HTML)
            .with(csrf()))
    .andExpect(status().is2xxSuccessful()).andExpect(content().string(""))
    .andExpect(view().name("redirect:/events")).andExpect(model().hasNoErrors())
    .andExpect(handler().methodName("createEvent")).andExpect(flash().attributeExists("ok_message"));

    verify(eventService).save(arg.capture());
    assertThat("Test event", equalTo(arg.getValue().getName()));
    assertThat("2020-04-04", equalTo(arg.getValue().getDate()));
    assertThat("12:00", equalTo(arg.getValue().getTime()));
    assertThat("1", equalTo(arg.getValue().getVenue()));
}

Это маршрут контроллера для запроса на публикацию

@RequestMapping(method = RequestMethod.POST, consumes = MediaType.APPLICATION_FORM_URLENCODED_VALUE)
    public String createEvent(@RequestBody @Valid @ModelAttribute Event event,
            BindingResult errors, Model model, RedirectAttributes redirectAttrs) {

    // If form has errors, stay on event/new (stay on form)
    if (errors.hasErrors()) {
            model.addAttribute("event", event);
            model.addAttribute("venues", venueService.findAll()); // Reload venues 
            return "events/new";
        }   

        // If no errors, save the event
        eventService.save(event);
        redirectAttrs.addFlashAttribute("ok_message", "New event added.");

        // Go back to /events
        return "redirect:/events";
    }

Это (часть) HTML формы, которая отправляет и успешно создает сущность Событие (не соответствует параметру Venue)

<form action="#" th:action="@{/events}" th:object="${event}" method="post">

  <!-- NAME -->
  <div class="form-group" th:classappend="${#fields.hasErrors('name')}? has-error">
    <label for="name">Event name</label>
    <input class="form-control" type="text" name="name" id="name" placeholder="Event name" autofocus="autofocus" />
    <p class="text-danger" th:if="${#fields.hasErrors('name')}" th:errors="*{name}">errors</p>
  </div>

  <!-- VENUE -->
  <div class="form-group" th:classappend="${#fields.hasErrors('venue')}? has-error">
    <label for="venue">Event venue</label>
    <select th:field="*{venue}" class="form-control" id="venue" name="venue"> 
      <option th:each="v : ${venues}" th:value="${v.id}" th:text="${v.name}"></option>
    </select>
    <p class="text-danger" th:if="${#fields.hasErrors('venue')}" th:errors="*{venue}">errors</p>
  </div>
...
...