Cookie 和 Session概念及相关API

目录

1.Cookie概念

2.理解会话机制 (Session)

3.相关API 

3.1HttpServletRequest

3.2HttpServletResponse

3.3HttpSession

3.4Cookie

4.代码示例: 实现用户登陆


1.Cookie概念

Cookie 是存储在用户本地终端(如计算机、手机等)上的数据片段。

它主要有以下一些特点和作用:

特点:

小型数据存储:通常用于存储少量的信息。

与特定网站关联:由访问的网站创建和管理。

作用:

用户识别:帮助网站识别用户身份,实现登录状态保持等功能。

个性化设置保存:比如记住用户的偏好设置。

跟踪用户行为:用于分析和优化网站体验。

然而,Cookie 也存在一些隐私方面的问题,可能会被用于跟踪用户的浏览行为等。用户可以在浏览器中对 Cookie 的使用进行一定程度的管理和控制。

在实际开发中,我们很多时候是需要知道请求之间的关联关系的

例如登陆网站成功后, 第二次访问的时候服务器就能知道该请求是否是已经登陆过了.

图中的 "令牌" 通常就存储在 Cookie 字段中

1. 例如到了医院先挂号. 挂号时候需要提供身份证, 同时得到了一张 "就诊卡", 这个就诊卡就相当于患者的 "令牌".

2. 后续去各个科室进行检查, 诊断, 开药等操作, 都不必再出示身份证了, 只要凭就诊卡即可识别出当前患者的身份.

3. 看完病了之后, 不想要就诊卡了, 就可以注销这个卡. 此时患者的身份和就诊卡的关联就销毁. (类似于网站的注销操作)

4. 又来看病, 可以办一张新的就诊卡, 此时就得到了一个新的 "牌"

此时在服务器这边需要记录令牌信息, 以及令牌对应的用户信息, 这就是 Session 机制所做的工作

2.理解会话机制 (Session)

服务器同一时刻收到的请求是很多的. 服务器需要清除的区分清楚每个请求是从属于哪个用户, 就需要在服务器这边记录每个用户令牌以及用户的信息的对应关系.

在上面的例子中, 就诊卡就是一张 "令牌". 要想让这个令牌能够生效, 就需要医院这边通过系统记录 每个就诊卡和患者信息之间的关联关系.

会话的本质就是一个 "哈希表", 存储了一些键值对结构. key 就是令牌的 ID(token/sessionId), value 就是 用户信息(用户信息可以根据需求灵活设计).

sessionId 是由服务器生成的一个 "唯一性字符串", session 机制的角度来看, 这个唯一性字符串称为 "sessionId"..在整个登录流程中看待, 也可以把这个唯一性字符串称为 "token".

当用户登陆的时候, 服务器在 Session 中新增一个新记录, 并把 sessionId / token 返回给客户端. (如通过 HTTP 响应中的 Set-Cookie 字段返回).

客户端后续再给服务器发送请求的时候, 需要在请求中带上 sessionId/ token. (例如通过 HTTP 请求中的 Cookie 字段带上).

服务器收到请求之后, 根据请求中的 sessionId / token Session 信息中获取到对应的用户信息,再进行后续操作.

Servlet Session 默认是保存在内存中. 如果重启服务器则 Session 数据就会丢失.

3.相关API 

3.1HttpServletRequest

方法

描述

HttpSession  getSession()

在服务器中获取会话. 参数如果为 true, 则当不存在会话时新建会话; 参数如果false, 则当不存在会话时返回 null

Cookie[]  getCookies()

返回一个数组, 包含客户端发送该请求的所有的 Cookie 对象. 会自动把 Cookie 中的格式解析成键值对.

3.2HttpServletResponse

方法

描述

void addCookie(Cookie cookie)

把指定的 cookie 添加到响应中.

3.3HttpSession

一个 HttpSession 对象里面包含多个键值对. 我们可以往 HttpSession 中存任何我们需要的信息

方法

描述

Object getAttribute(String name)

该方法返回在该 session 会话中具有指定名称的对象,如果没有指定名称的对象,则返回 null.

