什么是 Session?Web 开发中 Session 的使用与注意事项

什么是 Session?Web 开发中 Session 的使用与注意事项

✅ 引言

在 Web 开发中,HTTP 协议是无状态的,这意味着每次请求之间没有关联。为了实现用户登录、购物车、权限控制等功能,服务器需要一种机制来“记住”用户。Session(会话) 就是解决这一问题的核心技术之一。

本文将深入讲解:

  • 什么是 Session?
  • Session 的工作原理
  • 在 Java Web 和 Spring Boot 中如何使用 Session
  • 使用 Session 的最佳实践与常见注意事项
  • 安全风险与应对策略

并提供完整的 Java + Spring Boot 示例代码,帮助你全面掌握 Session 的使用。


📌 一、什么是 Session?

1.1 基本定义

Session(会话)是服务器端用于保存用户状态的一种机制。当用户访问服务器时,服务器为其创建一个唯一的会话(Session),并在内存或存储中保存该用户的相关信息(如登录状态、用户ID等)。

每个 Session 都有一个唯一的 Session ID,通常通过 Cookie 发送给客户端,后续请求中客户端携带该 ID,服务器据此识别用户。想象 Session 就像超市给你的会员卡,第一次访问时服务器给你生成一张唯一的 “会员卡”(Session ID),以后每次访问你都出示这张卡,服务器就能通过卡片识别你的身份和之前的操作记录。

1.2 工作流程图解

在这里插入图片描述

1.3 Session 的工作原理

Session的工作流程可以分为四个阶段:

  1. 创建阶段:当用户第一次访问服务器时,服务器会生成一个唯一的Session ID,并创建对应的Session对象存储用户数据。
  2. 传输阶段:服务器通过Set-Cookie响应头,将Session ID发送给客户端,客户端会将其保存在Cookie中。
  3. 验证阶段:后续请求中,客户端会自动在Cookie中携带Session ID,服务器通过这个ID找到对应的Session对象。
  4. 销毁阶段:当用户登出或会话超时后,服务器会删除Session对象,客户端Cookie也会被清除或标记为过期。

📌 二、Session 的使用场景

  • 用户登录状态保持
  • 购物车信息存储
  • 表单防重复提交
  • 一次性验证码(如短信验证码)
  • 权限控制与访问记录

📌 三、Java Web 中使用 Session(原生 Servlet)

3.1 获取或创建 Session

