首页 > 编程语言 >Java 实战介绍 Cookie 和 Session 的区别

Java 实战介绍 Cookie 和 Session 的区别

时间:2023-06-13 09:00:50浏览次数:46  
标签:session Java 请求 Session Cookie 服务端 客户端

HTTP 是一种不保存状态的协议,即无状态协议,HTTP 协议不会保存请求和响应之间的通信状态,协议对于发送过的请求和响应都不会做持久化处理。

无状态协议减少了对服务压力,如果一个服务器需要处理百万级用户的请求状态,对服务器的压力无疑的是巨大的。

无状态的 HTTP 由于其简单和易用性,应用比较管广泛。而且早期的 Web 服务对于状态的需求也很低,所以应用场景也比较广泛。

随着 Web 的不断发展,越来越多的服务需要记录用户的登录状态,比如购物、聊天、论坛服务,请求都是无状态的服务,服务器就无法识别是 HTTP 请求的用户信息,所以就需要一种技术保存用户的状态,也就 Cookie 技术,有了 Cookie 的 HTTP 协议通信,就能保存状态了。

Cookie

在无状态协议不受影响的基础上,通过引入 Cookie 来记录状态,这样既不会影响原有的功能,也可以解决请求状态问题。Cookie 是当你浏览网页,通过服务器记录你的用户名,密码等网页信息。

Cookie 是由服务端创建,客户端向服务发送请求后,服务端通过响应报文的Set-Cookie 字段将 Cookie 信息返回给客户端,客户端自动保存 Cookie。Cookie 会标记来源、有效期、路径等信息。客户端再次请求该服务端时,会自动将 Cookie 添加到请求报文中(Request Header),服务端就能通过传递的 Cookie 识别客户端的信息。

1.没有 Cookie 信息的请求

2.再次(有了Cookie信息后)发送请求

使用 Spring Boot 创建简单的 Controller,当客户端传递的参数 a 有值时,服务端才添加 Cookie:

@GetMapping("/cookie")
@ResponseBody
public String cookie(String a, HttpServletRequest request, HttpServletResponse response) {
    if (a != null) {
        Cookie cookie = new Cookie("name",a);
        response.addCookie(cookie);
    }
    return "ok";
}

首先使用 Chrome 浏览器发送请求http://localhost:8080/cookie:

返回结果没有 Cookie。

再发送带有 a 参数的请求http://localhost:8080/cookie?a=jeremy:

返回 Cookie 都存在 Set-Cookie 字段中,客户端会自动保存 Cookie。

再次发送相同的请求http://localhost:8080/cookie?a=jeremy:

请求会将客户端的 Cooike 自动添加到请求报文中,此时服务端也能接收到 Cookie信息:

Session

Session 是服务端保存用户状态的一种机制,当用户访问网站时,服务端会为每个用户创建唯一个会话标识,并根据用户登录请求创建和存储会话信息,客户端再次请求时,就能从服务端获取会话信息了。

Session 简单实践

在 Java 中的 Servlet 提供 HttpSession 的接口来操作会话信息,只要有以下几个方法:

  • public HttpSession getSession() 获取会话信息,如果不存在就创建会话信息。
  • public String getId() 获取唯一的会话 id。
  • public void invalidate() 将会话信息失效,一般注销时候使用。

HttpSession 接口通过 getAttribute() 和 setAttribute() 来获取和设置会话信息,
下面创建两个方法,session() 方法获取会话判断用户是否登录,login() 方法添加会话信息。

@GetMapping("/session")
@ResponseBody
public String session(HttpServletRequest request, HttpServletResponse response) {
    HttpSession session = request.getSession();
    Boolean login =(Boolean) session.getAttribute("login");
    String loginInfo;
    if (login == null) {
        loginInfo = "未登录";
    } else {
        loginInfo = "已登录";
    }
    return "session id :" + session.getId() + ":" + loginInfo;
}

@GetMapping("/login")
@ResponseBody
public String login(HttpServletRequest request) {
    HttpSession session = request.getSession();
    session.setAttribute("login",true);
    return "ok";
}

先请求 http://localhost:8080/session,返回如下信息:

session id :F3C560208A54E3D5B465CDEBE7419817:未登录

多次发送请求,session id 是一致的,说明 session id是在会话周期之内(浏览器不关闭)都是不变的。

然后请求登录接口 http://localhost:8080/login,设置了会话信息之后,再请求 http://localhost:8080/session:返回如下信息:

session id :F3C560208A54E3D5B465CDEBE7419817:已登录

同一个用户请求,服务端会创建唯一的会话,在请求的生命周期之内,会话 id 一直不改变。session 会话由服务端添加后,后续请求就能获取到会话信息,会话信息只存储在服务端。

Cookie 和 Session 的区别

Cookie 是存储在客户端上小型文本,是由服务端创建,然后通过响应报文的 Set-Cookie 字段返回给客户端。客户端每次请求服务端吗,浏览器都会将 Cookie 信息发送给服务端,服务端根据 Cookie 来识别用户的会话信息。Cookie 有如下几个特点:

  • 存储在客户端
  • 可以被客户端修改和删除
  • 数据比较小,例如用户基本信息、购物信息
  • 可以设置过期时间。