void setAttribute(String name, Object value)

该方法使用指定的名称绑定一个对象到该 session 会话

boolean isNew()

判定当前是否是新创建出的会话

3.4Cookie

每个 Cookie 对象就是一个键值对.

方法

描述

String getName()

该方法返回 cookie 的名称。名称在创建后不能改变。(这个值是 Set- Cooke 字段设置给浏览器的)

String getValue()

该方法获取cookie 关联的值

void setValue(String newValue)

该方法设置cookie 关联的值。

HTTPCooke 字段中存储的是多组键值对. 每个键值对在 Servlet 中都对应了一个 Cookie 对象

通过 HttpServletRequest.getCookies()  获取到请求中的一系列 Cookie 键值对.  

通过 HttpServletResponse.addCookie()  可以向响应中添加新的 Cookie 键值对.

4.代码示例: 实现用户登陆

实现简单的用户登陆逻辑,代码主要是通过HttpSession完成. 不需要我们手动操作 Cookie对象.

1. 创建 IndexServlet 

@WebServlet("/index")
public class IndexServlet extends HelloServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        resp.setContentType("text/html; charset=utf-8");
        // 1. 判定当前用户是否已经登陆
        HttpSession session = req.getSession(false);
        if (session == null) {
            // 用户没有登陆 , 重定向到 login.html
            resp.sendRedirect("login.html");
            return;
        }
            // 2. 如果已经登陆 , 则从 Session 中取出访问次数数据
            String userName = (String) session.getAttribute("username");
            String countString = (String) session.getAttribute("loginCount");
            int loginCount = Integer.parseInt(countString);
            loginCount += 1;
            session.setAttribute("loginCount", loginCount + "");
            // 3. 展示到页面上 .
            StringBuilder html = new StringBuilder();
            html.append(String.format("<div>用户名: %s</div>", userName));
            html.append(String.format("<div>loginCount: %d</div>", loginCount));
            resp.getWriter().write(html.toString());

    }
}

2. 创建 login.html, 放到 webapp 目录中

<form action="login" method="POST">
    <input type="text" name="username">
    <input type="password" name="password">
    <input type="submit" value="提交">
</form>

3. 创建 LoginServlet 

@WebServlet("/login")
public class LoginServlet extends HttpServlet {
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        resp.setContentType("text/html; charset=utf-8");
        // 1. 获取到用户提交的用户名和密码
        String username = req.getParameter("username");
        String password = req.getParameter("password");
        // 2. 判定用户名密码是否正确
        if (!username.equals("admin") || !password.equals("123")) {
        // 登陆失败
            resp.getWriter().write("登陆失败");
            return;
        }
        // 登陆成功
        System.out.println("登陆成功");
        // 设置 Session
        HttpSession session = req.getSession(true);
        session.setAttribute("username", "admin");
        session.setAttribute("loginCount", "0");
        resp.sendRedirect("index");
    }
}

此处的 getSession 参数为 true, 表示查找不到 HttpSession 时会创建新的 HttpSession 对象, 生成一个 sessionId, 插入到哈希表中, 并且把 sessionId 通过 Set-Cookie 返回给浏览器.

 4. 部署程序 

通过 http://127.0.0.1:8080/ServletHelloWorld/index 访问.

首次访问的时候可以看到, 当前用户尚未登陆, 此时页面自动重定向到 login.html

抓包结果显示:

login.html 中输入用户名密码之后, 会跳转到  /login . 此时服务器返回了一个 token, 并在 Session 中记录用户信息, 然后重定向到 /index

抓包结果:

注意: 响应中的 302表示重定向,其中JSESSIONIDServlet 自动生成的 token

  /index, 通过 Session 拿到了用户信息, 进一步获取到用户的访问次数. 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/635769.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

5款AI工具,PS插件的智能升级

在Photoshop插件的世界里&#xff0c;创新和效率是永远的主题。随着AI技术的融入&#xff0c;传统的PS插件正在经历一场革命。本文将介绍五款结合了人工智能技术的PS插件&#xff0c;它们不仅提升了设计工作的效率&#xff0c;还拓展了创意的边界。 StartAI —— 智能设计的未来…