@WebServlet("/login")publicclassLoginServletextendsHttpServlet{@OverrideprotectedvoiddoPost(HttpServletRequest req,HttpServletResponse resp){String username = req.getParameter("username");// 获取或创建 SessionHttpSession session = req.getSession();// 存储用户信息 session.setAttribute("username", username); session.setAttribute("loginTime",newDate()); resp.getWriter().println("登录成功,欢迎 "+ username);}}

3.2 读取 Session 数据

@WebServlet("/profile")publicclassProfileServletextendsHttpServlet{@OverrideprotectedvoiddoGet(HttpServletRequest req,HttpServletResponse resp){HttpSession session = req.getSession(false);// 不自动创建if(session !=null&& session.getAttribute("username")!=null){String username =(String) session.getAttribute("username");Date loginTime =(Date) session.getAttribute("loginTime"); resp.getWriter().println("用户:"+ username +",登录时间:"+ loginTime);}else{ resp.setStatus(401); resp.getWriter().println("请先登录");}}}

3.3 注销 Session

@WebServlet("/logout")publicclassLogoutServletextendsHttpServlet{@OverrideprotectedvoiddoGet(HttpServletRequest req,HttpServletResponse resp){HttpSession session = req.getSession(false);if(session !=null){ session.invalidate();// 销毁 Session} resp.getWriter().println("已退出登录");}}

📌 四、Spring Boot 中使用 Session

4.1 启用 Session 支持(默认已开启)

@RestControllerpublicclassUserController{@PostMapping("/login")publicStringlogin(@RequestParamString username,HttpServletRequest request){HttpSession session = request.getSession(); session.setAttribute("username", username);return"登录成功,用户:"+ username;}@GetMapping("/info")publicStringgetUserInfo(HttpServletRequest request){HttpSession session = request.getSession(false);if(session !=null&& session.getAttribute("username")!=null){return"当前用户:"+ session.getAttribute("username");}return"未登录";}@GetMapping("/logout")publicStringlogout(HttpServletRequest request){HttpSession session = request.getSession(false);if(session !=null){ session.invalidate();}return"已退出";}}

4.2 使用 @SessionAttribute 注解(更优雅)

@Controller@SessionAttributes("user")publicclassSessionController{@PostMapping("/login")publicStringlogin(@RequestParamString username,Model model){ model.addAttribute("user",newUser(username));return"redirect:/dashboard";}@GetMapping("/dashboard")publicStringdashboard(@SessionAttribute("user")User user,Model model){ model.addAttribute("user", user);return"dashboard";}}

📌 五、Session 的注意事项与最佳实践

5.1 安全性问题

风险解决方案
Session 劫持使用 HTTPS、设置 SecureHttpOnly Cookie
Session 固定攻击登录成功后调用 session.invalidate() 并创建新 Session
Session 泄露敏感信息不要存入 Session(如密码)
// 在 Spring Boot 中配置 server.servlet.session.cookie.http-only=true server.servlet.session.cookie.secure=true server.servlet.session.cookie.same-site=strict 

5.2 性能与可扩展性

  • 内存占用:Session 默认存储在服务器内存中,大量用户会消耗内存。
  • 集群部署问题:多台服务器时,Session 无法共享。
解决方案:
  • 使用 Redis 存储 Session(推荐)
  • 使用 Spring Session + Redis
<!-- pom.xml --><dependency><groupId>org.springframework.session</groupId><artifactId>spring-session-data-redis</artifactId></dependency>
# application.ymlspring:session:store-type: redis redis:host: localhost port:6379

5.3 Session 过期时间

# application.ymlserver:servlet:session:timeout: 30m # 30分钟

或在代码中设置:

session.setMaxInactiveInterval(1800);// 秒

✅ 总结

项目说明
Session 本质服务器端状态保持机制
核心原理通过 Session ID 识别用户
优点简单易用、数据安全(不暴露给客户端)
缺点占用服务器资源、集群部署需共享
最佳实践使用 Redis 存储、设置合理过期时间、防止 Session 劫持
替代方案JWT(无状态认证)

📚 推荐

Read more

【前端小站】CSS 样式美学:从基础语法到界面精筑的实战宝典

【前端小站】CSS 样式美学:从基础语法到界面精筑的实战宝典

半桔:个人主页  🔥 个人专栏: 《前端扫盲》《手撕面试算法》《C++从入门到入土》 🔖阻止了我的脚步的,并不是我所看见的东西,而是我所无法看见的那些东西。 《海上钢琴师》 文章目录 * 前言 * 一. CSS是什么 * 1.1 概念 * 1.2 基本语法 * 二. CSS如何引入HTML * 2.1 内部样式表 * 2.2 行内选择器 * 2.3 外部引入 * 三. CSS选择器 * 3.1 基础选择器 * 3.1.1 标签选择器 * 3.1.2 类选择器 * 3.1.3 id选择器 * 3.

黑马程序员java web学习笔记--后端进阶(二)SpringBoot原理

目录 1 配置优先级 2 Bean的管理 2.1 Bean的作用域 2.2 第三方Bean 3 SpringBoot原理 3.1 起步依赖 3.2 自动配置 3.2.1 实现方案 3.2.2 原理分析 3.2.3 自定义starter 1 配置优先级 SpringBoot项目当中支持的三类配置文件: * application.properties * application.yml ❤ * application.yaml 配置文件优先级排名(从高到低):properties配置文件 > yml配置文件 > yaml配置文件 虽然springboot支持多种格式配置文件,但是在项目开发时,推荐统一使用一种格式的配置。

前端文件上传处理:别再让用户等待了!

前端文件上传处理:别再让用户等待了! 毒舌时刻 文件上传?听起来就像是前端工程师为了显得自己很专业而特意搞的一套复杂流程。你以为随便加个input[type=file]就能实现文件上传?别做梦了!到时候你会发现,大文件上传会导致页面崩溃,用户体验极差。 你以为FormData就能解决所有问题?别天真了!FormData在处理大文件时会导致内存溢出,而且无法显示上传进度。还有那些所谓的文件上传库,看起来高大上,用起来却各种问题。 为什么你需要这个 1. 用户体验:良好的文件上传处理可以提高用户体验,减少用户等待时间。 2. 性能优化:合理的文件上传策略可以减少服务器负担,提高上传速度。 3. 错误处理:完善的错误处理可以避免上传失败时的用户困惑。 4. 安全保障:安全的文件上传处理可以防止恶意文件上传,保障系统安全。 5. 功能丰富:支持多文件上传、拖拽上传、进度显示等功能,满足不同场景的需求。 反面教材 // 1. 简单文件上传 <input type="file&

Java Web 开发环境搭建:IDEA+Tomcat 安装与部署超详细教程

Java Web 开发环境搭建:IDEA+Tomcat 安装与部署超详细教程

在 Java Web 开发中,IDEA 作为主流的集成开发工具,搭配 Tomcat 轻量级 Web 服务器是入门首选。本文将基于 Java Web 基础开发要求,从 JDK 环境配置、Tomcat 安装配置、IDEA 安装、Web 项目创建,到 Tomcat 在 IDEA 中的部署运行,进行一步一图式详细讲解,零基础也能轻松上手。 一、前置准备:JDK 环境配置 Java Web 开发的核心基础是 JDK,Tomcat 和 IDEA 的运行都依赖 JDK 环境,需先完成 JDK 的安装与环境变量配置。 1. 下载与安装