什么是会话固定以及如何在 Node.js 中防止它
什么是会话固定以及如何在 Node.js 中防止它
在深入讨论之前,我们需要了解会话是什么以及会话身份验证如何工作。
什么是会话?
正如我们所知,HTTP 请求是无状态的,这意味着当我们发送登录请求时,并且我们有有效的用户名和密码,没有默认机制可以知道我们是发送下一个请求的同一个人。为了解决这个问题,换句话说,使请求有状态,有一些常用的方法,如Cookie、隐藏表单字段、URL 参数、浏览器存储、JWT 和 Session。在本文中,我们将重点关注Session。
Session是存储在服务器上的数据。每个客户端都会获得一个与服务器上的数据相关的唯一标识符 。客户端必须在每个请求上发送此唯一标识符,以便我们知道谁发送了此请求。该标识符可以在 cookie 或 URL 参数中发送。
下面是使用express-session和express创建session的简单示例:
const app = require('express')();
const session = require('express-session');
app.use(require('cookie-parser')());
app.use(require('body-parser').json());app.use(session({secret: 'secret',cookie: { maxAge: 60000 },name: 'sessionId'
}));app.get('/', (req, res) => {res.send('ping');
});app.listen(3000, () => {console.log('Server is running on port 3000');
});
当第一次发送请求时,express-session中间件会创建一个新的唯一标识符,并将其设置为 cookie 后再将其存储在某处(在本例中为内存,但我们也可以传递自定义存储)。在会话中间件的选项中,我们使用了sessionId存储此唯一标识符的密钥名称。现在,如果我们发送请求,我们会看到如下内容:

浏览器现在设置此 cookie 并自动存储它以供进一步请求。如果我们发送包含有效会话的请求(该会话存在于我们的会话存储中 - 在本例中为内存),在响应中获取标头的标头就不再包含Set-Cookie字段了:

