重写学习 localStorage 与 sessionStorage

localStorage 与 sessionStorage
localStorage 与 sessionStorage 很多小伙伴对它们俩都很熟悉了;
  最熟悉的莫过下面这2条
1,localStorage 存储的数据没有时间限制,理论上永久有效;除非手动清除。
  sessionStorage 存储的数据在关闭当前页面后失效;
2,有存储大小限制,两者存储大约5MB,但实际大小可能会因浏览器而异。
  但是下面的这2条小伙伴不一定知道。
2,localStorage可以被storage监听到,但是sessionStorage不能监听到。
3,在地址复制url到另外一个窗口,localStorage的数据会被复制一份,
  但是sessionStorage中的数据不会被复制;
下面我们一起来看下

localStorage 可以监听到数据变化

就是浏览器打开了一个页面A,点击A页面会在浏览中打开一个新创建的页面B;
点击B页面的推荐功能,A页面的推荐数据也会实时跟新。

简单的思路

我们的相关是vue技术栈;
我们需要在A页面监听 localStorage 的变化
监听
window.addEventListener('storage',(storageData)=>{
  console.log(storageData)
})
storageData这个参数中有newValue,和oldValue;以及key
newValue:新值;oldValue:旧值
key是我们存储的key,通过key可以判断是否是我们监听的那个对象
我们获取到新值后只需要重新赋值即可;
在B页面中,如果用户点击了推荐;
我们就需要把新值存储到localStorage中

监听 localStorage数据的变化

A页面代码

<template>
  <div>
     <div >
      <div @click="goToPages" class="item-box">
         <h4>{{infoObj.time  }}</h4>
         <span>喜欢{{infoObj.like  }}</span>
      </div>
      </div>
  </div>
</template>
<script>
export default {
  data() {
    return {
      infoObj: {time:'【2024】前端,该卷什么呢?', id:'7329126541320536074', like:244},
    }
  },
  created(){
  },
  methods:{
    goToPages(){
       // 监听 storage 事件
      window.addEventListener('storage',(storageData)=>{
        if(storageData.key == this.infoObj.id){
          // 获取到变化后的新值
          let obj = JSON.parse(storageData.newValue)
          // 重新赋值
          this.infoObj.like = obj.like
        }
        console.log(storageData)
      })
      // 通过 setItem 存储在 localStorage 中,接受2个参数 key 和 value
      localStorage.setItem(this.infoObj.id,JSON.stringify(this.infoObj))
      const {href} = this.$router.resolve({
        path: "/details",
        query:{
          id:this.infoObj.id
        }
      });
      // 新窗口打开页面
      window.open(href, '_blank');
    }
  },
}
</script>
<style scoped lang="scss">
.item-box{
  display: flex;
  padding-left: 20px;
  box-sizing: border-box;
  height: 100px;
  line-height: 100px;
  background-color: azure;
  margin-bottom:10px;
  span{
    display: inline-block;
    margin-left: 10px;
  }
}
</style>

B页面代码

<template>
  <div>
     <div >
      <div  class="item-box">
         <h4>{{details.time  }}</h4>
         <!-- 只能触发一次 once-->
         <span @click.once="addLikeHandler">喜欢{{details.like  }}</span>
      </div>
      </div>
  </div>
</template>

<script>
  export default {
    data() {
      return {
        details:{}
      }
    },
    mounted() {
      this.getDetails()
    },
    methods:{
      getDetails(){
        // 获取数据
        const details = JSON.parse( localStorage.getItem(this.$route.query.id))
        this.details = details
      },
      addLikeHandler(){
        this.details.like = this.details.like + 1
        // 用户点击喜欢后,重新存储在 localStorage 中,这样A页面就可以监听了
        localStorage.setItem(this.$route.query.id,JSON.stringify(this.details))
      },
    }
  }
</script>

监听storage无法知晓sessionStorage数据的变化

上面的代码我们只需要将localStorage改成sessionStorage即可,
我们看下页面效果;发现监听storage无法知晓sessionStorage数据是否发生变化;
无论打开是否有_blank这属性;都是无法监听sessionStorage数据变化的。
再次提醒:监听storage无法知晓sessionStorage数据的变化

在地址复制url到另外一个窗口,localStorage和sessionStorage表现如何?

在地址复制url到另外一个窗口,
localStorage的数据会被复制一份。
但是sessionStorage中的数据不会被复制;

sessionStorage -数据不会被复制

localStorage-数据会被复制

window.open()的方式打开窗口,localStorage 和 sessionStorage表现如何?

localStorage的数据会被复制一份。
但是sessionStorage中的数据也会被复制;
无论是否是 window.open(href)还是window.open(href, '_blank')

localStorage设置过期时间

为啥要写这个,因为很多面试官都喜欢问。
设置过期的时间的基本思路是:在存储的时候,设置一个有效期的时间戳;
通过new Date().getTime() + 我们的有效时间
在读取的时候,
如果当前时间戳大于存储时设置的时间戳,说明已经过期;
需要移除当前这条Storage数据,返回 null;
如果当前时间戳小于存储时设置的时间戳;没有过期,正常返回;
class Storage {
  /**
   * key表示设置的key值,value存储的时候,time有效期单位分钟
  */
  setItem(key, value, minuteTime){
    let expires = 0
    if(minuteTime){
      // 计算存储时的有效时间需要转化为毫秒
      expires = new Date().getTime() + minuteTime * 1000 * 60
    }
    let storageData = JSON.stringify({value, expires})
    localStorage.setItem(key, storageData)  // 存储数据
  }
  getItem(key){
    const item = localStorage.getItem(key)
    const getData = JSON.parse(item)
    if(!getData){
      return null
    }
    // 说明已经过期了
    if(getData.expires < new Date().getTime()){
      // 移除 Storage
      this.removeItem(key)
      return null
    }
    return getData.value
  }
  // 移除 Storage
  removeItem(key){
    localStorage.removeItem(key)
  }
}
export const storage = new Storage()

使用的时候

import {storage} from './storage.js'
// 设置storage有效时间
storage.setItem('info',this.infoObj, 1)
// 读取storage数据
const details = storage.getItem('info')

尾声

如果阅读后,有所收获;
可以给我点个推荐吗? 也可以打赏我
感谢了!
posted @ 2024-06-05 09:01  南风晚来晚相识  阅读(124)  评论(0编辑  收藏  举报