Spring-Security

来源:互联网 发布:古典白话小说推荐知乎 编辑:程序博客网 时间:2024/06/05 07:25

Spring-Security是spring的一个权限管理框架,对于我们需要知道的就是他的认证和授权功能。spring3+对于其整个权限管理架构的过滤器链已经进行了屏蔽。我们可以对器过滤器链的某个进行修改获得与我们业务更加合拍的权限管理,我们需要关心的就是spring-security的两个功能,认证和授权。他和Acegi security的认证架构是一致的,不过Acegi security不再进行更新。

认证,对于认证spring提供了不同层次的认证,顺序为:①数字证书认证(X509_FILTER)②CAS认证CAS_FILTER③用户登录域的验证(FORM_LOGIN_FILTER),这也是我们经常使用的验证,对于不是特定的需求,我们一般不进行数字证书等的验证。而只是对其username和password进行验证。

username/password的认证我们使用的是【FORM_LOGIN_FILTER】这个过滤器。这一个过滤器默认的实现类是UsernamePasswordAuthenticationFilter,其继承了AbstractAuthenticationProcessingFilter类,主要的作用为:①判断url请求是否是一个认证请求(默认的认证请求是j_spring_security_check)②对于是认证的请求则进行前期数据判断(for-example:username,password is not null)③创建一个未经认证的Authenticate对象,例如:UsernamePasswordAuthenticationToken对象,其继承【AbstractAuthenticationToken】,将用户名、密码存入其中,可以以UserDetails的对象形式存储,这时我们自定义的authentication中getName方法就要好好写,以后的用户名来源于此方法。④setDetails()使用创建一个额外信息的保存,例如sessionId等主要存放的是request的一些详情;⑤将未认证的Authenticate交予与之关联的认证管理器进行认证⑥对认证通过的对象保存在SecurityContextHolder容器中。⑦多人登录的限制问题session控制, sessionStrategy.onAuthentication(authResult,request, response);

认证管理器中提供了一些列的provider,我们在FORM_LOGIN_FILTER过滤器中创建的未认证的authentication对象会选择一个provider进行认证,认证管理器要做的就是对于不同的authenticate交给不同的认证管理器进行认证,因此每一个provider需要说明其适合于认证哪一种authenticate,所以对于provider需要复写一个方法supports(Class <? extend Object>),Class中isAssignableFrom(Class)判定此Class 对象所表示的类或接口与指定的Class 参数所表示的类或接口是否相同,或是否是其超类或超接口。

对于合适的provider需要对未认证的Authenticate进行认证,一个provider跟一个userDetailsService进行关联。userDetailsService将根据用户名来加载用户信息(loadUserDetailsByUsername(String username)),返回一个UserDetails对象。provider会从userDetails对象中提取password和我们未认证的对象中的密码进行比对,成功则创建一个已认证的对象返回。

  对于认证通过的对象,那么Authenticate中认证标示是true。这时候其SecurityIntercept过滤器会对这个给对象的访问权限进行判断和授权。具体为:①判定Authenticate对象是否为已经认证通过,如果没有,调用认证管理器进行认证。②创建安全环境,将认证通过的{对象、request、response}等包装成一个security0bject对象。这个对象需要继承AbstractSecurityIntercept.③将安全对象(securityObject)交予与之关联的访问决策器accessDecisionManager进行决策。对于授权的这个过滤器其实在服务器启动的时候他就知道了所有的ConfigAttribute(配置属性,使用Map存储),当我们进行请求授权的时候,我们传递过去的安全对象可以解析出一个url,根据这个url使用urlMarcher去返回一个你请求的配置属性。这样将配置属性使用getAttribute()方法获得你访问所需的权限,再使用已认证的Authentication中的getAuthority()方法获得你已经拥有的权限进行对比,看一下你是否有权限访问。

ConfigAttribute和Authority对象相似,都提供了仅仅一个返回String的方法。

决策管理器用来对一个安全对象的请求给予合适的投票器①从securityObject中获得其请求的安全环境属性(ConfigAttribute)②从Authenticate对象中获取GrantAuthority数组对象。③交给投票器链头投票,策管理器中有多个voter,其有一个supports对象,用来指定这个voter用来对那个ConfigAttribute进行vote。

voter(投票器),隶属于决策管理器中,给特定的ConfigAttribute进行投票。同意 1,中立 0,拒绝 -1。对于自己管辖的ConfigAttribute进行投票(1或-1),对于不是自己管辖的ConfigAttribute则返回中立。对于投票成功将有访问的权利。

UserDetails和Authentication对象的关联

①  通过一个未认证的Authentication中的getName方法获取用户名,根据用户名UserDetailsService可以返回一个UserDetails对象,UserDetails对象中的getAuthorities()方法获得的权限集将会给Authentication对象

②  UserDetails对象中的getUsername和getPassword方法可以获得真正的数据用户名和密码,他和Authentication对象中的getCredentials()得到的密码进行比较,获得商户是否正确的一个说法,当然有passwordEncoder的使用会将getCredentials()获得的密码在加密后比较

③  对于UserDetails对象我们还可以保存在已认证的Authentication中。

④  如果认证的时候我们传递了一个未认证的authentication对象,回来的时候我们也有个已近认证的authentication对象,但这两个对象不是同一个,没任何管理。返回来的authentication对象中getPrincipal();就是我们userDetails对象,而未认证的authentication对象中这个方法我们仅仅存储了一个字符串。


0 0
原创粉丝点击