当用户登录时,我们可以将用户信息存储在 cookie 中(序列化),也可以将其存储在数据库中并将数据与sessionId进行绑定. 让我们使用 Map 作为我们的简单数据库:
const db = new Map();
app.get('/me', (req, res) => {const user = db.get(req.sessionID);res.json({ mySessionId: req.sessionID, me: user ? user : 'anonymous' });
});
const users = [{ name: 'leo', age: 19 }, { name: 'joe', age: 20 }];
app.post('/login', (req, res) => {const { name } = req.body;const user = users.find(u => u.name === name);if (user) {db.set(req.sessionID, user);res.send('ok');} else {res.send('try again');}
});
攻击者可以创建有效的会话 ID 吗?
在本例中,我们使用的是express-session。可以看到我们向express-session中间件传递了一个secret值。这个secret用于签署我们的 cookie 的值。它只是意味着我们确信是我们生成了sessionId。
session示例:
sessionId=s%3AL6j4T8hBwMk1ulJqGoisZbAxUOkOuQqP.x5UxPQEtKrj3sWrIy6S01CQRjAtp4biVs4H2zgqmSs
第一部分:s%3A简单来说:s:这是一个前缀,表明我们的 cookie 会话已签名!
第二部分:L6j4T8hBwMk1ulJqGoisZbAxUOkOuQqP这是我们的sessionId,我们在数据库中使用它来关联数据。
第三部分:x5UxPQEtKrj3sWrIy6S01CQRjAtp4biVs4H2zgqmSs这是签字部分。我们使用我们的secret生成了此文本,因此我们可以确定此 cookie 是由我们生成的。
我们可以简单地重新生成这个标志并检查它是否有效:
const crypto = require('crypto');
const secret = 'secret';
const sessionId = 'L6j4T8hBwMk1ulJqGoisZbAxUOkOuQqP';
const hmac = crypto.createHmac('sha256', secret);
hmac.update(sessionId);
const signature = hmac.digest('base64').replace(/\=+$/, '');
console.log(signature); // x5UxPQEtKrj3sWrIy6S01CQRjAtp4biVs4H2zgqmSs
什么是会话固定?
在会话固定攻击中,攻击者劫持有效的用户会话。我们说过,我们对 cookie 进行签名是为了确保没有人可以劫持其他用户的有效会话。但是,如果攻击者拥有自己的有效会话并尝试将其与另一个用户关联怎么办?在这种情况下,他可以代表受害者采取行动。
当我们没有在 Login 之类的操作上生成新的 sessionIds(唯一标识符)时,就会出现问题。
通过会话固定,攻击者可以劫持有效的用户会话,了解此漏洞并防范它绝对重要。
攻击者如何才能做到这一点?
其中一种情况是攻击者可以物理访问计算机。作为攻击者,我们可以选择一台共享计算机,打开某个已经登录过的网页,然后复制session后发送请求。
sessionId在有些网站在请求中作为 URL 参数传递。在这种情况下,如果攻击者使用其 URL 参数提供登录页面的链接,sessionId则有可能被利用。
如何防止会话固定?
登录时生成新会话
主要解决方案非常简单,通过这样做,始终可以确保不会发生此会话覆盖!
让我们改变代码:
app.post('/login', (req, res) => {const { name } = req.body;req.session.regenerate(err => {if (err) {res.send('error');} else {const user = users.find(u => u.name === name);if (user) {db.set(req.sessionID, user);res.send('ok');} else {res.send('try again');}}});
});
我们可以使用regenerate函数,以便每次有人想要登录时分配一个新的会话。无论我们是否传递会话cookie,它都会生成一个新的会话Id并将其发送到客户端中。
仅使用HTTP Only 的 Cookie
当我们使用HTTP Only时,这意味着只有服务器可以通过Set-Cookie标头设置cookie,而客户端(浏览器JavaScript)无法更改它。所以即使我们的应用存在XSS漏洞,攻击者也无法更改sessionId(cookie)。
防范 XSS
会话固定可以与 XSS 攻击结合使用,从而更加有效,因此如果我们担心会话固定,那么认真对待 XSS 攻击确实有意义。
合理的会话过期时间
会话过期时间应该符合我们的应用程序特定要求,如果我们更关心安全性,那么它应该更短,反之亦然。
正确的注销实施
注销时,我们必须正确销毁现有会话及其与任何数据的关联。否则,这些会话可以在注销后使用。(仅从客户端浏览器中删除 cookie 是不够的!)
相关文章:
什么是会话固定以及如何在 Node.js 中防止它
什么是会话固定以及如何在 Node.js 中防止它 在深入讨论之前,我们需要了解会话是什么以及会话身份验证如何工作。 什么是会话? 正如我们所知,HTTP 请求是无状态的,这意味着当我们发送登录请求时,并且我们有有效的用…...
代码随想录算法训练营第五十二天|300. 最长递增子序列、674. 最长连续递增序列、718. 最长重复子数组
第九章 动态规划part13 300. 最长递增子序列 给你一个整数数组 nums ,找到其中最长严格递增子序列的长度。 子序列 是由数组派生而来的序列,删除(或不删除)数组中的元素而不改变其余元素的顺序。例如,[3,6,2,7] 是数…...
使用 Hugging Face Transformer 微调 BERT
微调 BERT有助于将其语言理解能力扩展到更新的文本领域。BERT 的与众不同之处在于它能够掌握句子的上下文关系,理解每个单词相对于其邻居的含义。我们将使用 Hugging Face Transformers 训练 BERT,还将教 BERT 分析 Arxiv 的摘要并将其分类为 11 个类别之一。 为什么微调 BER…...
Vue原型对象
原型对象 prototype 称为:显示的原型属性,用法:函数.prototype,例如:Vue.prototype __proto__称为:隐式的原型属性,用户:实例.proto,例如:vm.proto 不管如何 …...
向量数据库的分类概况
保存和检索矢量数据的五种方法: 像 Pinecone 这样的纯矢量数据库 全文搜索数据库,例如 ElasticSearch 矢量库,如 Faiss、Annoy 和 Hnswlib 支持矢量的NoSQL 数据库,例如 MongoDB、Cosmos DB 和 Cassandra 支持矢量的SQL 数据库&am…...
工业镜头的类别
工业镜头的类别 按照等效焦距分为: 广角镜头 中焦距镜头 长焦距镜头 广角镜头 等效焦距小于标准镜头(等效焦距为50mm)的镜头。特点是最小工作距离短,景深大,视角大。常常表现为桶形畸变。 中焦距镜头 焦距介于广角镜…...
实验11 SQL互联网业务查询-2
这就是SQL题带给我的自信😕 可能发题解到博客上,主要是写完一遍实在不想看第二遍,太长了,优化都不想优化,看着头疼。 技术栈 – WhiteNights Site 一 USE mydata; #请在此处添加实现代码 ########## Begin #######…...
C++知识点梳理:C++ templates
c模板包括:类模板、类(非模板类和模板类)方法模板、函数模板、别名模板、变量模板。 类模板模板参数列表说明: 1)类定义 仅模板参数列表声明,template<>行。 类名后无需参数说明<>。 2…...
uniapp form表单提交事件手动调用
背景: UI把提交的按钮弄成了图片,之前的button不能用了。 <button form-type"submit">搜索</button> 实现: html: 通过 this.$refs.fd 获取到form的vue对象。手动调用里面的_onSubmit()方法。 methods:…...
Accelerate 0.24.0文档 三:超大模型推理(内存估算、Sharded checkpoints、bitsandbytes量化、分布式推理)
文章目录 一、内存估算1.1 Gradio Demos1.2 The Command 二、使用Accelerate加载超大模型2.1 模型加载的常规流程2.2 加载空模型2.3 分片检查点(Sharded checkpoints)2.4 示例:使用Accelerate推理GPT2-1.5B2.5 device_map 三、bitsandbytes量…...
HackTheBox-Starting Point--Tier 2---Markup
文章目录 一 Markup测试过程1.1 打点1.2 权限获取1.3 权限升级 二 题目 一 Markup测试过程 1.1 打点 1.端口扫描 nmap -A -Pn -sC 10.129.95.1922.访问web网站,登录口爆破发现存在弱口令admin:password 3.抓包,发现请求体是XML格式 4.尝试使…...
android studio导入eclipse项目
网上下载一个老工程,.project文件里有eclipse。 android studio导入eclipse项目 eclipse项目结构 Android studio文件结构 下面是导入步骤: 第一步,打开一个项目。 选择File->New->Import Project 第二步,选择Eclipse项目根…...
如何利用AI实现银行存量客户的营销?
近年来,大数据、人工智能等热门关键字多次被写入中央文件与国务院政府工作报告,目前已上升为国家战略,并将深刻地改变现有行业的游戏规则。 金融行业是当今大数据、人工智能应用最广、最深的领域之一。随着数据仓库和数据科学的发展ÿ…...
springboot327基于Java的医院急诊系统
交流学习: 更多项目: 全网最全的Java成品项目列表 https://docs.qq.com/doc/DUXdsVlhIdVlsemdX 演示 项目功能演示: ————————————————...
Unity3d 导入中文字体转TMPtext asset
外部字体放入unity仓库以后呢,需要把这个字体转成用立体的字体文件才可以被使用! 要想转换的话呢先放入仓库对字体点右键上面有一个Create创建里面有一个TEXT Asset,创建好就可以使用了...
云积万相,焕发电商店铺新活力
数字化时代,电商店铺的运营和营销策略越来越受到重视。如何让店铺在众多的竞争中脱颖而出,吸引更多的顾客,提高销售额,是每个电商品牌都需要思考的问题。云积天赫最近推出的云积万相为电商店铺带来全新的活力和更多的可能性。 …...
字典管理怎么使用,vue3项目使用若依的的字典管理模块
若依框架数据字典的使用_若依数据字典_哈哈水水水水的博客-CSDN博客 【精选】关于数据字典的理解与设计_数据字典怎么设计-CSDN博客 若依的字典值如何使用(超详细图文教程)_若依字典管理_丿BAIKAL巛的博客-CSDN博客 Vue3组合式API:getCurr…...
【汇编】内存中字的存储、用DS和[address]实现字的传送、DS与数据段
文章目录 前言一、内存中字的存储1.1 8086cpu字的概念1.2 16位的字存储在一个16位的寄存器中,如何存储?1.3 字单元 二、用DS和[address]实现字的传送2.1 字的传送是什么意思?2.2 要求原理解决方案:DS和[address]配合8086传送16字节…...
数据分析 - 分散性与变异的量度
全距 - 极差 处理变异性 方差度量 数值与均值的距离,也就是数据的差异性 标准差描述:典型值 和 均值的距离的方法,数据与均值的分散情况...
Neo4j数据库介绍及简单使用
图数据库介绍 图数据库是一种专门设计用于存储和管理图形数据的数据库类型。在图数据库中,数据以图的形式表示,其中节点表示实体,边表示实体之间的关系。这种表示方式非常适合处理具有复杂关系的数据,如社交网络、推荐系统、网络…...
css实现圆环展示百分比,根据值动态展示所占比例
代码如下 <view class""><view class"circle-chart"><view v-if"!!num" class"pie-item" :style"{background: conic-gradient(var(--one-color) 0%,#E9E6F1 ${num}%),}"></view><view v-else …...
【Oracle APEX开发小技巧12】
有如下需求: 有一个问题反馈页面,要实现在apex页面展示能直观看到反馈时间超过7天未处理的数据,方便管理员及时处理反馈。 我的方法:直接将逻辑写在SQL中,这样可以直接在页面展示 完整代码: SELECTSF.FE…...
8k长序列建模,蛋白质语言模型Prot42仅利用目标蛋白序列即可生成高亲和力结合剂
蛋白质结合剂(如抗体、抑制肽)在疾病诊断、成像分析及靶向药物递送等关键场景中发挥着不可替代的作用。传统上,高特异性蛋白质结合剂的开发高度依赖噬菌体展示、定向进化等实验技术,但这类方法普遍面临资源消耗巨大、研发周期冗长…...
Python实现prophet 理论及参数优化
文章目录 Prophet理论及模型参数介绍Python代码完整实现prophet 添加外部数据进行模型优化 之前初步学习prophet的时候,写过一篇简单实现,后期随着对该模型的深入研究,本次记录涉及到prophet 的公式以及参数调优,从公式可以更直观…...
06 Deep learning神经网络编程基础 激活函数 --吴恩达
深度学习激活函数详解 一、核心作用 引入非线性:使神经网络可学习复杂模式控制输出范围:如Sigmoid将输出限制在(0,1)梯度传递:影响反向传播的稳定性二、常见类型及数学表达 Sigmoid σ ( x ) = 1 1 +...
实现弹窗随键盘上移居中
实现弹窗随键盘上移的核心思路 在Android中,可以通过监听键盘的显示和隐藏事件,动态调整弹窗的位置。关键点在于获取键盘高度,并计算剩余屏幕空间以重新定位弹窗。 // 在Activity或Fragment中设置键盘监听 val rootView findViewById<V…...
Java毕业设计:WML信息查询与后端信息发布系统开发
JAVAWML信息查询与后端信息发布系统实现 一、系统概述 本系统基于Java和WML(无线标记语言)技术开发,实现了移动设备上的信息查询与后端信息发布功能。系统采用B/S架构,服务器端使用Java Servlet处理请求,数据库采用MySQL存储信息࿰…...
【MATLAB代码】基于最大相关熵准则(MCC)的三维鲁棒卡尔曼滤波算法(MCC-KF),附源代码|订阅专栏后可直接查看
文章所述的代码实现了基于最大相关熵准则(MCC)的三维鲁棒卡尔曼滤波算法(MCC-KF),针对传感器观测数据中存在的脉冲型异常噪声问题,通过非线性加权机制提升滤波器的抗干扰能力。代码通过对比传统KF与MCC-KF在含异常值场景下的表现,验证了后者在状态估计鲁棒性方面的显著优…...
Unity UGUI Button事件流程
场景结构 测试代码 public class TestBtn : MonoBehaviour {void Start(){var btn GetComponent<Button>();btn.onClick.AddListener(OnClick);}private void OnClick(){Debug.Log("666");}}当添加事件时 // 实例化一个ButtonClickedEvent的事件 [Formerl…...
Java求职者面试指南:Spring、Spring Boot、Spring MVC与MyBatis技术解析
Java求职者面试指南:Spring、Spring Boot、Spring MVC与MyBatis技术解析 一、第一轮基础概念问题 1. Spring框架的核心容器是什么?它的作用是什么? Spring框架的核心容器是IoC(控制反转)容器。它的主要作用是管理对…...
