I am trying to work on Ajax based login system using Spring Security and it was working fine, till I got with another requirement where I need to configure authentication-success-handler
, so as I can do some post processing once user is authenticated by Spring security.
Earlier I was not using <form-login/>
for showing Login page.My Login section is a drop down and part of header section which is common for entire application.
This is how I am trying to configure Spring security
<http pattern="/customer/**" auto-config="true" use-expressions="true" authentication-manager-ref="customerAuthenticationManager">
<!--<http pattern="/customer/**" auto-config="true" use-expressions="true">-->
<intercept-url pattern="/customer/logon.html*" access="permitAll" />
<intercept-url pattern="/customer/denied.html" access="permitAll"/>
<intercept-url pattern="/customer" access="hasRole('AUTH_CUSTOMER')" />
<intercept-url pattern="/customer/" access="hasRole('AUTH_CUSTOMER')" />
<intercept-url pattern="/customer/*.html" access="hasRole('AUTH_CUSTOMER')" />
<intercept-url pattern="/customer/*/*.html" access="hasRole('AUTH_CUSTOMER')" />
<form-login login-processing-url="/customer/logon.html" login-page="/shop/home.html"
authentication-success-handler-ref="webshopAuthenticationSuccessHandler" />
<logout invalidate-session="true"
logout-success-url="/customer/home.html"
logout-url="/customer/j_spring_security_logout" />
<access-denied-handler error-page="/customer/denied.html"/>
</http>
With these configuration, when ever I am clicking on login button with correct credentials, i am getting HTTP 302 error
http://localhost:8080/shop/customer/logon.html 302 found
Not sure what exactly I am doing wrong?
<form id="login" method="post" accept-charset="UTF-8">
<input id="userName" type="text" name="userName" size="30" />
<button type="submit" class="btn">Login</button>
</form>
var data = $(this).serializeObject();
$.ajax({
'type': 'POST',
'url': "<c:url value="/customer/logon.html"/>",
'contentType': 'application/json',
'data': JSON.stringify(data),
'dataType': 'json',
....
}}:
Authentication authenticationToken = new UsernamePasswordAuthenticationToken(customer.getUserName(), customer.getPassword());
try {
Authentication authentication = customerAuthenticationManager.authenticate(authenticationToken);
SecurityContextHolder.getContext().setAuthentication(authentication);
resp.setStatus(AjaxResponse.RESPONSE_STATUS_SUCCESS);
} catch (AuthenticationException ex) {
resp.setStatus(AjaxResponse.RESPONSE_STATUS_FAIURE);
}
Any inputs? With all my efforts, I am still getting 302 and with above configuration, even my logon.html
controller is not getting called.
My main issue is when I am enabling Spring security using
<form-login login-processing-url="/customer/logon.html" login-page="/shop/home.html"
authentication-success-handler-ref="webshopAuthenticationSuccessHandler" />
I am getting 302
from logon.html
and even logon.html
Controller is not being triggered (placed debugger on it)
The first feature was fairly easy to implement thanks to Spring Security. Its configuration supports a requires-channel attribute that can be used for this. I used this to force HTTPS on the "users" page and it subsequently causes the login to be secure.
Implement login with Ajax, with the request coming from an insecure page. The first feature was fairly easy to implement thanks to Spring Security. Its configuration supports a requires-channel attribute that can be used for this. I used this to force HTTPS on the "users" page and it subsequently causes the login to be secure.
Whenever we use a custom form for authentication in place of the one provided by Spring Security, we have to inform Spring Security of it using the formLogin () method. We then also specify our login URL – /login. We will map the URL to our custom login page in our Controller later.
Similarly, we can use the XML configuration: If we don't specify this, Spring Security will generate a very basic Login Form at the /login URL. 8.2. The POST URL for Login The default URL where the Spring Login will POST to trigger the authentication process is /login, which used to be /j_spring_security_check before Spring Security 4.
First you don't need a controller, spring security handles all this for you. So drop the controller.
The current problem is due to your JSON based post. This is handled by the normal filter which handles login, but it doesn't see a j_username
and j_password
field and as such will redirect (the 302) to the login page (in your case /shop/home.html
) asking for those fields.
Basically you are posting the data as JSON whereas it simply should be just an ajaxified form post. This allows you to write a simple AuthenticationSuccessHandler
which simply returns a 401 or a 200 status-code (and maybe a body) when things are ok.
Changing your ajax submit to something like this should make things work.
var data = $(this).serializeObject();
$.ajax({
'type': $(this).action,
'url': $(this).target,
'data': data
}):
This should create a ajax form post. Might be that you need a call to preventDefault()
in the surrounding method to stop the form from actual posting.
With the login form that is currently posted it cannot work, as a form like this is needed:
<body>
<form action="/j_spring_security_check" method="POST">
<label for="username">User Name:</label>
<input id="username" name="j_username" type="text"/>
<label for="password">Password:</label>
<input id="password" name="j_password" type="password"/>
<input type="submit" value="Log In"/>
</form>
</body>
The post needs to be done j_spring_security_check, and username and password need to be suplied in fields j_username and j_password, otherwise it won't work.
I think you are getting a redirect to a login page.
You can see where the redirect is going with the chrome debugger or firebug if using firefox.
To approach this first get the rest of the config working with the default login page generated by spring security, by removing login-page="/customer/logon.html".
Once this works you can add back the custom login page, but it needs to have the elements above.
Also I believe you are trying to post a JSTL tag via ajax to the server? If it's true it won't work, otherwise can you edit the question.
Try it step by step by first using the default login page, then with an ajax request with hardcoded values just for testing and then when this works with a custom login page.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With