不要太相信 SetInterval!我被它給坑得好慘!
最近組員遇到了一個(gè) BUG,我們的需求是這樣的:前端需要通過(guò)輪詢的方式,每隔一段時(shí)間去做一些邏輯處理,并向后端發(fā)送請(qǐng)求上報(bào)。
出現(xiàn)的 BUG 是:后端發(fā)現(xiàn)前端有很長(zhǎng)一段時(shí)間都沒(méi)有向后端發(fā)起上報(bào)請(qǐng)求。
問(wèn)題排查
我們的的輪詢是通過(guò) setInterval 定時(shí)器去完成的,那么為啥定時(shí)器里的邏輯沒(méi)執(zhí)行呢?
通過(guò)向用戶詢問(wèn),我們得知了用戶有很長(zhǎng)一段時(shí)間沒(méi)有去看這個(gè)前端頁(yè)面,并且把這個(gè)頁(yè)面給隱藏了。
在這里我跟大家科普一個(gè)監(jiān)聽(tīng)事件 visibilitychange,他可以用來(lái)監(jiān)聽(tīng)當(dāng)前標(biāo)簽頁(yè)頁(yè)面顯隱的切換。
圖片
于是我需要復(fù)現(xiàn)一下這個(gè) BUG ,我簡(jiǎn)單寫了以下的代碼,并且做這些事:
- 先在頁(yè)面待一會(huì)
- 隱藏頁(yè)面一段時(shí)間
- 再顯示頁(yè)面,并查看控制臺(tái)的輸出是否連續(xù)
圖片
我先試著離開(kāi)很短一段時(shí)間,再回去看,可以發(fā)現(xiàn),控制臺(tái)的輸出還是很連續(xù)的,這說(shuō)明離開(kāi)很短時(shí)間,基本不會(huì)影響到定時(shí)器執(zhí)行的連續(xù)性。
圖片
第二次我離開(kāi)了一兩分鐘時(shí)間,可以看到定時(shí)器執(zhí)行的連續(xù)性不正常了,這說(shuō)明了當(dāng)頁(yè)面隱藏的時(shí)候,定時(shí)器的執(zhí)行有點(diǎn)類似于節(jié)流的感覺(jué),從而導(dǎo)致不太連續(xù)。
圖片
定時(shí)器連續(xù)性的保證?
其實(shí)瀏覽器這么做也是有他的道理的,畢竟當(dāng)頁(yè)面隱藏的時(shí)候,說(shuō)明這個(gè)頁(yè)面對(duì)于用戶當(dāng)前來(lái)說(shuō),不太重要了,所以適當(dāng)減少一些代碼邏輯的運(yùn)行,節(jié)省性能,也是無(wú)可厚非的!
但是如果你想一直保證定時(shí)器的連續(xù)性,還是有辦法做到的,可以用到我們的老朋友:Web Worker。
圖片
圖片
現(xiàn)在就能保證定時(shí)器的連續(xù)性執(zhí)行了!