One of the common task while using Spring Security in a Java web application is getting the username of currently logged in user. Sometime, you need that in your controller class and sometime in JSP for view purpose, but the big question mark is how do you get the current user in Spring Security? Well, there are many ways to do it and depending upon whether you need it inside a JSP page or Controller class, you can choose them. The current user, also known as Principal in Spring Security can be obtained from the UserDetails class, which holds all details for currently logged in user. You can get this class from the SecurityContext, which in turn can be retrieved from SecurityContextHolder as shown below:
final String currentUserName = SecurityContextHolder.getContext().getAuthentication().getName();
Btw, you don't need to code like that because you are working in Spring. It inject dependency at right level, which means you have access to UserDetails object at right places e.g. Controller and JSP pages.
In this article, I will show you a couple of ways to get the current user's name in Spring MVC Controller classes and inside JSP pages.
How to get current user's name in Controller class in Spring?
If you are using Spring Security 3 or higher version then the easiest way to get the current username is from the Principal object which is injected to handler method as shown below:
@RequestMapping(method = RequestMethod.GET) public ModelAndView showUserDetails (final HttpServletRequest request, Principal principal) { final String currentUser = principal.getName(); ..... }
Here Principal interface represents the abstract notion of a principal, which can be used to represent any entity, such as an individual, a corporation, and a login id. In this case java.security.Principal containing the currently authenticated user.
When you define Principal as a dependency in your controller method, Spring injects the current authenticated user in your method at invocation.
You can also get current username by using the Authentication object as shown below:
@RequestMapping(method = RequestMethod.GET) public String getCurrentUserNameByAuthentication(Authentication authentication) { return authentication.getName(); }
If you are using Spring Security 3.2 or higher then you can also use @AuthenticationPrincipal annotation to get the current username as shown below:
@RequestMapping(method = RequestMethod.GET) public ModelAndView showUserDetails(@AuthenticationPrincipal CustomUser user, HttpServletRequest request) { String currentUsername = user.getUsername(); ... }
Here, CustomUser is a custom object that implements UserDetails that is returned by a custom UserDetailsService interface of Spring Security. If you are wondering how does Spring Security populate these object, here is a diagram which explains it well:
How to show current username in JSP?
You can use Spring Security tag library to display current username in any JSP page. This tag libraries provides a couple of useful tags to access authentication and authorization information from Spring security e.g. authorize tag.
Here is the sample code to get the current user's name in JSP using Spring Security:
<security:authorize access = "isAuthenticated()"> Welcome <security:authentication property="principal.username" /> </security:authorize> <security:authorize access = "!isAuthenticated()"> Please login </security:authorize>
Though, in order to use these Spring security tags, you must import the tag library in your JSP page as shown below:
<%@ taglib prefix="security" uri="https://www.springframework.org/security/tags" %>
You also need to add use-expressions="true" in the <http> element of your Spring Security configuration file, otherwise methods like isAuthenticated() will not work. You also need spring-security-web.jar inside your application's WEB-INF/lib for this code to work.
That's all about how to get the current username in Spring Security. I have showed you how you can retrieve this detail inside Controller class as well as inside JSP page. As I said, it's pretty easy to get current username in Spring MVC Controller by using the dependency injection, just define Principal or Authentication in your handler method and Spring will do the rest.
You can then retrieve the username and other user details by using Principal or Authentication Objects.
It's even easier in JSP by using Spring Security tag library, just use the Spring Security tag library and access user details using principal object.
Further Reading
Thanks for reading this article so far. If you like this article and my explanation then please share with your friends and colleagues. If you have any feedback or question then please drop a note and I'll try to find an answer for you.
No comments:
Post a Comment