@@ -128,25 +128,22 @@ async function getFollowedStreams(userId: string) {
128128 return followedStreams ;
129129}
130130
131- async function filterFollowedStreams ( streams : HelixStream [ ] ) {
132- const [ followedStreams , settings ] = await Promise . all ( [
133- stores . followedStreams . get ( ) ,
134- stores . settings . get ( ) ,
135- ] ) ;
131+ async function filterNewStreams ( newStreams : HelixStream [ ] , oldStreams : HelixStream [ ] ) {
132+ const settings = await stores . settings . get ( ) ;
136133
137134 const {
138135 notifications : { ignoredCategories, selectedUsers, withCategoryChanges, withFilters } ,
139136 } = settings ;
140137
141- return streams . filter ( ( stream ) => {
138+ return newStreams . filter ( ( stream ) => {
142139 if (
143140 ( withFilters && ! selectedUsers . includes ( stream . userId ) ) ||
144- ignoredCategories . some ( matchString . bind ( null , stream . gameName ) )
141+ ignoredCategories . some ( ( input ) => matchString ( stream . gameName , input ) )
145142 ) {
146143 return false ;
147144 }
148145
149- const oldStream = find ( followedStreams , {
146+ const oldStream = find ( oldStreams , {
150147 userId : stream . userId ,
151148 } ) ;
152149
@@ -166,7 +163,7 @@ async function refreshCurrentUser(accessToken: string | null) {
166163 return currentUser ;
167164}
168165
169- async function refreshFollowedStreams ( user : HelixUser , showNotifications = true ) {
166+ async function refreshFollowedStreams ( user : HelixUser ) {
170167 const settings = await stores . settings . get ( ) ;
171168
172169 let followedStreams = new Array < HelixStream > ( ) ;
@@ -177,66 +174,70 @@ async function refreshFollowedStreams(user: HelixUser, showNotifications = true)
177174 if ( ! settings . streams . withReruns ) {
178175 remove ( followedStreams , isRerunStream ) ;
179176 }
180-
181- if ( showNotifications && settings . notifications . enabled ) {
182- const streams = await filterFollowedStreams ( followedStreams ) ;
183- const users = await getUsersByIds ( map ( streams , "userId" ) ) ;
184-
185- settlePromises ( streams , async ( stream ) => {
186- const create = ( iconUrl = browser . runtime . getURL ( "icon-96.png" ) ) =>
187- browser . notifications . create ( `${ Date . now ( ) } :stream:${ stream . userLogin } ` , {
188- title : t ( `notificationMessage_stream${ stream . gameName ? "Playing" : "Online" } ` , [
189- stream . userName || stream . userLogin ,
190- stream . gameName ,
191- ] ) ,
192- message : stream . title || t ( "detailText_noTitle" ) ,
193- type : "basic" ,
194- iconUrl,
195- } ) ;
196-
197- try {
198- const user = find ( users , {
199- id : stream . userId ,
200- } ) ;
201-
202- if ( user ) {
203- return await create ( user . profileImageUrl ) ;
204- }
205- } catch { } // eslint-disable-line no-empty
206-
207- await create ( ) ;
208- } ) ;
209- }
210177 }
211178
212179 await stores . followedStreams . set ( followedStreams ) ;
213180}
214181
215- async function refresh ( withNotifications : boolean ) {
182+ async function refresh ( ) {
216183 try {
217184 const user = await refreshCurrentUser ( await stores . accessToken . get ( ) ) ;
218185
219186 if ( user ) {
220- await refreshFollowedStreams ( user , withNotifications ) ;
187+ await refreshFollowedStreams ( user ) ;
221188 }
222189 } catch { } // eslint-disable-line no-empty
223190
191+ browser . alarms . clearAll ( ) ;
224192 browser . alarms . create ( "refresh" , {
225193 delayInMinutes : 1 ,
226194 } ) ;
227195}
228196
229- async function refreshActionBadge ( ) {
230- const [ currentUser , followedStreams , settings ] = await Promise . all ( [
197+ async function sendNotifications ( newStreams : HelixStream [ ] , oldStreams : HelixStream [ ] ) {
198+ const settings = await stores . settings . get ( ) ;
199+
200+ if ( settings . notifications . enabled ) {
201+ const filteredStreams = await filterNewStreams ( newStreams , oldStreams ) ;
202+ const users = await getUsersByIds ( map ( filteredStreams , "userId" ) ) ;
203+
204+ settlePromises ( filteredStreams , async ( stream ) => {
205+ const create = ( iconUrl = browser . runtime . getURL ( "icon-96.png" ) ) =>
206+ browser . notifications . create ( `${ Date . now ( ) } :stream:${ stream . userLogin } ` , {
207+ title : t ( `notificationMessage_stream${ stream . gameName ? "Playing" : "Online" } ` , [
208+ stream . userName || stream . userLogin ,
209+ stream . gameName ,
210+ ] ) ,
211+ message : stream . title || t ( "detailText_noTitle" ) ,
212+ type : "basic" ,
213+ iconUrl,
214+ } ) ;
215+
216+ try {
217+ const user = find ( users , {
218+ id : stream . userId ,
219+ } ) ;
220+
221+ if ( user ) {
222+ return await create ( user . profileImageUrl ) ;
223+ }
224+ } catch { } // eslint-disable-line no-empty
225+
226+ await create ( ) ;
227+ } ) ;
228+ }
229+ }
230+
231+ async function refreshActionBadge ( count : number ) {
232+ const [ currentUser , settings ] = await Promise . all ( [
231233 stores . currentUser . get ( ) ,
232- stores . followedStreams . get ( ) ,
233234 stores . settings . get ( ) ,
234235 ] ) ;
235236
236237 let text = "" ;
237238
238- if ( settings . badge . enabled && followedStreams . length > 0 ) {
239- text = followedStreams . length . toLocaleString ( "en-US" ) ;
239+ if ( settings . badge . enabled && count > 0 ) {
240+ text = count . toLocaleString ( "en-US" ) ;
240241 }
241242
242243 const getIconPath = ( size : number ) =>
@@ -288,19 +289,14 @@ async function authorize() {
288289 return openUrl ( AUTHORIZE_URL , undefined , true ) ;
289290}
290291
291- async function setup ( ) : Promise < void > {
292- await settlePromises ( Object . values ( stores ) , ( store ) => store . migrate ( ) ) ;
293- await refresh ( false ) ;
294- }
295-
296292async function reset ( ) : Promise < void > {
297293 await Promise . allSettled ( [
298294 browser . storage . local . clear ( ) ,
299295 browser . storage . session . clear ( ) ,
300296 browser . storage . sync . clear ( ) ,
301297 ] ) ;
302298
303- await setup ( ) ;
299+ await refresh ( ) ;
304300}
305301
306302async function revoke ( ) {
@@ -322,19 +318,7 @@ async function revoke() {
322318 await stores . accessToken . reset ( ) ;
323319}
324320
325- const messageHandlers : Dictionary < ( ...args : any [ ] ) => Promise < any > > = {
326- authorize,
327- backup,
328- refresh,
329- request,
330- reset,
331- restore,
332- revoke,
333- } ;
334-
335- browser . alarms . onAlarm . addListener ( ( alarm ) => {
336- refresh ( Date . now ( ) < alarm . scheduledTime + 300_000 ) ;
337- } ) ;
321+ browser . alarms . onAlarm . addListener ( ( ) => refresh ( ) ) ;
338322
339323browser . notifications . onClicked . addListener ( ( notificationId ) => {
340324 const [ , type , data ] = notificationId . split ( ":" ) ;
@@ -348,13 +332,15 @@ browser.notifications.onClicked.addListener((notificationId) => {
348332 }
349333} ) ;
350334
351- browser . runtime . onInstalled . addListener ( ( ) => {
352- setup ( ) ;
353- } ) ;
354-
355- browser . runtime . onStartup . addListener ( ( ) => {
356- setup ( ) ;
357- } ) ;
335+ const messageHandlers : Dictionary < ( ...args : any [ ] ) => Promise < any > > = {
336+ authorize,
337+ backup,
338+ refresh,
339+ request,
340+ reset,
341+ restore,
342+ revoke,
343+ } ;
358344
359345browser . runtime . onMessage . addListener ( ( message ) => {
360346 const { [ message . type ] : handler } = messageHandlers ;
@@ -382,24 +368,15 @@ browser.tabs.onUpdated.addListener((tabId, changeInfo, tab) => {
382368 }
383369} ) ;
384370
385- stores . accessToken . onChange ( ( ) => {
386- refresh ( false ) ;
387- } ) ;
388-
389- stores . followedStreams . onChange ( ( ) => {
390- refreshActionBadge ( ) ;
391- } ) ;
392-
393- stores . settings . onChange ( ( ) => {
394- refreshActionBadge ( ) ;
395- } ) ;
371+ stores . accessToken . onChange ( ( ) => refresh ( ) ) ;
372+ stores . settings . onChange ( ( ) => refresh ( ) ) ;
396373
397- async function checkAlarm ( ) {
398- if ( await browser . alarms . get ( "refresh" ) ) {
399- return ;
374+ stores . followedStreams . onChange ( ( newValue , oldValue ) => {
375+ if ( Array . isArray ( oldValue ) ) {
376+ sendNotifications ( newValue , oldValue ) ;
400377 }
401378
402- refresh ( false ) ;
403- }
379+ refreshActionBadge ( newValue . length ) ;
380+ } ) ;
404381
405- checkAlarm ( ) ;
382+ refresh ( ) ;
0 commit comments