Spring MVC - Checking if User is already logged in via Spring Security?

后端 未结 4 777
小蘑菇
小蘑菇 2020-12-04 06:59

I have a Spring MVC application.It uses its own custom Login page. Upon successful login, a \'LOGGED_IN_USER\' object is placed in the HTTPSession.

4条回答
  •  温柔的废话
    2020-12-04 07:28

    There are at least 4 different ways:

    spring security XML configuration

    this is the easiest way

    
       ...
      
      
    
    
    • @see Spring Security Reference, Chapter 16.1.1 Common Built-In Expressions
    • @see Spring Security Reference, Chapter 16.2 Web Security Expressions

    Per @Secured Annotation

    requires

    @Secured("ROLE_ADMIN")
    @RequestMapping(params = "onlyForAdmins")    
    public ModelAndView onlyForAdmins() {
        ....
    }
    

    Per @PreAuthorize Annotation

    requires

     @PreAuthorize("isAuthenticated()")
     @RequestMapping(params = "onlyForAuthenticated")
     public ModelAndView onlyForAuthenticatedUsers() {
         ....
     }
    

    Programmatic

     SecurityContextHolder.getContext().getAuthentication() != null &&
     SecurityContextHolder.getContext().getAuthentication().isAuthenticated() &&
     //when Anonymous Authentication is enabled
     !(SecurityContextHolder.getContext().getAuthentication() 
              instanceof AnonymousAuthenticationToken) 
    

    Custom Expression

    If the built-in expressions are not enough, you can extend them. How to extend the SpEL Expressions for the method annotations is discussed for example here:

    • How to create custom methods for use in spring security expression language annotations
    • http://bmchild.blogspot.de/2012/02/creating-custom-regex-spring-security.html

    But for the interceptor there is a slightly different approach possible, that does not need to deal with the private class problem. -- I have only done it for Spring Security 3.0, but I hope it works for 3.1 too.

    1.) you need to create a new class that extends from WebSecurityExpressionRoot (Prefix Web is the important part!).

    public class MyCustomWebSecurityExpressionRoot
             extends WebSecurityExpressionRoot {
         public MyCustomWebSecurityExpressionRoot(Authentication a,
                     FilterInvocation f) {
              super(a, f);
         }
    
         /** That method is the one that does the expression evaluation! */
         public boolean myCustomAuthenticatedExpression() {
            return super.request.getSession().getValue("myFlag") != null;
         }
    }
    

    2.) you need a extend the DefaultWebSecurityExpressionRootHandler to have a handler that provides your custom expression root

     public class MyCustomWebSecurityExpressionHandler
                  extends DefaultWebSecurityExpressionHandler {
    
          @Override        
          public EvaluationContext createEvaluationContext(Authentication a,
                    FilterInvocation f) {
              StandardEvaluationContext ctx =
                       (StandardEvaluationContext) super.createEvaluationContext(a, f);
    
               WebSecurityExpressionRoot myRoot =
                        new MyCustomWebSecurityExpressionRoot(a, f);
    
               ctx.setRootObject(myRoot);
               return ctx;
          }
     }
    

    3.) Then you need to register your handler with the voters

    
          ...
                 
          ...
    
    
    
        
                
                    
                
        
    
    
    
        
    
    
    
    

    Spring Security 3.1 Update

    Since Spring Security 3.1 it is a bit easier to implement a custom expression. One does not longer need to sublcass WebSecurityExpressionHandler and override createEvaluationContext. Instead one sublass AbstractSecurityExpressionHandler or its subclass DefaultWebSecurityExpressionHandler and override SecurityExpressionOperations createSecurityExpressionRoot(final Authentication a, final FilterInvocation f).

     public class MyCustomWebSecurityExpressionHandler
                  extends DefaultWebSecurityExpressionHandler {
    
          @Override        
          public SecurityExpressionOperations createSecurityExpressionRoot(
                    Authentication a,
                    FilterInvocation f) {
               WebSecurityExpressionRoot myRoot =
                        new MyCustomWebSecurityExpressionRoot(a, f);
    
               myRoot.setPermissionEvaluator(getPermissionEvaluator());
               myRoot.setTrustResolver(this.trustResolver);
               myRoot.setRoleHierarchy(getRoleHierarchy());
               return myRoot;
          }
     }
    

提交回复
热议问题