文章目录
- 1. Session 共享
- 1.0 cookie和session的工作流
- 1.1 Cookie范围
- 1.2 为什么要共享?
- 1.3 如何共享存储
- 1.4 session共享实现
1. Session 共享
1.0 cookie和session的工作流
在 Web 开发中,Cookie 和 Session 是非常常见的,尤其是在处理用户身份验证、会话管理等方面。
-
用户提交登录请求:
用户通过登录页面提交用户名和密码。 -
服务器验证用户信息:
服务器接收到登录请求后,验证用户提供的用户名和密码是否正确。 -
创建 Session:
如果验证通过,服务器生成一个唯一的 Session ID,并在服务器端创建一个 Session 来存储用户的相关信息(如用户 ID、用户名、权限等)。服务器将这个 Session ID 存储在 Session 对象中,并设置一个过期时间。
-
发送 Session ID 到客户端:
服务器通过响应头,在响应头中设置 Set-Cookie,Set-cookie中包含了 Session ID。 -
浏览器发送请求:
客户端收到响应后,如果服务器给了Set-cookie,当用户在登录后访问其他页面时,浏览器会自动将包含 Session ID 的 Cookie 附加到每个 HTTP 请求中。 -
服务器验证 Session:
服务器接收到请求后,会检查请求中的 Cookie,提取出 Session ID。
服务器使用这个 Session ID 查找对应的 Session,以确定该用户的身份,并获取相关的用户数据。
1.1 Cookie范围
-
Cookie存储在客户端且不可跨域。
-
种session的时候注意范围,可以在配置的cookie.domain进行设置
如果要共享cookie,可以种一个更高层的公共域名。 -
比如,前端localhost:3000访问,分配cookie;后4000访问,又重新分配cookie。设置成更高的公共域名localhost之后,4000、5000等再访问的时候,不用重新给分配cookie了。
server:
port: 8080
servlet:
context-path: /api
session:
cookie:
domain: localhost
1.2 为什么要共享?
-
为什么服务器A登陆后,请求发到服务器B,B不认识该用户?
原因:请求发到服务器A上,session(用户登录信息)存在A的内存中。
此时B的内存没有该用户的sessionID,因此不认识该用户。
解决方案:共享存储,把session存储到A和B都能读取到的中间件中,可以使用redis、mysql、文件服务器ceph等;而不是把数据放到单台服务器的内存中。
1.3 如何共享存储
核心思想:把数据放到同一个地方集中管理。
- Redis。用户信息读取 / 是否登录的判断及其频繁,Redis是基于内存的键值存储系统,读写性能很高,简单的数据单机qps能达到5w-10w。
- MySQL
- 文件服务器,如ceph
1.4 session共享实现
redis的云上装载参考:Java相关工具/插件的安装教程汇总
- 引入redis → 能够操作redis。
<!-- https://mvnrepository.com/artifact/org.springframework.boot/spring-boot-starter-data-redis -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
<version>2.6.4</version>
</dependency>
redis管理工具:quick redis,能看到存进来的session信息等。
- 引入spring-session 和 redis 的整合,使得自动将session存储到redis中。
<!-- https://mvnrepository.com/artifact/org.springframework.session/spring-session-data-redis -->
<dependency>
<groupId>org.springframework.session</groupId>
<artifactId>spring-session-data-redis</artifactId>
<version>2.6.3</version>
</dependency>
- 修改spring-session存储配置,改application.yml的配置。
原来session只设置了timeout过期时间,现在要加一个store-type。
spring.session.store-type默认是none,表示存储在服务器
设置成:store-type:redis 表示从 redis 读写 session
Spring:
session:
timeout: 86400
store-type: redis