Session 是服务端存储会话信息,当客户端请求服务端时,服务端会被每个用户创建一个唯一的会话(Session id)标识,并在服务端设置和存储会话信息,并在后续的请求,可以获取到会话信息,主要有如下特点:

  • 存储在服务端,客户端无法修改和删除
  • 数据比较大,比如用户的信息,登录记录。
  • 通常依赖 Cookie 和客户端进行数据交换。

Cookie 和 Session 的主要区别:

  • 储存位置:Cookie 存储在客户端,Session 存储在服务端上。
  • 数据大小:Cookie 通常比较小,Session 通常存储较大的数据。
  • 安全性:Cookie 可以通过 js 设置和修改,也可能通过抓包工具修改,可以轻易的被修改,Cookie 安全性差,很多浏览器也禁用了 Cookie,Cookie 使用也不多。Session 的设置和修改都在服务端,安全性相对 Cookie 高很多。

在实际的使用场景上,Cookie 和 Session 也会结合使用,服务端使用Session记录用户的会话信息,而将会话信息存储在 Cookie 中,这样可以减少服务端的压力。

标签:session,Java,请求,Session,Cookie,服务端,客户端
From: https://www.cnblogs.com/jeremylai7/p/17476525.html

相关文章

  • java实现一个接口多个实现类,并且依次调用指定方法
    接口packagecn.daenx.yhchatsdk.mytest;publicinterfaceMyInterface{/***返回-1,后面的实现类将不再执行*返回0,后面的实现类继续执行**@return*/IntegerdoSomething();}实现类实现类1packagecn.daenx.yhchatsdk.mytest;......
  • Java网络编程
    Java网络编程什么是网络编程在网络通信协议下,不同计算机上运行的程序,进行的数据传输.常见的软件架构CS:客户端/服务器BS:浏览器/服务器BS架构优缺点CS架构优缺点总结网络编程三要素IP端口号协议总结......
  • 关于进程、线程、协程的概念以及Java中的应用
    进程、线程、协程本文将从“操作系统”、“Java应用”上两个角度来探究这三者的区别。一、进程在我本人的疑惑中,我有以下3个问题。1.1为什么要引入进程?在“多道程序环境下”,允许多个程序并发执行,此时它们将失去封闭性,并具有间断性以及不可再现性的特征,因此需要引入进程的概念......
  • 数据存储的两种方式:cookie和webStorage存储
    一、sessionstorage(会话存储)1、添加数据:SessionStorage.setItem('key','value');该方法接受一个键和值作为参数,会把键值对添加到存储中,如果键名存在,则更新其对应的值。2、获取数据:SessionStorage.getItem('key');该方法接受一个键名作为参数,返回键名对应的值。如果获取不到......
  • nohub命令和java -jar启动Spring Boot
    1.nohub命令启动SpringBoot项目nohupjava-Xms1024m-Xmx2048m-jardemo-0.0.1-SNAPSHOT.jar1>start.out2>&1&2.java-jar启动SpringBoot项目java-Xms800m-Xmx800m-XX:PermSize=256m-XX:MaxPermSize=512m-XX:MaxNewSize=512m-jardemo-0.0.1-SNAPSHOT.jar&g......
  • nohup java -jar 启动java项目
    一、java-jara.jar&直接启动jar文件,在当前会话进程中开启一个子进程来运行程序,这个子进程会随着会话进程的结束而结束。这种情况适合短时间测试用。二、nohupjava-jara.jar&先交代一下名词:hangup(挂断),终端退出时会发送hangup信号来通知其关闭所有子进程。nohup(不挂断......
  • Hbase的JavaAPI和数据存储
    导入Maven依赖<dependencies><dependency><groupId>org.apache.zookeeper</groupId><artifactId>zookeeper</artifactId><version>3.4.6</version></dependency><dependen......
  • java返回树型结构
    //先查询出所有的数据List<table>list=kineticEnergyFileImportService.getguzhang(ELECTRICALTYPE);Set<String>roots=newLinkedHashSet<>();Map<String,Set<String>>map=newHashMap<>();for(tablefaul......
  • java调用第三方接口,请求方式 get,传参方式 param形式非json。
    项目调用第三方接口,调用方式人家做了限制“请求方式get 传参方式param形式传参,非json”。所有有了下面的代码: importcom.alibaba.fastjson.JSONObject;importcom.spcp.platform.common.util.StringUtil;importcom.spcp.qypt.whpt.util.HttpClientUtil;importorg.spring......
  • java8随手记(包含idea连接远程分支出现Nothing to update问题)
    Steam流一、映射1.map()和.flatMap()map将数据放入集合中,返回Steam流中。例如:map集合{1,2,3},返回Steam流[a,b,c,{1,2,3}]flatMap将将集合中的数据,返回Steam流中.例如:flatMap集合{1,2,3},返回Steam流中[a,b,c,1,2,3]注意:add与addAll有同样的效果。   ......