【包公断案】http请求神秘失踪案

案件名称&#xff1a;http请求离奇失踪案 案发地点&#xff1a;公司内部机器 案发时间&#xff1a;早上9点到9点30分 案发背景&#xff1a;两地三中心&#xff0c;双机房只单边出现该问题 案发事件&#xff1a;服务A的某些api请求离奇失踪&#xff0c;超时无响应&#xff0c;微…

【Qt】如何优雅的进行界面布局

文章目录 1 :peach:写在前面:peach:2 :peach:垂直布局:peach:3 :peach:水平布局:peach:4 :peach:网格布局:peach:5 :peach:表单布局:peach: 1 &#x1f351;写在前面&#x1f351; 之前使⽤ Qt 在界⾯上创建的控件, 都是通过 “绝对定位” 的⽅式来设定的。也就是每个控件所在…

数字信号处理:matlab解差分方程

1. 验证全响应 %验证全响应零状态响应零输入响应 %y(n)4y(n-1)x(n),其中x(n)δ(n),y(-1)2.clc;%清屏 clear all;%清除所有变量的值 b[1]; a[1,-4]; ys[2]; xs[0];%没有初始值&#xff0c;就是0 xn[1, zeros(1,4)];%输入序列&#xff0c;假设长度是5&#xff0c;则输出长度也是…

WDW-100G 高温拉力试验机 技术方案书

一、整机外观图&#xff1a; 二、项目简介&#xff1a; 微机控制高温拉力试验机是电子技术与机械传动相结合的新型材料试验机&#xff0c;它具有宽广准确的加载速度和测力范围&#xff0c;对载荷、变形、位移的测量和控制有较高的精度和灵敏度&#xff0c;还可以进行等速加载、…

sharded jedis pipelined 执行后 数据并未存入redis

前言 因为历史原因&#xff0c;在某个同步菜单操作的方法中先清除缓存&#xff0c;然后在初始化缓存。本来很正常的逻辑&#xff0c;但是这个清除是db查询获取所有的菜单 然后循环一条条删除 然后在db查询有效的菜单操作 在循环一条条插进去 经统计这个菜单操作大概有个7千个 …

【区块链】fisco网络运维之添加节点黑名单

基于已完成的区块链系统与管理平台搭建工作&#xff0c;开展区块链节点的黑名单工作&#xff0c;具体操作如下 以node3为例子 1查看node0节点的连接状态日志&#xff08;现有4个节点连接&#xff09; 注意&#xff1a;如果查询不到连接状态&#xff0c;修改node0的配置文件中…

QT5.15.2及以上版本安装

更新时间&#xff1a;2024-05-20 安装qt5.15以上版本 系统&#xff1a;ubuntu20.04.06 本文安装&#xff1a;linux-5.15.2 下载安装 # 安装编译套件g sudo apt-get install build-essential #安装OpenGL sudo apt-get install libgl1-mesa-dev# 下载qt安装器 https://downl…

每天五分钟深度学习框架PyTorch:创建具有特殊值的tensor张量

本文重点 tensor张量是一个多维数组,本节课程我们将学习一些pytorch中已经封装好的方法,使用这些方法我们可以快速创建出具有特殊意义的tensor张量。 创建一个值为空的张量 import torch import numpy as np a=torch.empty(1) print(a) print(a.dim()) print(s.shape) 如图…

supOS NEO科技普惠!永久免费!亿元补贴

数字化转型正在全球蓬勃发展&#xff0c;工业操作系统进入大规模推广期&#xff01; 如果您正在被预算不足、技术团队不强、数字化投入产出比等问题困扰&#xff0c;supOS NEO是您最好的选择。 “让supOS走进万千工厂、千行百业&#xff01;让全世界每个工厂都能用得上supOS&am…

.net core web项目部署IIS报错:HTTP 错误 413.1 - Request Entity Too Large

