Open
Description
I want to test a login controller that is used together with spring security.
The controller is implemented like this:
@Controller
@RequestMapping("/login")
public class LoginController
{
@GetMapping
public ModelAndView loginPage(@RequestParam(value = "logout", required = false) String logout,
@RequestParam(value = "error", required = false) String error)
{
ModelAndView modelAndView = new ModelAndView("login");
if (logout != null)
{
modelAndView.addObject("SUCCESS_MESSAGE", "Logout erfolgreich");
}
if (error != null)
{
modelAndView.addObject("ERROR_MESSAGE", "Login nicht erfolgreich");
}
return modelAndView;
}
This works perfectly with spring-security's behavior for logouts and invalid login attempts, where the logout
and error
parameters are an empty string and not null.
For the test, I choose the following setup:
@WebMvcTest(controllers = {LoginController.class}, excludeAutoConfiguration = SecurityAutoConfiguration.class)
class LoginControllerTest
{
@Autowired
MockMvc mockMvc;
@SneakyThrows
@Test
void testLogoutPage()
{
mockMvc.perform(get("/login?logout"))
.andExpectAll(status().isOk(),
MockMvcResultMatchers.view().name("login"),
MockMvcResultMatchers.model().attributeExists("SUCCESS_MESSAGE"));
}
}
This however leads to the query parameter logout
being null in the LoginController
, which fails the test. I also tried get("/login").queryParam("logout")
, but queryParam(...)
does not permit empty values. I could add a dummy value, but this would be inconsistent with the redirect behavior of spring-security. I would prefer to pass an empty query parameter through MockMvc
, but this seems to be not possible?