Issue
I am trying to mock a post request using the below code .
I am testing a spring security login request.
MockMvc mvc = MockMvcBuilders.webAppContextSetup(context).addFilter(springSecurityFilterChain)
.apply(springSecurity())
.build();
MvcResult mvcResult = mvc.perform(post("/j_spring_security_check?api=true").param("userName", USERNAME)
.param("password", PASSWORD)).andReturn();
The code works fine and after successful login , I am redirecting to another controller.
@Override
public void onAuthenticationSuccess(HttpServletRequest request,
HttpServletResponse response, Authentication authentication) throws IOException,
ServletException {
RequestDispatcher rd = request.getRequestDispatcher("/myURL");
rd.forward(request, response);
}
When I run the test , I get the below logs. The redirect does not happen and the controller mapped to /myURL is not getting invoked.
11:59:55.839 [main] DEBUG o.s.mock.web.MockRequestDispatcher - MockRequestDispatcher: forwarding to [/myURL]
11:59:55.841 [main] DEBUG o.s.s.w.c.HttpSessionSecurityContextRepository - The HttpSession is currently null, and the HttpSessionSecurityContextRepository is prohibited from creating an HttpSession (because the allowSessionCreation property is false) - SecurityContext thus not stored for next request
11:59:55.841 [main] DEBUG o.s.s.w.c.SecurityContextPersistenceFilter - SecurityContextHolder now cleared, as request processing completed
There is no error reported .
Am I missing something ? Will redirect not happen while using MockMvc ?
Solution
Will redirect not happen while using MockMvc ?
NO.
The following is taken straight from the MockMvc vs End-to-End Tests section of the reference manual.
Things that may catch you by surprise are that there is no context path by default, no jsessionid cookie, no forwarding, error, or async dispatches, and therefore no actual JSP rendering. Instead, "forwarded" and "redirected" URLs are saved in the MockHttpServletResponse and can be asserted with expectations.
Thus, all you can do is verify that a forward would take place in a real Servlet Container, and you do that by invoking andExpect(forwardedUrl("/myURL"))
instead of andReturn()
.
Note that forwardedUrl
is a static method in MockMvcResultMatchers
.
Answered By - Sam Brannen
Answer Checked By - Willingham (JavaFixing Volunteer)