`
ws715
  • 浏览: 20646 次
  • 性别: Icon_minigender_1
  • 来自: 武汉
社区版块
存档分类
最新评论

Apache.Tomcat整合,用cookie取代Tomcat之间Session的复制

阅读更多

公司网站用Apache+Tomcat集群后,经过观察发现Tomcat之间的Session复制非常的消耗资源。一个Tomcat挂掉后,另外一个要复制很久才能复制完成。导致如果session很多,一个Tomcat挂掉,网站访问变得很慢.

现在改成Cookie来取替Tomcat之间的复制,具体实现方式如下:

 

登录时将用户信息存入一份在Session中,然后向用户的本机中插入一条cookie信息。由于去掉了Tomcat之间Session的复制所以需要用到Session业务的时候,在一个Tomcat中有session信息,如果在这个过程中被分配到另外一个Tomcat运行后就会出现找不到Session信息的错误。考虑到这一条我写了一个过滤器来对网站的请求进行过滤,先判断session中有没有值。如果有就过,如果没有就到本地来取一次cookie,如果存在即在当前Tomcat上恢复Session.代码如下

 

Cookie工具类

import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

/**
 * Cookie 工具类增,删,查
 * 
 * @author ws715
 * 
 */
public class CookieUtil {
	/**
	 * 按名字得到Cookie
	 * 
	 * @param request
	 * @param name
	 * @return
	 */

	private CookieUtil() {
	}

	public static Cookie getCookie(HttpServletRequest request, String name) {
		Cookie cookies[] = request.getCookies();
		if (cookies == null || name == null || name.length() == 0) {
			return null;
		}
		if (cookies != null) {
			for (int i = 0; i < cookies.length; i++) {
				if (name.equals(cookies[i].getName())) {
					return cookies[i];
				}
			}
		}
		return null;
	}

	/**
	 * 将cookie中的数据保存到session中
	 * 
	 * @param request
	 * @param name
	 * @return
	 */
	public static boolean setSessionFormCookie(HttpServletRequest request,
			String name) {

		String target = null;
		Cookie cookies[] = request.getCookies();
		boolean bool = false;
		if (cookies == null || name == null || name.length() == 0) {
			bool = false;
		}

		if (cookies != null) {

			for (int i = 0; i < cookies.length; i++) {

				if (name.equals(cookies[i].getName())) {
					target = cookies[i].getValue();
					break;
				}
			}

		}

		if (target != null && !target.equals("")) {

			HttpSession session = request.getSession();
			session.setAttribute("UserName", target.toString());
			bool = true;
		}
		return bool;
	}

	/**
	 * 删除Cookie
	 * 
	 * @param request
	 * @param response
	 * @param cookie
	 */
	public static void deleteCookie(HttpServletRequest request,
			HttpServletResponse response, Cookie cookie) {
		if (cookie != null) {
			cookie.setPath(getPath(request));
			cookie.setValue("");
			// cookie.setDomain("");
			cookie.setMaxAge(0);
			response.addCookie(cookie);
		}
	}

	/**
	 * 按名字删除
	 * 
	 * @param request
	 * @param response
	 * @param name
	 */
	public static void deleteCookie(HttpServletRequest request,
			HttpServletResponse response, String name) {

		Cookie cookies[] = request.getCookies();
		Cookie myCookie = null;
		boolean bool = false;
		if (cookies == null || name == null || name.length() == 0) {
			throw new NullPointerException(
					"getCookie deleteCookie method name is not null");
		}
		if (cookies != null) {
			for (int i = 0; i < cookies.length; i++) {
				if (name.equals(cookies[i].getName())) {
					myCookie = cookies[i];
					break;
				}
			}

			if (myCookie != null) {
				deleteCookie(request, response, myCookie);
			}
		}
	}

	/**
	 * 保存到Cookie中
	 * 
	 * @param request
	 * @param response
	 * @param name
	 * @param value
	 */
	public static void setCookie(HttpServletRequest request,
			HttpServletResponse response, String name, String value) {
		setCookie(request, response, name, value, 0x278d00);
	}

	/**
	 * 可以设置时间
	 * 
	 * @param request
	 * @param response
	 * @param name
	 * @param value
	 * @param maxAge
	 */
	public static void setCookie(HttpServletRequest request,
			HttpServletResponse response, String name, String value, int maxAge) {
		Cookie cookie = new Cookie(name, value == null ? "" : value);
		cookie.setMaxAge(maxAge);
		// cookie.setDomain(request.getServerName());
		cookie.setPath(getPath(request));
		response.addCookie(cookie);
	}

	private static String getPath(HttpServletRequest request) {
		String path = request.getContextPath();
		return (path == null || path.length() == 0) ? "/" : path;
	}

	/**
	 * 从cookie中获得username
	 * 
	 * @param request
	 * @param name
	 * @return
	 */

	public static String getUserNameForCookie(HttpServletRequest request,
			String name) {
		String username = "";
		Cookie cookies[] = request.getCookies();
		if (cookies == null || name == null || name.length() == 0) {
			return null;
		}

		if (cookies != null) {

			for (int i = 0; i < cookies.length; i++) {

				if (name.equals(cookies[i].getName())) {
					try {
						username = (cookies[i].getValue().split("#"))[0];
					} catch (Exception e) {
						username = null;
					}
				}
			}

		}
		return username;
	}

}

 

过滤器

 

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

public class SessionCookieFilter implements Filter {

	public void destroy() {
		// TODO Auto-generated method stub
		
	}

	public void doFilter(ServletRequest request, ServletResponse response,
			FilterChain chain) throws IOException, ServletException {
		// TODO Auto-generated method stub
		    HttpServletRequest httpServletRequest = (HttpServletRequest) request;
	        HttpServletResponse httpServletResponse = (HttpServletResponse) response;
	        // 通过检查session中的变量,过虑请求
	        HttpSession session = httpServletRequest.getSession();
	        
	        String   UserName="guest" ;
	        
	 
	        if(session.getAttribute("UserName")==null || 
session.getAttribute("UserName").equals("guest")){ 
	        
	         if(!com.pixel.util.CookieUtil.setSessionFormCookie(httpServletRequest,"cookiename")){  
	        	   session.setAttribute("UserName",UserName);
	        }
	        }
	        
	        chain.doFilter(request, response);  
	}

	public void init(FilterConfig arg0) throws ServletException {
		// TODO Auto-generated method stub
	}

}

 

登录时加入cookie中

 

						 CookieUtil.setCookie(request,response,"cookiename",cookieValue.toString(),60*120);     
 

不知道还有没有更好的办法和改进的余地

分享到:
评论
2 楼 ws715 2009-02-05  
wuyuwentian 写道
这样做是不安全的,我们都知道cookie的值是能被伪造的,我觉得你应该对cookie的值加密,服务端需要回复session的时候需要验证cookie的有效性

除了安全,还有别的可以改进吗?
1 楼 wuyuwentian 2009-02-05  
这样做是不安全的,我们都知道cookie的值是能被伪造的,我觉得你应该对cookie的值加密,服务端需要回复session的时候需要验证cookie的有效性

相关推荐

    tomcat修改jsessionid在cookie中的名称

    在Tomcat 5.x 版本中,可以通过设置系统属性 `org.apache.catalina.SESSION_COOKIE_NAME` 来更改JSessionID在Cookie中的名称。具体操作步骤如下: 1. **Linux环境:** ```bash JAVA_OPTS="-Dorg.apache.catalina....

    tomcat redis session.rar

    【描述】:“Tomcat集群Nginx使用Redis保证Session同步”这一场景中,通常是因为在多台Tomcat服务器组成的集群中,每个服务器各自维护独立的Session,当用户在集群中的不同服务器之间切换时,可能会导致Session丢失...

    apache+tomcat配置文件

    6. **Session粘滞(Session Stickiness)**:为了保持用户会话的连续性,可以配置mod_proxy_balancer来基于特定的会话ID或cookie将请求始终路由到同一个Tomcat实例。 7. **安全性**:使用SSL/TLS证书进行HTTPS配置...

    Apache2.2 tomcat-6.0.18负载均衡与集群

    Tomcat的集群功能依赖于org.apache.catalina.ha.session.JvmRouteBinderValve,它添加了JVM路由信息到Cookie,使得请求能够正确地发送到保存会话的服务器。此外,还需要配置共享的session存储,例如使用memcached或...

    Apache2.4+tomcat7集群

    5. 配置session复制或粘滞会话:保持用户会话在集群中的连续性,可以通过session复制或者使用粘滞会话(基于cookie或IP哈希)来实现。 6. 测试和监控:完成配置后,通过测试各种请求来验证集群是否工作正常,并使用...

    Tomcat7+Redis+Session 负载之后session 共享 tomcat jar包

    标题 "Tomcat7+Redis+Session 负载之后session 共享 tomcat jar包" 涉及的是在使用Nginx做负载均衡时,如何通过集成Redis来实现Tomcat7服务器之间的Session共享,从而确保用户在不同服务器之间切换时仍然能够保持...

    tomcat+redis共享session所需jar包

    Tomcat Redis Session Manager是一个插件,允许Tomcat将Session数据存储在Redis中,以便多个Tomcat实例之间共享。 以下是压缩包中提供的jar包及其作用: 1. tomcat-catalina-7.0.27.jar:这是Tomcat的主要组件之一...

    Apache+tomcat集群环境配置

    - **cookie复制**:将session ID存储在cookie中,每次请求时,用户携带session ID到达任意节点,节点根据ID查找session。 - **共享内存**:所有Tomcat实例共享同一内存区域,session存储其中,但这种方法限制了集群...

    Tomcat8亲测可用 tomcat-redis-session-manager的jar包

    标题中的“Tomcat8亲测可用 tomcat-redis-session-manager的jar包”指的是一个专为Tomcat8设计的,用于管理session的扩展组件。这个组件实现了将Tomcat应用服务器中的用户session数据存储到Redis分布式缓存系统中,...

    tomcat7整合redis实现session共享,jar包带配置方法

    Tomcat作为广泛使用的Java Servlet容器,可以通过整合其他技术,如Redis这样的内存数据存储系统,来实现跨服务器的session共享。本篇文章将深入讲解如何在Tomcat7中整合Redis,以实现session的共享,并提供必要的jar...

    apache+tomcat

    3. session ID管理:使用cookie或URL重写等方式保存session ID,确保请求能在不同的Tomcat实例间正确转发。 4. 故障转移:当某个Tomcat实例发生故障时,Apache应能够自动将请求切换到其他正常工作的实例,保证服务...

    tomcat8-redis-session共享

    标题 "tomcat8-redis-session共享" 涉及到的是在Tomcat 8中使用Redis作为Session共享存储的解决方案。这是一个常见的需求,特别是在分布式系统中,为了保持用户会话的一致性,需要将Session数据在多台服务器之间共享...

    tomcat-session共享

    - 在Tomcat的`conf/context.xml`或应用的`WEB-INF/web.xml`中添加`Manager`元素,指定使用`org.apache.catalina.session.PersistentManager`,并配置相关的Redis连接参数,如主机、端口、密码等。 - 配置Tomcat...

    Tomcat_Session的持久化

    Tomcat 实现持久 Session Store 的接口为 org.apache.Catalina.store,目前提供了两个实现这一接口的类:org.apache.Catalina.FileStore 和 org.apache.Catalina.JDBCStore。 FileStore 将 HttpSession 对象保存在...

    apache+tomcat负载均衡整合文档

    以下是实现Apache+Tomcat负载均衡整合的详细步骤: 1. **安装与配置Apache**: - 安装Apache HTTP服务器,并确保已启用mod_proxy、mod_proxy_balancer和mod_proxy_http模块。这些模块通常在默认的Apache安装中已经...

    Windows下Apache2.2+Tomcat6配置集群、负载均衡、session共享

    3. **使用cookie**:在cookie中存储session ID,每次请求时携带,Apache通过stickysession指令将请求定向到对应的Tomcat实例。 通过以上配置,我们可以构建一个高可用、负载均衡的Web服务系统。在实际操作中,还...

    Tomcat 6 集群配置 session 共享 同一台机器

    3. **Session复制**:Tomcat使用`org.apache.catalina.ha.session.DeltaManager`作为默认的集群session管理器,它负责在集群节点间同步session数据。DeltaManager使用序列化将session对象在节点间传输。 4. **...

    tomcat-redis配置session共享

    3. **配置Session管理器**:Tomcat提供了`MemcachedSessionManager`和`org.apache.catalina.session.PersistentManagerBase`,但这里我们将使用`RedisSessionManager`。首先,添加`tomcat-redis-session-manager`...

    apache-tomcat-9.0.24.rar

    可以使用Session对象或者Cookie来保存验证码值。 4. **用户输入验证**:用户提交验证码后,服务器会接收到用户输入的值。这时,需要对比用户输入与服务器存储的验证码是否一致,如果匹配则验证成功。 在Apache ...

Global site tag (gtag.js) - Google Analytics