JS本地存储与会话存储操作详解
时间:2025-08-13 12:36:29 347浏览 收藏
今日不肯埋头,明日何以抬头!每日一句努力自己的话哈哈~哈喽,今天我将给大家带来一篇《JS如何操作本地存储和会话存储》,主要内容是讲解等等,感兴趣的朋友可以收藏或者有更好的建议在评论提出,我都会认真看的!大家一起进步,一起学习!
答案是:选择浏览器存储技术需根据数据的生命周期、大小、安全性及用途来决定。localStorage适用于长期存储非敏感用户偏好数据,因其持久化且容量较大(5-10MB),但需注意其同步操作可能阻塞主线程且不适用于敏感信息;sessionStorage适合临时会话数据,页面关闭后自动清除,使用方式与localStorage相同;Cookies虽容量小(约4KB)且每次请求自动携带,但可通过设置HttpOnly、Secure和SameSite属性增强安全性,常用于存储需随请求发送的认证token或会话ID;对于大量结构化数据或复杂查询需求,应选用IndexedDB,其为异步的客户端NoSQL数据库,支持事务与索引,适合离线应用和PWA;若需缓存静态资源以实现离线访问和加速加载,则应使用Cache API配合Service Worker;Web SQL已废弃,不应再使用。最佳实践包括:绝不存储敏感信息于localStorage或sessionStorage中,始终对非字符串数据进行JSON序列化,合理设置Cookie安全属性,做好存储异常的错误处理,并在数据不再需要时及时清理。综上,应根据具体场景选择最合适的技术,没有通用的“银弹”方案,最终目标是保障性能、安全与用户体验的平衡。
JavaScript操作浏览器存储,主要是通过Web Storage API(localStorage
和sessionStorage
)以及更早的Cookies来实现的。简单来说,它们就是让你的网页应用能把一些数据直接塞到用户浏览器里,无论是为了记住用户偏好,还是临时缓存点什么,这套机制都挺管用。它让前端应用不再是无状态的,能更好地和用户交互,提升体验。
解决方案
前端在浏览器里存储数据,最常用的就是Web Storage(localStorage
和sessionStorage
)和Cookies。它们各有各的脾气和适用场景,用好了能让用户体验好很多,用不好嘛,可能就会遇到些头疼的问题。
1. localStorage
:本地存储,持久化
localStorage
就像是浏览器里一个永不打烊的小仓库,你把数据存进去,除非用户手动清除浏览器缓存,或者你的代码明确地把它删掉,否则数据会一直都在。即使关闭浏览器,下次再打开同一个网站,数据也还在那儿。它非常适合存储那些需要长期保留的用户设置、主题偏好、或者一些不敏感的缓存数据。
操作方法:
// 存数据:键值对形式,值必须是字符串 localStorage.setItem('userName', '张三'); localStorage.setItem('userTheme', 'dark'); // 如果要存对象或数组,记得先用JSON.stringify()转成字符串 const userSettings = { theme: 'light', notifications: true }; localStorage.setItem('settings', JSON.stringify(userSettings)); // 取数据:根据键名获取值 let name = localStorage.getItem('userName'); // '张三' let theme = localStorage.getItem('userTheme'); // 'dark' // 取出对象或数组时,要用JSON.parse()解析回来 const settings = JSON.parse(localStorage.getItem('settings')); console.log(settings.theme); // 'light' // 删数据:根据键名删除特定项 localStorage.removeItem('userName'); // 清空所有数据(慎用!会清掉当前域名下所有localStorage数据) // localStorage.clear(); // 获取存储项的数量 let count = localStorage.length;
2. sessionStorage
:会话存储,临时性
sessionStorage
则更像是一个临时的工作台。数据只在当前浏览器会话(也就是当前标签页或窗口)有效。一旦用户关闭了当前标签页或浏览器窗口,里头的数据就会被清空。它很适合存储那些只在本次访问中需要的数据,比如用户在购物流程中的临时数据、表单填写到一半的草稿、或者单次会话的认证信息。
操作方法:
sessionStorage
的操作方法和localStorage
几乎一模一样,只是存储的生命周期不同。
// 存数据 sessionStorage.setItem('tempOrderId', 'ORD2023001'); sessionStorage.setItem('formDraft', JSON.stringify({ step: 2, data: { name: '李四' } })); // 取数据 let orderId = sessionStorage.getItem('tempOrderId'); // 'ORD2023001' let draft = JSON.parse(sessionStorage.getItem('formDraft')); console.log(draft.data.name); // '李四' // 删数据 sessionStorage.removeItem('tempOrderId'); // 清空所有数据 // sessionStorage.clear();
3. Cookies:小甜饼,历史悠久但局限多
Cookies是浏览器存储的“老前辈”了,它们在HTTP协议诞生之初就有了。相比Web Storage,Cookies的容量非常小(通常只有几KB),而且每次HTTP请求都会自动携带上相关的Cookie,这意味着它会增加网络请求的开销。但它也有Web Storage不具备的特性:可以设置过期时间,可以设置路径和域名限制,而且最重要的是,可以设置HttpOnly
,让JavaScript无法直接访问,这在存储一些敏感信息(比如认证令牌)时,能有效防止XSS攻击。
操作方法:
JavaScript操作document.cookie
是一个字符串,你需要手动解析和拼接。这确实有点麻烦,所以通常大家会用库或者自己封装函数来处理。
// 设置一个Cookie,有效期一天 // document.cookie = "key=value; expires=Thu, 18 Dec 2024 12:00:00 UTC; path=/"; // 也可以这样设置过期时间,更动态 const now = new Date(); now.setTime(now.getTime() + (24 * 60 * 60 * 1000)); // 24小时后过期 document.cookie = `userId=user123; expires=${now.toUTCString()}; path=/`; // 设置一个会话Cookie(不设置expires,浏览器关闭即失效) document.cookie = "sessionId=abc; path=/"; // 获取所有Cookie(返回一个字符串,包含所有键值对,用分号和空格隔开) console.log(document.cookie); // "userId=user123; sessionId=abc" // 删除Cookie:通过设置过期时间为过去来删除 document.cookie = "userId=; expires=Thu, 01 Jan 1970 00:00:00 UTC; path=/;"; // 复杂的Cookie操作通常需要解析 function getCookie(name) { const nameEQ = name + "="; const ca = document.cookie.split(';'); for(let i=0; i < ca.length; i++) { let c = ca[i]; while (c.charAt(0)==' ') c = c.substring(1,c.length); if (c.indexOf(nameEQ) == 0) return c.substring(nameEQ.length,c.length); } return null; } console.log(getCookie('userId')); // 'user123'
浏览器存储的几种方式,我该如何选择?
这确实是前端开发者经常纠结的问题。在我看来,选择哪种存储方式,主要看你数据的“寿命”、大小、以及安全性要求。没有银弹,只有最适合的。
1. 数据寿命:
- 长期持久化? 比如用户的语言偏好、主题模式、记住登录状态(但不是直接存密码,而是token),那毫无疑问,
localStorage
是首选。它数据量大,且除非用户手动清理,否则永不失效。 - 单次会话有效? 比如用户在填写一个多步骤表单,或者一个临时的购物清单,关闭页面就不需要了,
sessionStorage
就非常合适。它用完即走,不留痕迹,也避免了数据残留的麻烦。 - 需要服务器交互? 如果有些数据(比如认证token、会话ID)需要在每次请求时自动发送给服务器,并且可能需要设置特定的域名、路径或
HttpOnly
属性来增强安全性,那Cookies
是你的不二选择。当然,它的容量小,不适合存大量数据。
2. 数据大小:
localStorage
和sessionStorage
通常有5MB到10MB的容量限制(不同浏览器可能略有差异),这对于存储大部分前端所需的数据来说,已经绰绰有余了。Cookies
的容量就可怜得多了,通常只有4KB左右。所以,千万别指望用它来存图片或者长篇文章。
3. 安全性与访问权限:
- 前端可读写?
localStorage
和sessionStorage
是完全暴露给JavaScript的,这意味着如果你的网站存在XSS漏洞,攻击者可以轻易地通过JS脚本获取到这些存储的数据。所以,绝对不要在localStorage
或sessionStorage
里存储敏感信息,比如用户的密码、未经加密的API密钥等。 - 后端可读写,前端受限?
Cookies
在这方面有独特优势。通过设置HttpOnly
属性,可以禁止JavaScript直接访问Cookie,大大降低了XSS攻击的风险。因此,像认证token这类敏感但又需要随请求发送给服务器的数据,通常会选择HttpOnly
的Cookies
。当然,如果只是HttpOnly
,仍需警惕CSRF攻击,通常还需要配合SameSite
属性来加强防护。
总结一下,我的个人建议是:
- 长期不敏感的用户偏好:
localStorage
。 - 临时性、会话级数据:
sessionStorage
。 - 需要随请求发送给服务器的认证信息或会话ID:
Cookies
(并尽可能设置HttpOnly
和Secure
、SameSite
)。 - 大量结构化数据,需要更复杂的查询或离线能力:考虑
IndexedDB
(后面会提到)。
使用浏览器存储时,有哪些常见的陷阱和最佳实践?
虽然浏览器存储用起来很方便,但如果掉以轻心,也容易踩坑。作为过来人,我总结了一些常见的“坑”和一些我认为挺实用的最佳实践。
常见的“坑”:
- 安全漏洞: 这可能是最大的坑。我见过不少项目,为了方便,直接把用户的敏感信息(比如未加密的个人数据,甚至API密钥)扔到
localStorage
里。一旦网站出现XSS漏洞,这些数据就完全暴露了。记住,localStorage
和sessionStorage
是前端完全可读写的,它们不适合存放任何敏感、私密的数据。 - 容量限制: 虽然5-10MB听起来不少,但如果你不加节制地往里塞数据,或者存储了大量冗余信息,很快就会达到上限。当存储操作超出配额时,会抛出
QuotaExceededError
,如果没做错误处理,你的应用可能就直接崩溃了。 - 只存字符串:
localStorage
和sessionStorage
只能存储字符串。如果你直接setItem('myObject', {a:1})
,取出来会是"[object Object]"
,这显然不是你想要的。必须手动进行JSON.stringify()
和JSON.parse()
。这虽然不是什么大问题,但新手很容易忘记。 - 同步操作的性能问题:
localStorage
和sessionStorage
的操作是同步的。这意味着当你进行大量的读写操作时,可能会阻塞主线程,导致页面卡顿。对于小量数据问题不大,但如果数据量非常大,就需要警惕了。 - 跨域问题:
localStorage
和sessionStorage
是同源策略的,也就是说,a.com
存的数据,b.com
是无法访问的。这既是安全保障,也意味着如果你想在不同子域名之间共享数据,Web Storage就无能为力了(除非是顶级域名相同,且路径设置得当的Cookies)。
最佳实践:
- 永不存储敏感数据: 划重点!密码、未加密的身份信息、信用卡号等,永远不要直接存放在前端的浏览器存储中。对于认证token,如果必须前端存储,优先考虑
HttpOnly
的Cookies
。 - 数据序列化与反序列化: 凡是存储非字符串类型的数据(对象、数组、布尔值、数字),务必使用
JSON.stringify()
将其转换为字符串存储,并在读取时使用JSON.parse()
解析回来。 - 错误处理: 尤其是在
localStorage
中,由于可能达到容量上限,或者用户设置了隐私模式导致无法写入,应该用try...catch
包裹存储操作。try { localStorage.setItem('testKey', 'testValue'); } catch (e) { if (e.name === 'QuotaExceededError') { console.error('超出存储空间限制!请清理不必要的数据或通知用户。'); } else { console.error('存储操作失败:', e); } }
- 及时清理不再需要的数据: 当用户退出登录,或者某些临时数据已经处理完毕时,及时调用
removeItem()
或clear()
来清理数据。这不仅能节省空间,也能避免数据泄露或混淆。 - 为Cookie设置合理的属性: 如果使用Cookie,务必设置
HttpOnly
(防止XSS)、Secure
(只在HTTPS下发送)、SameSite
(防止CSRF,推荐Lax
或Strict
)以及合适的expires
(过期时间)和path
(路径)属性。这些通常由后端来设置,但作为前端,了解它们的工作原理也很重要。 - 考虑替代方案: 如果你需要存储大量结构化数据,或者需要复杂的查询功能,那么
IndexedDB
会是更好的选择,因为它是一个功能更强大的客户端数据库。对于离线缓存静态资源,Service Worker
的Cache API
则更专业。
除了localStorage和sessionStorage,还有哪些浏览器存储技术?它们有什么用?
除了我们常说的localStorage
、sessionStorage
和Cookies
,浏览器其实还有一些更强大、更专业的存储技术。它们各自有独特的应用场景,尤其是在构建复杂应用或者离线应用时,显得尤为重要。
1. IndexedDB:客户端的NoSQL数据库
如果说localStorage
是浏览器里的一个键值对小抽屉,那IndexedDB
就是一套完整的、强大的客户端NoSQL数据库系统。它能够存储大量的结构化数据(通常可达几十MB甚至更多,具体取决于浏览器和用户设备),并且支持事务、索引、游标等数据库特性。最重要的是,IndexedDB
的操作是异步的,不会阻塞主线程,这对于处理大数据量时的性能至关重要。
它有什么用?
- 离线应用(PWA): 存储大量应用数据,使得应用在没有网络连接时也能正常工作。比如一个离线笔记应用、一个数据分析工具的本地缓存。
- 大型数据缓存: 缓存服务器返回的大量数据,减少网络请求,提升应用响应速度。
- 复杂数据结构存储: 如果你的数据不是简单的键值对,而是需要复杂的查询、过滤、排序,或者需要存储嵌套的对象、数组,
IndexedDB
会比localStorage
方便得多。 - 用户生成内容: 比如一个图片编辑器,用户在本地操作时,可以把中间步骤或者最终结果暂存到
IndexedDB
。
当然,IndexedDB
的API相对复杂,通常会借助一些库(如Dexie.js
、localForage
)来简化操作。
2. Cache API (Service Workers):专为网络请求缓存而生
Cache API
是与Service Worker
紧密配合的一种存储机制。它的主要职责是缓存网络请求的响应,包括HTML文件、CSS样式表、JavaScript脚本、图片、字体等静态资源,甚至API请求的JSON数据。它的设计初衷就是为了让Web应用能够更快地加载,并在离线状态下提供内容。
它有什么用?
- 构建Progressive Web Apps (PWAs): 实现“离线优先”的策略,即使没有网络,用户也能访问到部分或全部应用内容。
- 提升加载速度: 缓存静态资源,第二次访问时直接从缓存读取,大大减少了网络延迟。
- 优化用户体验: 即使网络不稳定,也能提供流畅的用户体验,避免“空白页”的出现。
Cache API
和IndexedDB
虽然都能存储数据,但用途侧重点不同。Cache API
更专注于HTTP请求的响应缓存,而IndexedDB
则是一个通用的数据存储解决方案。
3. Web SQL (已废弃):一段历史
Web SQL Database是早期尝试在浏览器中实现关系型数据库的一个标准,它基于SQLite。但由于没有一个统一的SQL方言标准,导致各浏览器实现不一致,最终被废弃了。现在,如果你看到有项目还在用这个,那基本可以认为是历史遗留问题了。它的功能已经被IndexedDB
更好地替代了。
总结一下:
localStorage
/sessionStorage
: 简单键值对,容量适中,同步操作,适用于用户偏好、临时数据。Cookies
: 容量小,自动随请求发送,可设置HttpOnly
等安全属性,适用于认证token、会话ID。IndexedDB
: 客户端NoSQL数据库,容量大,异步操作,支持复杂查询,适用于离线应用、大量结构化数据存储。Cache API
: 配合Service Worker
,用于缓存网络请求响应,实现离线和加速。
选择哪种存储技术,
今天带大家了解了的相关知识,希望对你有所帮助;关于文章的技术知识我们会一点点深入介绍,欢迎大家关注golang学习网公众号,一起学习编程~
-
501 收藏
-
501 收藏
-
501 收藏
-
501 收藏
-
501 收藏
-
198 收藏
-
153 收藏
-
138 收藏
-
375 收藏
-
468 收藏
-
136 收藏
-
155 收藏
-
298 收藏
-
445 收藏
-
419 收藏
-
430 收藏
-
250 收藏
-
- 前端进阶之JavaScript设计模式
- 设计模式是开发人员在软件开发过程中面临一般问题时的解决方案,代表了最佳的实践。本课程的主打内容包括JS常见设计模式以及具体应用场景,打造一站式知识长龙服务,适合有JS基础的同学学习。
- 立即学习 542次学习
-
- GO语言核心编程课程
- 本课程采用真实案例,全面具体可落地,从理论到实践,一步一步将GO核心编程技术、编程思想、底层实现融会贯通,使学习者贴近时代脉搏,做IT互联网时代的弄潮儿。
- 立即学习 511次学习
-
- 简单聊聊mysql8与网络通信
- 如有问题加微信:Le-studyg;在课程中,我们将首先介绍MySQL8的新特性,包括性能优化、安全增强、新数据类型等,帮助学生快速熟悉MySQL8的最新功能。接着,我们将深入解析MySQL的网络通信机制,包括协议、连接管理、数据传输等,让
- 立即学习 498次学习
-
- JavaScript正则表达式基础与实战
- 在任何一门编程语言中,正则表达式,都是一项重要的知识,它提供了高效的字符串匹配与捕获机制,可以极大的简化程序设计。
- 立即学习 487次学习
-
- 从零制作响应式网站—Grid布局
- 本系列教程将展示从零制作一个假想的网络科技公司官网,分为导航,轮播,关于我们,成功案例,服务流程,团队介绍,数据部分,公司动态,底部信息等内容区块。网站整体采用CSSGrid布局,支持响应式,有流畅过渡和展现动画。
- 立即学习 484次学习