1. 单点登录简介
1.1CAS简介
CAS 是 Yale (耶鲁)大学发起的一个开源项目,旨在为 Web 应用系统提供一种可靠的单点登录方法,CAS 在 2004 年 12 月正式成为 JA-SIG 的一个项目。
http://www.jasig.org/cas
CAS 具有以下特点:
•基于kerberos身份认证协议技术
•开源的企业级单点登录解决方案。
•CAS Server 为需要独立部署的 Web 应用。
•CAS Client 支持非常多的客户端(这里指单点登录系统中的各个 Web 应用),包括 Java, .Net, PHP, Perl, Apache, uPortal, Ruby 等。
单点登录(Single Sign On),简称为 SSO,是目前比较流行的企业业务整合的解决方案之一。SSO的基本功能是在多个应用系统中,用户只需要登录一次就可以访问所有相互信任的应用系统。
例如:
A和B两个完全独立的系统分别有各自完全独立的用户管理,现在需要将这两个系统整合,不管是A系统中的帐户,还是B系统中的帐户,都只需要登录一次,就可以访问A和B系统的服务了。
如果一个人同时具有A和B系统的帐户,当他以A系统的帐户登录后,访问B系统时,B系统自动将它转换成本系统帐户再进行访问操作,反之亦然。
A和B系统整合后,不再单独提供新用户注册功能。新用户注册统一到中央认证管理系统中,新注册的用户可以同时访问A和B系统,例如,sina和sohu等网站的通行证注册就是这么回事。
1.2 关键字
KDC( Key Distribution Center ) ---------- 密钥发放中心
authentication service (AS) --------- 认证用服务,索取 Crendential ,发放 TGT
Ticket Granting tieckt(TGT) --------- 票据授权票据,由 KDC 的 AS 发放。即获取这样一张票据后,以后申请各种其他服务票据 (ST) 便不必再向 KDC 提交身份认证信息 ( 准确术语是 Credentials) 。
ticket-granting service (TGS) --------- 票据授权服务,索取 TGT ,发放 ST ,CAS 单点服务器的认证过程,所有应用服务器收到应用请求后,检查 ST 和 TGT ,如果没有或不对,转到 CAS 认证服务器登陆页面,通过安全认证后得到 ST 和 TGT 再重定向到相关应用服务器,在会话生命周期之内如果再定向到别的应用,将出示ST 和 TGT 进行认证 , 注意 , 取得 TGT 的过程是通过 SSL 安全协议的 ( 换句话说就是如果不用 ssl 协议 , 每访问一个应用服务,就得重新到认证服务中心认证一次 )。
Service ticket(ST) --------- 服务票据, 由 KDC 的 TGS 发放。 任何一台 Workstation 都需要拥有一张有效的 Service Ticket 才能访问域内部的应用 (Applications) 。如果能正确接收 Service Ticket ,说明在CASClient-CASServer 之间的信任关系已经被正确建立起来 , 通常为一张数字加密的证书
TGC(ticket-granting cookie) --------- 票据授权票Cookie(Ticket Grangting Cookie) 。在用户成功登录后,在CAS Server的Cookie中保存登录成功信息。在访问其他应用时,根据TGC去验证获取用户的登录信息
1.3 单点登录原理
cas 实现single sign out的原理,如图所示:
图一
第一张图演示了单点登陆的工作原理。
从第一张图中,当一个web浏览器登录到应用服务器时,应用服务器(application)会检测用户的session,如果没有登记过(登录),则应用服务器会把url跳转到CAS server上,要求用户登录,用户登录成功后,CAS server会记请求的application的url和该用户的sessionId(在应用服务器跳转url时,通过参数传给CAS server)。此时在CAS服务器会种下TGC Cookie值到webbrowser.拥有该TGC Cookie的webbrowser可以无需登录进入所有建立sso服务的应用服务器application。
图二
图二演示了单点登出的工作原理。
在第二张图中,当一个web浏览器要求登退应用服务器,应用服务器(application)会把url跳转到CAS server上的 /cas/logout url资源上,
CAS server接受请求后,会检测用户的TCG Cookie,把对应的session清除,同时会找到所有通过该TGC sso登录的应用服务器URL提交请求,所有的回调请求中,包含一个参数logoutRequest, logoutRequest包含:NameID,SessionIndex,所有收到请求的应用服务器application会解析这个参数,取得sessionId,根据这个Id取得session后,把session删除。
这样就实现单点登出的功能。
认证过程:
白话描述:
单点登陆,无非就是提供给用户一次登陆, 多个系统共享用户信息的操作。
这个是怎么操作的呢 ? 有简单的方法 , 当用户访问其他系统的时候 , 写个 URL 带上用户的 ID 和 PASS 提交到相应的系统就可以了。这也是一种方法。
那 CAS 是怎么操作的呢 ? 或则是 KRB(Kerberos 是一个加密认证协议,允许网络用户不使用明文密码访问服务,一个普通的协议实现包括 LOGIN 服务存在伪造欺骗对 Key Distribution Center 的响应。
怎么操作的呢 ?
他并不是很复杂 , 他先是建立一个专门认证用户的 服务 (SERVER) 这个服务只做一件事 , 负责验证用户的 ID 和 PASS 是否是正确 , 在正确的情况提供用户一个名为 TGT 的票据 , 相当你要去游乐场玩 , 首先你要在门口检查你的身份 ( 即 CHECK 你的 ID 和 PASS), 如果你通过验证 , 游乐场的票务中心 (AS) 即提供给你一张门卡 (TGT),同时把TGC保存到你的cookie(仅包含用户名等对安全不是很敏感的信息)。
这张卡片的用处就是告诉 游乐场的各个场所 , 你是通过正门进来 , 而不是后门偷爬进来的 , 并且也是获取进入场所一把钥匙。
好的, 现在你有张卡, 但是这对你来不重要, 因为你来游乐场不是为了拿这张卡的 , 好的 , 我们向你的目的出发, 恩, 你来到一个摩天楼 , 你想进入玩玩 , 这时摩天轮的服务员 (client) 拦下你 , 向你要求摩天轮的 (ST) 票据 , 你说你只有一个门卡 (TGT), 好的 , 那你只要把 TGT 放在一旁的票据授权机 (TGS) 上刷一下 , 票据授权机 (TGS) 就根据你现在所在的摩天轮 , 给你一张摩天轮的票据 (ST) , 现在你可以畅通无阻的进入摩天轮里游玩了。
当然如果你玩完摩天轮后 , 想去游乐园的咖啡厅休息下 , 那你一样只要带着那张门卡 (TGT). 到相应的咖啡厅的票据授权机 (TGS) 刷一下 , 得到咖啡厅的票据 (ST) 就可以进入咖啡厅。
从咖啡馆出来,女朋友说还想玩摩天轮,ok,你们又来到摩天轮,摩天轮工作人员一看你们有ST (第一次来的时候,TGS已经签发ST给你的TGT了)就直接放行。不让你们再跑到CAS那边去索取摩天轮的ST了,同样的,你们再此进入咖啡厅也是如此。
当你离开游乐场后 , 想用这张 TGT 去进去玩大摆锤 , 呵呵 , 对不起 , 你的 TGT 已经过期了 , 在你离开游乐场那刻开始 , 你的 TGT和TGC 就已经销毁了。想玩吗?想玩重新去注册吧(登录)
1.4 生命周期TGT生命周期是通过配置文件设定的,默认2小时,失效后自动回收
TGC生命周期和TGT一样。
ST生命周期为一个服务进行一次认证的过程
Assertion生命周期为Session Timeout
1、为基于J2EE企业应用提供了全面安全服务
1,将系统的安全逻辑从业务中分离出来
2,提供很多认证授权策略
3,基于URL的WEB资源访问控制
4,业务方法调用访问控制
5,领域对象访问控制
Access Control List(ACL)
6,单点登录(Central Authentication Service) 缓存、信道安全(Channel Security)管理等功能
1)、安全包括认证授权两个主要操作。
“认证”是为用户建立一个他所声明的主体。主体一般是指用户,设备或可以在你系统中执行行动的其他系统。
“授权”指的一个用户能否在你的应用中执行某个操作。在到达授权判断之前,身份的主体已经由身份验证过程建立了。
用户认证过程:
1.你点击一个链接访问一个网页;
2.浏览器发送一个请求到服务器,服务器判断出你正在访问一个受保护的资源;
3.如果此时你并未通过身份认证,服务器发回一个响应提示你进行认证——这个响应可能是一个HTTP响应代码,抑或重定向到一个指定页面;
4.根据系统使用认证机制的不同,浏览器或者重定向到一个登录页面中,或者由浏览器通过一些其它的方式获取你的身份信息(如通过BASIC认证对话框、一个Cookie);
5.浏览器再次将用户身份信息发送到服务器上(可能是一个用户登录表单的HTTP POST信息、也可能是包含认证信息的HTTP报文头);
6.服务器判断用户认证信息是否有效,如果无效,一般情况下,浏览器会要求你继续尝试,这意味着返回第3步。如果有效,则到达下一步;
7.服务器重新响应第2步所提交的原始请求,并判断该请求所访问的程序资源是否在你的权限范围内,如果你有权访问,请求将得到正确的执行并返回结果。否则,你将收到一个HTTP 403错误,这意味着你被禁止访问。
授权过程
Spring Security称受保护的应用资源为“安全对象”,这包括URL资源和业务类方法。spring AOP中有前置advice(处理、拦截器、通知)、后置advice 、异常advice和环绕advice 。Acegi使用环绕advice对安全对象进行保护。 Acegi通AbstractSecurityInterceptor为安全对象访问提供一致的工作模型,它按照以下流程进行工作:
1. 从SecurityContext中取出已经认证过的Authentication(包括权限信息);
2. 通过反射机制,根据目标安全对象和“配置属性”得到访问目标安全对象所需的权限;
3. AccessDecisionManager根据Authentication的授权信息和目标安全对象所需权限做出是否有权访问的判断。如果无权访问,Acegi将抛出AccessDeniedException异常,否则到下一步;
4. 访问安全对象并获取结果(返回值或HTTP响应);
5. AbstractSecurityInterceptor可以在结果返回前进行处理:更改结果或抛出异常。
如果需要使用taglib,首先要把spring-security-taglibs-2.0.6.jar放到项目的classpath下。剩下的只要在jsp上添加taglib的定义就可以使用标签库了。
<%@ taglib prefix="sec" uri="http://www.springframework.org/security/tags"%>
1.6.1 Authenticaitonauthentication的功能是从SecurityContext中获得一些权限相关的信息。
可以用它获得当前登陆的用户名:
<sec:authentication property="name"/>
获得当前用户所有的权限,把权限列表放到authorities变量里,然后循环输出权限信息:
<sec:authentication property="authorities" var="authorities" scope="page"/>
<c:forEach items="${authorities}" var="authority">
${authority.authority}
</c:forEach>
1.6.2 authorizeauthorize用来判断当前用户的权限,然后根据指定的条件判断是否显示内部的内容。
<sec:authorize ifAllGranted="ROLE_ADMIN,ROLE_USER">
admin and user
</sec:authorize>
<sec:authorize ifAnyGranted="ROLE_ADMIN,ROLE_USER">
admin or user
</sec:authorize>
<sec:authorize ifNotGranted="ROLE_ADMIN">
not admin
</sec:authorize>
说明:
1,ifAllGranted,只有当前用户同时拥有ROLE_ADMIN和ROLE_USER两个权限时,才能显示
标签内部内容。
2,ifAnyGranted,如果当前用户拥有ROLE_ADMIN或ROLE_USER其中一个权限时,就能显示
标签内部内容。
3,ifNotGranted,如果当前用户没有ROLE_ADMIN时,才能显示标签内部内容。
1.Spring Security与CAS可以无缝集成
Spring Security支持所有主流的认证方式,HTTP 基本认证、HTTP 表单验证、HTTP 摘要认证、OpenID 和 LDAP 等。CAS也是其中之一。
2.Spring Security与CAS有两种集成方式
第一种方式:Spring使用由Filter组成的Chain,来判断权限。如果Spring提供的Filter不能满足系统的权限功能,开发者可以自定义Filter,然后把Filter放在某个Filter Chain的某个位置。可以替换掉原有Filter Chain的某个Filter,也可以放在某个Filter之前或者之后。关于认证CAS提供两个filter。
第二种方式:Spring Security中自带关于CAS认证方式的组件。经过配置Spring Security自带的CasProcessingFilter和CasAuthenticationProvider即可。
举例说明下:
如上图,利用intercept-url来判断用户需要具有何种权限才能访问对应的url资源,可以在pattern中指定一个特定的url资源,也可以使用通配符指定一组类似的url资源。例子中定义的两个intercepter-url,第一个用来控制对/admin.jsp的访问,第二个使用了通配符/**,说明它将控制对系统中所有url资源的访问。
在实际使用中,Spring Security采用的是一种就近原则,就是说当用户访问的url资源满足多个intercepter-url时,系统将使用第一个符合条件的intercept-url进行权限控制。在我们这个例子中就是,当用户访问/admin.jsp时,虽然两个intercept-url都满足要求,但因为第一个intercept-url排在上面,所以Spring Security会使用第一个intercept-url中的配置处理对/admin.jsp的请求,也就是说,只有那些拥有了ROLE_ADMIN权限的用户才能访问/admin.jsp。user-service中定义了两个用户,admin和user。为了简便起见,我们使用明文定义了两个用户对应的密码,是为了当前演示的方便(实际应用中我们会使用CAS来验证用户信息,这里只需配置用户和角色就可以了)最最重要的部分是authorities,这里定义了这个用户登陆之后将会拥有的权限,它与上面intercept-url中定义的权限内容一一对应。每个用户可以同时拥有多个权限,例子中的admin用户就拥有ROLE_ADMIN和ROLE_USER两种权限,这使得admin用户在登陆之后可以访问ROLE_ADMIN和ROLE_USER允许访问的所有资源。与之对应的是,user用户就只拥有ROLE_USER权限,所以他只能访问ROLE_USER允许访问的资源,而不能访问ROLE_ADMIN允许访问的资源。
当然实际应用中,资源信息和用户角色信息都是通过数据库来进行维护的,如下图:
user用户表,role角色表,resc资源表相互独立,它们通过各自之间的连接表实现多对
多关系。
查询数据库得到的数据如下:
用户角色信息:
角色资源信息(访问URL所需角色):
上图中,1,用户admin具有R_ADMIN角色,角色资源表中,R_ADMIN角色可以访问:/jsp/admin/**和jps/user/**,那么admin就可以访问/jsp/admin/**资源和jps/user/**
2,user用户具有R_USER角色,角色资源表中,R_USER角色可以访问/jsp/user/**,那么user用户就只能访问/jsp/user/**下的资源,而不能其他的资源