spring security 获取用户信息

spring security 获取用户信息

本文描述在spring security中如何获取用户信息。分别介绍几种常用的方法实现。

通过Bean获取用户

获取当前认证用户(authenticated principal)最简单的方式是通过SecurityContextHolder类的静态方法:

Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
String currentPrincipalName = authentication.getName();

下面是改进版本代码,获取前首先检查是否存在认证用户:

Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
if (!(authentication instanceof AnonymousAuthenticationToken)) {
    String currentUserName = authentication.getName();
    return currentUserName;
}

当然,静态调用的缺点是代码的可测试性明显降低。我们继续探索新的方式实现。

在控制器中获取用户

在@Controller 注解的bean里,有额外的选项。principal 可以直接作为方法参数,框架会自动赋值。

import java.security.Principal;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
 
@Controller
public class SecurityController {
 
    @RequestMapping(value = "/username", method = RequestMethod.GET)
    @ResponseBody
    public String currentUserName(Principal principal) {
        return principal.getName();
    }
}

或者也可以使用认证信息:

import org.springframework.security.core.Authentication;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
 
@Controller
public class SecurityController {
 
    @RequestMapping(value = "/username", method = RequestMethod.GET)
    @ResponseBody
    public String currentUserName(Authentication authentication) {
        return authentication.getName();
    }
}

框架为了尽可能的灵活,Authentication 类的API很方便使用。因此,通过转换可以返回principal对象。

UserDetails userDetails = (UserDetails) authentication.getPrincipal();
System.out.println("User has authorities: " + userDetails.getAuthorities());

最后一种方式直接通过http request:

import java.security.Principal;
 
import javax.servlet.http.HttpServletRequest;
 
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
 
@Controller
public class SecurityController {
 
    @RequestMapping(value = "/username", method = RequestMethod.GET)
    @ResponseBody
    public String currentUserNameSimple(HttpServletRequest request) {
        Principal principal = request.getUserPrincipal();
        return principal.getName();
    }
}

通过自定义接口获取用户信息

为了充分利用spring的依赖注入功能,可以在在任何地方获取认证信息,不仅仅是@Controller注解的bean,我们通过简单的门面隐藏静态访问:

public interface IAuthenticationFacade {
    Authentication getAuthentication();
}

@Component
public class AuthenticationFacade implements IAuthenticationFacade {
 
    @Override
    public Authentication getAuthentication() {
        return SecurityContextHolder.getContext().getAuthentication();
    }
}

该门面暴露了认证对象并隐藏静态访问代码,让业务解耦并方便测试:

@Controller
public class SecurityController {
    @Autowired
    private IAuthenticationFacade authenticationFacade;
 
    @RequestMapping(value = "/username", method = RequestMethod.GET)
    @ResponseBody
    public String currentUserNameSimple() {
        Authentication authentication = authenticationFacade.getAuthentication();
        return authentication.getName();
    }
}

在jsp中获取用户信息

当前认证用户也可以在jsp页面中获取到。利用spring security标签支持。首先我们需要在页面中定义标签:

<%@ taglib prefix="security" uri="http://www.springframework.org/security/tags" %>

然后,我们可以引用principal:


    authenticated as  

总计

本文说明在spring应用中如何获取用户信息,开始介绍了通用的静态方法访问机制,后面提供了几种更好的注入方式获取principal。

你可能感兴趣的:(spring,security,principal,认证信息,用户信息,spring,Spring,Security,spring,security,实战)