由于本人最近刚换工作,在新的公司的系统的WEB.XML中发现有如下的配置:
<listener>
<listener-class>org.jasig.cas.client.session.SingleSignOutHttpSessionListener</listener-class>
</listener>
由于本人之前没有接触过CAS单点登录和单点登出,所以就上google上“百度”了一下,发现是CAS的单点登录配置。接下来看了一些关于CAS的文章,现在分享一下。
实现CAS需要使用cas-server-core-3.3.3.jar(CAS Server 3.3.3)和cas-client-core-3.1.3.jar(CAS Client 3.1.3)
项目结合CAS SpringSecurity SSH
普通项目(没有结合Spring Security)的可以在web.xml中加入如下代码:
1 <filter>
2 <filter-name>CAS Single Sign Out Filter</filter-name>
3 <filter-class>org.jasig.cas.client.session.SingleSignOutFilter</filter-class>
4 </filter>
5
6 <filter-mapping>
7 <filter-name>CAS Single Sign Out Filter</filter-name>
8 <url-pattern>/*</url-pattern>
9 </filter-mapping>
10
11 <listener>
12 <listener-class>
13 org.jasig.cas.client.session.SingleSignOutHttpSessionListener
14 </listener-class>
15 </listener>
在我们的项目中由于结合了SpringSecurity 可以将filter加入到spring Security过滤链中,也可以直接向上面的一样加入web.xml中
首先在web.xml中加入监听器。
[xhtml]view plaincopyprint?
16 <!-- single sign out -->
17 <listener>
18 <listener-class>
19 org.jasig.cas.client.session.SingleSignOutHttpSessionListener
20 </listener-class>
21 </listener>
22 <!-- single sign out -->
然后把filter加入到spring Security过滤链中
23 <!-- single sign out -->
24 <b:bean id="casSingleSignOutFilter" class="check.SingleSignOutFilter">
25 <custom-filter before="CAS_PROCESSING_FILTER"/>
26 </b:bean>
27 <!-- single sign out -->
注意上面的class="check.SingleSignOutFilter"是我自定义的filter(由于CAS3.1.3定义的SingleSignOutFilter在某种意思上没有起到作用)详情请见http://www.javaeye.com/topic/546785
自己定义一个类?
28 package check;
29
30 import java.io.IOException;
31 import java.util.Enumeration;
32
33 import javax.servlet.FilterChain;
34 import javax.servlet.FilterConfig;
35 import javax.servlet.ServletException;
36 import javax.servlet.ServletRequest;
37 import javax.servlet.ServletResponse;
38 import javax.servlet.http.HttpServletRequest;
39 import javax.servlet.http.HttpSession;
40
41 import org.apache.commons.logging.Log;
42 import org.apache.commons.logging.LogFactory;
43 import org.jasig.cas.client.session.HashMapBackedSessionMappingStorage;
44 import org.jasig.cas.client.session.SessionMappingStorage;
45 import org.jasig.cas.client.util.AbstractConfigurationFilter;
46 import org.jasig.cas.client.util.CommonUtils;
47 import org.jasig.cas.client.util.XmlUtils;
48
49 public final class SingleSignOutFilter extends AbstractConfigurationFilter
50 {
51 private String artifactParameterName;
52 private static SessionMappingStorage SESSION_MAPPING_STORAGE = new HashMapBackedSessionMappingStorage();
53 private static Log log = LogFactory.getLog(SingleSignOutFilter.class);
54
55 public SingleSignOutFilter()
56 {
57 this.artifactParameterName = "ticket";
58 }
59
60 public void init(FilterConfig filterConfig)
61 throws ServletException
62 {
63 setArtifactParameterName(getPropertyFromInitParams(filterConfig, "artifactParameterName", "ticket"));
64 init();
65 }
66
67 public void init() {
68 CommonUtils.assertNotNull(this.artifactParameterName, "artifactParameterName cannot be null.");
69 CommonUtils.assertNotNull(SESSION_MAPPING_STORAGE, "sessionMappingStorage cannote be null.");
70 }
71
72 public void setArtifactParameterName(String artifactParameterName) {
73 this.artifactParameterName = artifactParameterName;
74 }
75
76 public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
77 final HttpServletRequest request = (HttpServletRequest) servletRequest;
78 final String logoutRequest = CommonUtils.safeGetParameter(request, "logoutRequest");
79 Enumeration ff = request.getParameterNames();
80 String a = request.getQueryString();
81 if (CommonUtils.isNotBlank(logoutRequest)) {
82 final String sessionIdentifier = XmlUtils.getTextForElement(logoutRequest, "SessionIndex");
83
84 if (CommonUtils.isNotBlank(sessionIdentifier)) {
85 final HttpSession session = SESSION_MAPPING_STORAGE.removeSessionByMappingId(sessionIdentifier);
86
87 if (session != null) {
88 String sessionID = session.getId();
89 try {
90 session.invalidate();
91 } catch (final IllegalStateException e) {
92
93 }
94 }
95 }
96 }
97
98 else{
99 final String artifact = CommonUtils.safeGetParameter(request, this.artifactParameterName);
100 final HttpSession session = request.getSession(false);
101
102 if (CommonUtils.isNotBlank(artifact) && session!=null) {
103 try {
104 SESSION_MAPPING_STORAGE.removeBySessionById(session.getId());
105 } catch (final Exception e) {
106
107 }
108 SESSION_MAPPING_STORAGE.addSessionById(artifact, session);
109 }
110 }
111
112 filterChain.doFilter(servletRequest, servletResponse);
113 }
114
115 public void setSessionMappingStorage(SessionMappingStorage storage) {
116 SESSION_MAPPING_STORAGE = storage;
117 }
118
119 public static SessionMappingStorage getSessionMappingStorage() {
120 return SESSION_MAPPING_STORAGE;
121 }
122
123 public void destroy()
124 {
125 }
126 }
完成。
这样即可实现单点登出。(所有java应用的单点退出)
1)这样实现的效果是在登出的时候CAS Server 分发给各个客户端让各个客户端都登出,这个得让FIlter来获取,例子:一个index页面有两个链接一个指向java应用,一个指向php应用在java应用加filter 后能做出相应的动作退出动作,而对于php自己没加任何filter就没有退出。所以也得写个filter。
2)由于我们点击退出的时候请求CAS Server 而后Server分发任务让每个应用退出的消息,java程序通过filter来执行退出。
分享到此结束。希望大家多多捧场。
同时在了解CAS的同时,看到一篇不错的文章,在这里分享一下,主要阐述CAS从无到有的搭建过程,因为本人刚来CSDN发现文章不能加载附件,可到本人的CSDN中下载,免积分。