Note that there are some explanatory texts on larger screens.

plurals
  1. POPlayframework Secure module: how do you "log in" to test a secured controller in a FunctionalTest?
    text
    copied!<p><strong>EDIT</strong>: I'm using Play! version 1.2 (production release)</p> <p>I want to test controller actions that are secured by Secure module class, so I need to log in prior to testing my controller (otherwise I will be redirected to the login page). </p> <p>I've tried to log in prior to calling a secured action. Here's what my FunctionalTest looks like: </p> <pre><code>@Test public void someTestOfASecuredAction() { Map&lt;String, String&gt; loginUserParams = new HashMap&lt;String, String&gt;(); loginUserParams.put("username", "admin"); loginUserParams.put("password", "admin"); // Login here so the following request will be authenticated: Response response = POST("/login", loginUserParams); // The following is an action that requires an authenticated user: Map&lt;String, String&gt; params; params.put("someparam", "somevalue"); response = POST("/some/secured/action", params); assertIsOk(response); // this always fails because it is a 302 redirecting to /login } </code></pre> <p>Stepping through the code, I've verified that the login post works - it causes a redirect response with location set to the home page (which indicates a successful login).</p> <p>But then in the subsequent call to a secured action, I am always redirected to the "/login" page - indicating that my previous login did not stick for the second POST request. </p> <p>Looking into the source code of FunctionalTest I saw there was an @Before interceptor that clears all cookies. I tried overriding this intercepter in my own intermediary superclass (to preserve the cookies), but that didn't work either.</p> <p><strong>EDIT</strong>: I was confusing the play.mvc.Before interceptor with org.junit.Before - the former for use with Play! controllers, the latter for JUnit tests. The @Before in the FuncitonTest is a JUnit interceptor, so it should have any affect on cookies (since it gets run once prior to the test being run).</p> <p>I do not want to have to write a Selenium test for every secured action - since almost all will be secured. Is there a way to "fool" the Secure module into believing you're authenticated? Or maybe some other very obvious way for handling this (seemingly common) scenario in a FunctionalTest?</p> <p>Thanks in advance,</p> <p>Mark</p> <p><strong>EDIT</strong>: Working code, Codemwnci's answer marked as correct</p> <p>Codemwnci's answer is correct. Here is my workaround for preserving the cookies from one request to the next:</p> <pre><code>@Test public void someTestOfASecuredAction() { Map&lt;String, String&gt; loginUserParams = new HashMap&lt;String, String&gt;(); loginUserParams.put("username", "admin"); loginUserParams.put("password", "admin"); Response loginResponse = POST("/login", loginUserParams); Request request = newRequest(); request.cookies = loginResponse.cookies; // this makes the request authenticated request.url = "/some/secured/action"; request.method = "POST"; request.params.put("someparam", "somevalue"); Response response = makeRequest(request); assertIsOk(response); // Passes! } </code></pre>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload