給localStorage加上過時時間

1、酷酷的開頭

在掘金潛水的時間長達一年以後,我終於鼓起勇氣開始寫個人第一篇文章了。前端小菜,只是想記錄一下本身的想法,望各位看到這文的大佬輕噴。javascript

在如今先後端分離的開發模式下,存儲信息通常都不在使用以往使用的cookie了,就拿筆主我以前作過的項目來講。咱們都是登陸成功了以後後端會返回給我一個token,通常狀況下我會將這個token存到localStorage中,後續再每一次請求中都會將這個token攜帶在請求頭中。 至於爲何要存到localStorage中呢,相信作過單頁web應用的開發者們也知道,若是不存着,那用戶刷新了就啥都沒有了。前端

能夠見得前端存儲在項目中是愈來愈重要了,瀏覽器給咱們提供了兩個存儲方案,一個是localStorage,一個是sessionStorage。 存到localStorage中的信息是永久存儲,若是用戶不手動刪除或者代碼中沒有localStorage.removeItem(xxx)這樣的調用那這個信息將永遠不會消失; 在sessionStorage中存儲的信息則是一次性的,用戶關掉網頁了下一次在進入這個網頁信息就不會再存儲了。 可是在實際項目的運用中,這兩個方案的表現都不是那麼使人滿意。就好比說,我想要實現用戶登陸以後七天以內不須要再次登陸這樣的功能,token生成了以後,後端設置了這個token的過時時間爲7天,ok,傳到前端, 可是針對瀏覽器目前提供的存儲方案,我卻只能選擇永久存儲和一次性存儲。一次性存儲確定是不能知足需求的,永久存儲也違背了個人意願。java

2、以前在項目中的解決方案

以前我在項目中的作法是,在用localStorage存儲了token值的同時, 我還存了一個過時時間(一個毫秒數),而後在項目初始化的時候我就會去檢查這個時間看看是否是已經小於當前時間了,若是是就將token刪掉。 這樣後續項目在使用到這個token的時候token就已經從localStorage中被刪掉了。可是這樣作也有一個問題,若是打開項目的時間恰好是還有10s token就過時的話,token也不會被刪掉了。因而我腦殼裏就在構想一個可(垃)靠(圾)的解決方案,一不作,二不休,我把它封裝成了一個工具。git

先厚臉皮的介紹一下個人項目, sweet-storage, 請無視這土的要死的名字。 github的地址爲:github.com/Chechengyi/…。 順便也正(卑)大(鄙)光(無)明(恥)的求一波star。 github

3、提出新的想法

咳咳咳! 廢話很少說了,講一下個人實現思路。web

在遇到有過時時間的存儲需求時, 用我這個項目舉栗子, storage.save('name', 'chechengyi', 10000) 這行代碼的意思是我想在localStorage中存一個鍵爲name,值爲chechengyi的信息,我但願這條信息只存10s,在將信息存入localStorage中的同時,我會把它的過時時間信息以npm

{
      key: time
  }
複製代碼

的形式也存到localStorage中。 key就是鍵, time就是這條信息到期的時間。 這裏的時間的話應該存的是new Date().getTime()+咱們設置的時間。這樣就獲得了一個精確的毫秒數了。 這個過時時間信息在個人項目中以ISTORAGE_RECORD的字段存儲。 而後後面咱們在根據這裏面所提取出來的時間,即:new Date().getTime()-time這個時間去作一個定時器。定時器時間到了就將localStorage中存的信息以及存的時間信息就是那個對象中的key-time刪掉就好了。後端

可是這裏也有一個問題,就是。可能咱們須要有過時時間存儲的時間不僅有一條啊。難道存了三條我就作三個定時器?存的100條我就作100個定時器? 這也太low了並且也並不符合實際。因而我左思右想,發現我前幾天剛學習的優先隊列很適合用在這裏。瀏覽器

咱們能夠這樣作,基於ISTORAGE_RECORD拿出來的對象裏的time去作一個最小堆(個人這個優先隊列是基於最小堆的),最小堆嘛,根節點確定就是最小的,time最小的那個不就是最早執行的定時器嗎? 等這個定時器執行時就刪掉localStorage裏存的信息和時間信息,而後優先隊列出列,下一個排隊等着出列的元素就是下一個時間最近,等着過時的信息了。這裏涉及到了最小堆數據結構的操做就很少講了。有興趣的同窗能夠本身去看看實現。這就是個人項目實現的大概思路, 真正實現的話還要去考慮還沒過時就被用戶刪除了等等的狀況。cookie

到這裏了我又在想,不行啊,這樣過時了也只是「悄悄」的過時了。 我想知道它何時過時的,也就是我但願它過時的時候能通知我一聲行不行啊? 因而通過我又一輪的左思右想,我發現我去年學的發佈-訂閱模式能夠用到這裏。而後就是代碼實現啦,無非就是作了一個observers對象。 以存儲的key名去訂閱了一個事件,在個人項目中就是storage.on('name', (key)=>{}) 而後再定時器執行的時候我會observers.trriger('name')去發佈這個事件,而且將須要被刪除掉的信息的key傳入訂閱的函數當中。 這樣就作到了通知的功能。具體發佈-訂閱模式怎麼實現的也不在此多作贅述了。

4、無恥的總結

sweet-storage 實現的大概思路就說完了,有興趣的同窗能夠去看看源碼實現,在此強調 github的地址爲:github.com/Chechengyi/…。 個人代碼寫的很通(垃)俗易(圾)懂。

我還將這個項目傳到了npm上面, npm install sweet-storage就能夠安裝到本地。學以至用,這一年多來在各大論壇潛水每次看到別人分享心得內心都癢癢的,此次總算是下定了決心踏出第一步。在這個過程當中也學習到了不少,但願本身可以堅持下去。

若是有不對的地方但願朋友們指出,但願朋友們多給我提建議

最後在強調一波!!!

github的地址爲:github.com/Chechengyi/…

求star 求fuck......

相關文章
相關標籤/搜索