HTTP 错误 413.1 - Request Entity Too Large 解决办法 这个报错的原因是因为IIS配置问题&#xff0c;IIS最大默认配置只有30M&#xff0c;超过30M就会报错 解决办法 在程序中配置能接收最大字节大小 //配置请求头中能最大接收多少数据 //builder.WebHost.UseKestrel(option…

VS2022通过C++网络库Boost.asio搭建一个简单TCP异步服务器和客户端

基本介绍 上一篇博客我们介绍了通过Boost.asio搭建一个TCP同步服务器和客户端&#xff0c;这次我们再通过asio搭建一个异步通信的服务器和客户端系统&#xff0c;由于这是一个简单异步服务器&#xff0c;所以我们的异步特指异步服务器而不是异步客户端&#xff0c;同步服务器在…

c语言:利用随机函数产生20个[120, 834] 之间互不相等的随机数, 并利用选择排序法将其从小到大排序后输出(每行输出5个)

利用随机函数产生20个[120, 834] 之间互不相等的随机数&#xff0c; 并利用选择排序法将其从小到大排序后输出&#xff08;每行输出5个&#xff09; 代码如下&#xff1a; #include <stdio.h> #include <time.h> #include <stdlib.h> int shenchen(int a[…

全栈实现发送验证码注册账号 全栈开发之路——全栈篇(3)

全栈开发一条龙——前端篇 第一篇&#xff1a;框架确定、ide设置与项目创建 第二篇&#xff1a;介绍项目文件意义、组件结构与导入以及setup的引入。 第三篇&#xff1a;setup语法&#xff0c;设置响应式数据。 第四篇&#xff1a;数据绑定、计算属性和watch监视 第五篇 : 组件…

分布式音乐播放器适配了Stage模型

OpenAtom OpenHarmony&#xff08;以下简称“OpenHarmony”&#xff09;应用开发自API 8及其更早版本一直使用的是FA模型进行开发。FA模型是Feature Ability的缩写&#xff0c;它和PA&#xff08;Particle Ability&#xff09;两种类型是过往长期推广的术语&#xff0c;深入人心…

6.2 else if语句

本节必须掌握的知识点&#xff1a; 示例代码二十 代码分析 汇编解析 ■if语句表达形式3 if(表达式1) statement1 else if(表达式2) statement2 else if(表达式3) statement3 …… else statementN 解析&#xff1a; 如果表达式1非0&#xff0c;则执行statement1&#…

Java基础22(JSON解析 注解)

目录 一、JSON解析 1. JSON语法 2. JSON的用途 3. Java解析JSON 4. 使用Fastjson 4.1 Fastjson 的优点 4.2 Fastjson 导包 4.3 Fastjson的主要对象 4.4 常用方法 将Java对象 "序列化"&#xff08;转换&#xff09; 为JSON字符串&#xff1a; 将JSON字符串…

go语言中的一个特别的语法 //go:embed 可将将静态文件内容读取到string, []byte和 embed.FS 变量并直接打包到exe包中

go语言中的一个特别的语法 //go:embed 看上去像是注释&#xff0c;实则是golang中的一个内置的语法&#xff0c;而且是仅在你的go代码编译时生效的语法&#xff0c; 借助他我们可以将我们的静态资源文件读取到FS直接打包到我们的exe执行文件中。 同时他还支持文件的模式匹配…

C#中BufferedStream类详解与示例

文章目录 1. BufferedStream的基本介绍2. 创建BufferedStream对象从现有Stream创建指定缓冲区大小 3. 使用BufferedStream读取数据写入数据 4. BufferedStream的注意事项5. 示例代码 在C#中&#xff0c;BufferedStream是一个非常有用的流类&#xff0c;它提供了缓冲功能&#x…

出谈论点云文件pcd加载01

刚写完基于potree开发地图水印效果的时候&#xff0c;在网上分享实例&#xff0c;刚发出去&#xff0c;竟然被人喷了&#xff0c;这么简单的实例&#xff0c;竟然好意思发群里&#xff0c;哎… 好无奈&#xff01; 不过我还是坚持我的想法&#xff0c;大家看到文章后&#xff0…