package com.laizhi.util; |
002 |
003 | import java.io.IOException; |
004 |
005 | import java.io.PrintWriter; |
006 |
007 | import java.io.UnsupportedEncodingException; |
008 |
009 | import javax.servlet.FilterChain; |
010 |
011 | import javax.servlet.ServletException; |
012 |
013 | import javax.servlet.http.Cookie; |
014 |
015 | import javax.servlet.http.HttpServletRequest; |
016 |
017 | import javax.servlet.http.HttpServletResponse; |
018 |
019 | import javax.servlet.http.HttpSession; |
020 |
021 | import java.security.MessageDigest; |
022 |
023 | import java.security.NoSuchAlgorithmException; |
024 |
025 | import com.laizhi.bean.User; |
026 |
027 | import com.laizhi.dao.UserDAO; |
028 |
029 | import com.laizhi.factory.DaoImplFactory; |
030 |
031 | import com.sun.org.apache.xerces.internal.impl.dv.util.Base64; |
032 |
033 | /* |
034 |
035 | * 2014.07.01 |
036 |
037 | * */ |
038 |
039 | public class CookieUtil { |
040 | //保存cookie时的cookieName |
041 | private final static String cookieDomainName = “laizhi”; |
042 | //加密cookie时的网站自定码 |
043 |
044 | private final static String webKey = “ 123456 ”; |
045 | //设置cookie有效期是两个星期,根据需要自定义 |
046 | private final static long cookieMaxAge = 60 * 60 * 24 * 7 * 2 ; |
047 | //保存Cookie到客户端------------------------------------------------------------------------- |
048 | //在CheckLogonServlet.java中被调用 |
049 | //传递进来的user对象中封装了在登陆时填写的用户名与密码 |
050 |
051 | public static void saveCookie(User user, HttpServletResponse response) { |
052 | //cookie的有效期 |
053 | long validTime = System.currentTimeMillis() + (cookieMaxAge * 5000 ); |
054 | //MD5加密用户详细信息 |
055 | String cookieValueWithMd5 =getMD5(user.getUserName() + ":" + user.getPassword() |
056 |
057 | + ":" + validTime + ":" + webKey); |
058 | //将要被保存的完整的Cookie值 |
059 | String cookieValue = user.getUserName() + ":" + validTime + ":" + cookieValueWithMd5; |
060 | //再一次对Cookie的值进行BASE64编码 |
061 |
062 | String cookieValueBase64 = new String(Base64.encode(cookieValue.getBytes())); |
063 | //开始保存Cookie |
064 | Cookie cookie = new Cookie(cookieDomainName, cookieValueBase64); |
065 | //存两年(这个值应该大于或等于validTime) |
066 | cookie.setMaxAge( 60 * 60 * 24 * 365 * 2 ); |
067 |
068 | //cookie有效路径是网站根目录 |
069 |
070 | cookie.setPath( "/" ); |
071 |
072 | //向客户端写入 |
073 |
074 | response.addCookie(cookie); |
075 |
076 | } |
077 |
078 | |
079 |
080 | //读取Cookie,自动完成登陆操作---------------------------------------------------------------- |
081 |
082 | //在Filter程序中调用该方法,见AutoLogonFilter.java |
083 |
084 | public static void readCookieAndLogon(HttpServletRequest request, HttpServletResponse response, |
085 |
086 | FilterChain chain) throws IOException, ServletException,UnsupportedEncodingException{ |
087 | //根据cookieName取cookieValue |
088 | Cookie cookies[] = request.getCookies(); |
089 | String cookieValue = null ; |
090 | if (cookies!= null ){ |
091 | for ( int i= 0 ;i |
092 | if (cookieDomainName.equals(cookies[i].getName())) { |
093 | cookieValue = cookies[i].getValue(); |
094 | break ; |
095 | } |
096 |
097 | } |
098 |
099 | } |
100 | //如果cookieValue为空,返回, |
101 | if (cookieValue== null ){ |
102 | return ; |
103 | } |
104 | //如果cookieValue不为空,才执行下面的代码 |
105 | //先得到的CookieValue进行Base64解码 |
106 | String cookieValueAfterDecode = new String (Base64.decode(cookieValue), "utf-8" ); |
107 | //对解码后的值进行分拆,得到一个数组,如果数组长度不为3,就是非法登陆 |
108 | String cookieValues[] = cookieValueAfterDecode.split( ":" ); |
109 | if (cookieValues.length!= 3 ){ |
110 | response.setContentType( "text/html;charset=utf-8" ); |
111 | PrintWriter out = response.getWriter(); |
112 | out.println( "你正在用非正常方式进入本站..." ); |
113 | out.close(); |
114 | return ; |
115 | } |
116 | //判断是否在有效期内,过期就删除Cookie |
117 | long validTimeInCookie = new Long(cookieValues[ 1 ]); |
118 | if (validTimeInCookie < System.currentTimeMillis()){ |
119 | //删除Cookie |
120 | clearCookie(response); |
121 | response.setContentType( "text/html;charset=utf-8" ); |
122 | PrintWriter out = response.getWriter(); |
123 | out.println( "" );你的Cookie已经失效,请重新登陆 |
124 | out.close(); |
125 | return ; |
126 | } |
127 | //取出cookie中的用户名,并到数据库中检查这个用户名, |
128 | String username = cookieValues[ 0 ]; |
129 | |
130 | //根据用户名到数据库中检查用户是否存在 |
131 | UserDAO ud = DaoImplFactory.getInstance(); |
132 | User user = ud.selectUserByUsername(username); |
133 |
134 | //如果user返回不为空,就取出密码,使用用户名+密码+有效时间+ webSiteKey进行MD5加密 |
135 | if (user!= null ){ |
136 | String md5ValueInCookie = cookieValues[ 2 ]; |
137 | String md5ValueFromUser =getMD5(user.getUserName() + ":" + user.getPassword() |
138 | + ":" + validTimeInCookie + ":" + webKey); |
139 | //将结果与Cookie中的MD5码相比较,如果相同,写入Session,自动登陆成功,并继续用户请求 |
140 | if (md5ValueFromUser.equals(md5ValueInCookie)){ |
141 | HttpSession session = request.getSession( true ); |
142 | session.setAttribute( "user" , user); |
143 | chain.doFilter(request, response); |
144 | } |
145 |
146 | } else { |
147 |
148 | //返回为空执行 |
149 | response.setContentType( "text/html;charset=utf-8" ); |
150 | PrintWriter out = response.getWriter(); |
151 | out.println( "cookie验证错误!" ); |
152 | out.close(); |
153 | return ; |
154 |
155 | } |
156 |
157 | } |
158 |
159 | |
160 |
161 | //用户注销时,清除Cookie,在需要时可随时调用----------------------------------------------------- |
162 | public static void clearCookie( HttpServletResponse response){ |
163 | Cookie cookie = new Cookie(cookieDomainName, null ); |
164 | cookie.setMaxAge( 0 ); |
165 | cookie.setPath( "/" ); |
166 | response.addCookie(cookie); |
167 | } |
168 |
169 | //获取Cookie组合字符串的MD5码的字符串---------------------------------------------------------------- |
170 | public static String getMD5(String value) { |
171 | String result = null ; |
172 | try { |
173 | byte [] valueByte = value.getBytes(); |
174 | MessageDigest md = MessageDigest.getInstance( "MD5" ); |
175 | md.update(valueByte); |
176 | result = toHex(md.digest()); |
177 | } catch (NoSuchAlgorithmException e2){ |
178 | e1.printStackTrace(); |
179 | } |
180 | return result; |
181 | } |
182 | //将传递进来的字节数组转换成十六进制的字符串形式并返回 |
183 | private static String toHex( byte [] buffer){ |
184 | StringBuffer sb = new StringBuffer(buffer.length * 2 ); |
185 | for ( int i = 0 ; i < buffer.length; i++){ |
186 | sb.append(Character.forDigit((buffer[i] & 0xf0 ) >> 4 , 16 )); |
187 | sb.append(Character.forDigit(buffer[i] & 0x0f , 16 )); |
188 | } |
189 | return sb.toString(); |
190 | } |
191 | } |