SpringSession详解~

=============================================================================
服务端如何识别特定的客户?
每次HTTP请求的时候,客户端都会发送响应的Cookie信息到服务端,实际上大多数的引用都用Cookie来实现Session跟踪的,第一次创建Session的时候,服务端会在HTTP协议中向客户端Cookie中记录一个SessionId,以后每次请求都会把这个会话ID发送到服务器,这样服务端就知道客户端是谁了
如果客户端的浏览器禁用了Cookie怎么办
一般这种情况下,会使用一种叫做URL重写的技术来进行session会话跟踪,即每次HTTP交互,URL都会被附加一个诸如sessionID=XXXXXX这样的参数,服务端根据此来识别客户端是谁。

session会话管理
在web项目开发中,session会话管理是一个很重要的部分,用于存储于记录用户的状态或相关的数据,通常情况下session交由容器(tomcat)来负责春促和管理,但是如果项目部署在多台tomcat中,则session管理存在很大的问题
1.多台tomcat之间无法共享session,
2.一旦tomcat容器管理或重启也会导致session会话失效
因此如果项目部署在多台tomcat中,就需要解决session共享的问题
解决办法:
1.基于Tomcat的tomcat-Redis-session-manager
基于jetty的jetty-session-redis插件,memcached-session-manager插件
2.使用Nginx负载均衡Ip_hash,策略实现用户每次访问都绑定到同一台具体后台tomcat服务器实现session总是存在
3.自己写一套色杀死你回话管理的工具类,在需要使用会话的时候都从自己的工具类中获取,而工具类后端存储可以放在Redis中,这个方案灵活性好,单开发需要一定额外时间。
4.使用框架的会话管理工具,也就是我们要介绍的spring-session,这个方案既不依赖tomcat容器,又不需要改动代码,由spring session框架为我们提供,可以说是非常完美的session共享解决方案。

session共享
1.在pom文件中添加spring-session的Maven依赖

<dependency>
    <groupId>org.springframework.session</groupId>
    <artifactId>spring-session</artifactId>
    <version>1.3.1.RELEASE</version>
</dependency>
<!-- Spring Session 依赖end -->

<!-- Spring session redis 依赖start -->
<dependency>
    <groupId>org.springframework.session</groupId>
    <artifactId>spring-session-data-redis</artifactId>
    <version>1.3.1.RELEASE</version>
</dependency>
<!-- Spring session redis 依赖end -->

<!-- spring-data-redis依赖的JAR配置start -->
<dependency>
    <groupId>org.springframework.data</groupId>
    <artifactId>spring-data-redis</artifactId>
    <version>1.8.8.RELEASE</version>
</dependency>
<!-- spring-data-redis依赖的JAR配置end -->

<!-- jedis依赖的JAR配置start -->
<dependency>
    <groupId>redis.clients</groupId>
    <artifactId>jedis</artifactId>
    <version>2.9.0</version>
</dependency>
<!-- jedis依赖的JAR配置end -->

<!-- spring web模块依赖 start -->
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-web</artifactId>
    <version>4.3.10.RELEASE</version>
</dependency>
<!-- spring web模块依赖end -->

,

<dependency>
    <groupId>javax.servlet</groupId>
    <artifactId>javax.servlet-api</artifactId>
    <version>3.1.0</version>
</dependency>
<!-- servlet依赖的jar包start -->

<!-- jsp依赖jar包start -->
<dependency>
    <groupId>javax.servlet.jsp</groupId>
    <artifactId>javax.servlet.jsp-api</artifactId>
    <version>2.3.1</version>
</dependency>
<!-- jsp依赖jar包end -->

<!--jstl标签依赖的jar包start -->
<dependency>
    <groupId>javax.servlet</groupId>
    <artifactId>jstl</artifactId>
    <version>1.2</version>
</dependency>
<!--jstl标签依赖的jar包end -->
2.在web.xml文件文件中配置springSessionRepositoryFilter过滤器 springSessionRepositoryFilter org.springframework.web.filter.DelegatingFilterProxy springSessionRepositoryFilter /* contextConfigLocation classpath:applicationContext.xml org.springframework.web.context.ContextLoaderListener 3.在applicationContext.xml中导入springsession配置文件 4.Spring配置文件配置一个RedisHttpSessionConfiguration类


<context:property-placeholder location=“classpath:redis.properties”/>
5.redis的配置文件
redis.hostName=192.168.200.128
redis.port=6379
redis.password=123456
redis.usePool=true
redis.timeout=15000

同域名下相同项目实现session共享、
在p2p项目部署在nginx上实现负载均衡(轮询)后,到时项目无法保存session从而登录不上
最简单的办法将负载均衡策略改成ip_hash即可

还有一种方法就是加入spring-session的jar包
在web.xml加入spring-session所需要的全局过滤器(springmvc的容器如果原来启动过了,就不需要添加)
添加spring-session和redis-config配置文件 、
在总配置文件导入spring-session的配置文件

同域名下不同项目实现session共享
我们需要把cookie的路径设置文根/上下文路径





他们存放的path不一样,是两个不同的cookie,浏览器发现是两个不同的请求,我们需要把cookie存放在斜杠下,这样就可以了。

同根域名不同二级子域名下的项目实现session共享
同根域名 例如 :www.web.combeijign.web.com 和 nanjing.web.com这三个就是同根域名
其中 www.web.com 成为顶级域名 或者 根域名 而 beijing.web.com 和 nanjing.web.com成为二级域名 或者叫做 子域名 。
redis 的核心配置文件 daemonize yes(默认redis是后台启动)
4在浏览器解析我们输入的网页的时候首先去本地C:\Windows\System32\drivers\etc的Host文件中查看有没有指向我们本地的ip地址,如果没有再去网络上的DNS库去解析这个域名所对应的ip地址。
域名不同的时候默认session没有共享,主要原因是因为存放session的时候域名不同。所以当cookie的域名不一样或者路径不一样,他是共享不了session的,因为服务器端会认为这是两个不同的session,
要是想要可以共享session的时候,可以把域名改成一样的。但是不可以随便改,因为访问的时候的域名和cookie存放的域名必须要一致的,所以我们可以采用地址的跟域名来存放,
要实现同根域名,不同二级子域名实现session共享 :
1.设置cookie路径为根/上下文;(项目名一样的话,可以不设置)
2.设置域名为同域名 web.com;







(不同项目的路径和域名一致这样就可以了)

不同根域名下的项目实现session共享
对于不同根域名的场景,要实现一处登录,处处登录,spring session不支持。
对于这种情况,需要开发一个单点登录系统(Single Sign On)简称SSO,SSO是指在多个应用系统中,用户只需要登录一次就可以访问所有相互信任的应用系统。

springSession的执行流程,
@Bean注解 相当于
方法的名字就是Bean的ID,方法的返回值就是class。
1.页面请求被全局过滤器org.springframerwork.web.filter.DelegatingFilterProxy过滤。
2.全局的过滤器是一个代理过滤器,他不执行真正的过滤编辑,它代理了一个spring容器中名为:springSessionRepostoryFilter的一个过滤器
3.代理的这个springSessionRepostoryFilter过滤器是从spring容器中获取的,真正执行过滤逻辑的是sessionRepostoryFilter。
4.该SessionRepositoryFilter过滤器覆盖了原来servlet中的request和Response接口定义的操作session方法,替换成自己的session方法。
5.在过滤的时候,总是会执行一个finally语句块,在finally中提交session,保存到Redis.

session以Hash结构存放在Redis中。
session的默认存放时间是30分钟(在session的配置文件中)


  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值