Spring Security 3.1 配置笔记三

Spring Security 3.1 配置笔记三

Spring Security 按照大多数的默认配置完成之后,就可以实现基于数据库的用户角色权限验证。

如果我们要实现自己的验证,在Contorller或者Action里得到前台表单,验证用户密码,比如Ajax处理、复杂的密码加密等。

按照上篇文章的配置文件,对Form-login的属性进行设置,配置自己的表单参数,在登录后用Action方法实现验证:

判断用户名密码信息符合后可以将用户的权限信息加入到SS的框架中去,文档说通过:
SecurityContextHolder.getContext().setAuthentication(authentication);

就能实现验证后用户权限的传递,我测试不可行,应该是配置不对,对SS3的Filter还理解不深入,只有自己使用传统的SESSION来实现了,这里除了SESSION结合Cookies实现也还是可以的,系统应用压力不大使用SESSION是可以接受的。

	@RequestMapping(value="/login",method=RequestMethod.POST)
	public ModelAndView doLogin(@RequestParam("username")String userName,@RequestParam("password")String passWord,HttpServletRequest request) throws Exception{
		ModelAndView modelAndView = null;
		User user = userService.findUserByUserName(userName);
		if(user!=null){
			if(passWord.equals(user.getPassword())){
				modelAndView = new ModelAndView("/index");
				modelAndView.addObject("user",user);
				memberAuthenticationManager.cacheMemberPermission(user, request);
				return modelAndView;
			}else{
				throw new Exception("用户名或者密码错误!");
			}
		}else{
			throw new Exception("用户不存在!");
		}
	}

在验证通过后讲生成的SS3的权限信息保存到SESSION中,上篇文章的Filter配置里在将全线信息从SESSION中读取出来设置到SS3中,把角色和资源的验证交给SpringSecurity去做。我们更加去关注逻辑代码实现。

@Component("memberAuthenticationManager")
public class MemberAuthenticationManager{
	
	public void cacheMemberPermission(User user,HttpServletRequest request){
		UsernamePasswordAuthenticationToken authentication = new UsernamePasswordAuthenticationToken(user, user.getPassword(),user.getAuthorities());
		authentication.setDetails(new WebAuthenticationDetails(request));
		SecurityContextHolder.getContext().setAuthentication(authentication);
		HttpSession session =request.getSession(false);
		session.setAttribute(SecurityCoreInterceptor.SPRING_SECURITY_SESSION_ID,authentication);
	}
	
	public void releaseMemberPermission(HttpServletRequest request){
		if(request.getSession()!=null){
			SecurityContextHolder.getContext().setAuthentication(null);
			request.getSession().setAttribute(SecurityCoreInterceptor.SPRING_SECURITY_SESSION_ID,null);
			request.getSession().invalidate();
		}
	}

}

另外可能还会涉及到的用户信息注入:

实现方式让Conoller实现接口,使用SpringMVC的拦截器,注入从SS3中得到的用户信息.

public class MemberInterceptor extends HandlerInterceptorAdapter{

	@Override
	public void postHandle(HttpServletRequest request,
			HttpServletResponse response, Object handler,
			ModelAndView modelAndView) throws Exception {
		if(handler instanceof MemberAware){
			MemberAware aware = (MemberAware) handler;
			HttpSession session = request.getSession(false);
			if(session!=null 
					&& session.getAttribute(SecurityCoreInterceptor.SPRING_SECURITY_SESSION_ID) != null){
				Authentication authentication = (Authentication) session.getAttribute(SecurityCoreInterceptor.SPRING_SECURITY_SESSION_ID);
				User user = (User) authentication.getPrincipal();
				if(user != null)
				aware.setCustomer(user);
			}
		}
		super.postHandle(request, response, handler, modelAndView);
	}
  
}

public interface MemberAware {
	public void setCustomer(User user);
}


@Controller
@RequestMapping(value="/member")
public class MemberController implements MemberAware{
	
	private Logger log = LoggerFactory.getLogger(Thread.class);
	@Autowired
	private UserService userService;
	@Autowired
	private ResourceService resourceService;
	@Autowired
	private MemberAuthenticationManager memberAuthenticationManager;
	
	private User user;
........
}

这样主要流程就完成了,参考的一些资料:

spring security 3.0 配置实例 入门级(一)
http://hi.baidu.com/liang125353769/blog/item/4e277a814a5e99d89123d9b5.html
spring security 全配置
http://hi.baidu.com/hontlong/blog/item/055edd248e300b114d088d4c.html
Spring Security学习一
http://www.cnblogs.com/shitou/archive/2011/04/20/2022251.html

留下回复