Rietveld Code Review Tool
Help | Bug tracker | Discussion group | Source code

Side by Side Diff: lib/notification.js

Issue 5330039625220096: Issue 1162 - Cache notification URL matcher
Patch Set: Created Oct. 23, 2014, 2:09 p.m.
Left:
Right:
Use n/p to move between diff chunks; N/P to move between comments.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * This file is part of Adblock Plus <http://adblockplus.org/>, 2 * This file is part of Adblock Plus <http://adblockplus.org/>,
3 * Copyright (C) 2006-2014 Eyeo GmbH 3 * Copyright (C) 2006-2014 Eyeo GmbH
4 * 4 *
5 * Adblock Plus is free software: you can redistribute it and/or modify 5 * Adblock Plus is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License version 3 as 6 * it under the terms of the GNU General Public License version 3 as
7 * published by the Free Software Foundation. 7 * published by the Free Software Foundation.
8 * 8 *
9 * Adblock Plus is distributed in the hope that it will be useful, 9 * Adblock Plus is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
55 return translations[locale]; 55 return translations[locale];
56 56
57 let languagePart = locale.substring(0, locale.indexOf("-")); 57 let languagePart = locale.substring(0, locale.indexOf("-"));
58 if (languagePart && languagePart in translations) 58 if (languagePart && languagePart in translations)
59 return translations[languagePart]; 59 return translations[languagePart];
60 60
61 let defaultLocale = "en-US"; 61 let defaultLocale = "en-US";
62 return translations[defaultLocale]; 62 return translations[defaultLocale];
63 } 63 }
64 64
65 function initNotificationMatcher(notification)
66 {
67 if ("_matcher" in notification || !(notification.urlFilters instanceof Array))
68 return;
69
70 let matcher = new Matcher();
71 for (let urlFilter of notification.urlFilters)
72 matcher.add(Filter.fromText(urlFilter));
73 matcher.toJSON = () => {};
sergei 2018/01/03 11:12:22 This is not exactly how it's said in the issue "No
Thomas Greiner 2018/01/11 18:18:19 Fortunately, we can now use `Symbol` instead so th
kzar 2018/01/12 12:27:17 Acknowledged.
74 notification._matcher = matcher;
75 }
76
65 /** 77 /**
66 * The object providing actual downloading functionality. 78 * The object providing actual downloading functionality.
67 * @type Downloader 79 * @type Downloader
68 */ 80 */
69 let downloader = null; 81 let downloader = null;
70 let localData = []; 82 let localData = [];
83 let remoteData = [];
sergei 2018/01/03 11:12:22 Could you please add a comment that localData and
Thomas Greiner 2018/01/11 18:18:19 Yep, will do.
71 84
72 /** 85 /**
73 * Regularly fetches notifications and decides which to show. 86 * Regularly fetches notifications and decides which to show.
74 * @class 87 * @class
75 */ 88 */
76 let Notification = exports.Notification = 89 let Notification = exports.Notification =
77 { 90 {
78 /** 91 /**
79 * Called on module startup. 92 * Called on module startup.
80 */ 93 */
81 init: function() 94 init: function()
82 { 95 {
96 let notificationdata = Prefs.notificationdata.data;
97 if (notificationdata)
98 {
99 for (let notification of notificationdata.notifications)
100 initNotificationMatcher(notification);
101 remoteData = notificationdata.notifications;
102 }
103
83 downloader = new Downloader(this._getDownloadables.bind(this), INITIAL_DELAY , CHECK_INTERVAL); 104 downloader = new Downloader(this._getDownloadables.bind(this), INITIAL_DELAY , CHECK_INTERVAL);
84 onShutdown.add(function() 105 onShutdown.add(function()
85 { 106 {
86 downloader.cancel(); 107 downloader.cancel();
87 }); 108 });
88 109
89 downloader.onExpirationChange = this._onExpirationChange.bind(this); 110 downloader.onExpirationChange = this._onExpirationChange.bind(this);
90 downloader.onDownloadSuccess = this._onDownloadSuccess.bind(this); 111 downloader.onDownloadSuccess = this._onDownloadSuccess.bind(this);
91 downloader.onDownloadError = this._onDownloadError.bind(this); 112 downloader.onDownloadError = this._onDownloadError.bind(this);
92 }, 113 },
93 114
94 /** 115 /**
95 * Yields a Downloadable instances for the notifications download. 116 * Yields a Downloadable instances for the notifications download.
96 */ 117 */
97 _getDownloadables: function() 118 _getDownloadables: function()
kzar 2018/01/04 17:04:09 Why are we exporting functions like this and prefi
Thomas Greiner 2018/01/11 18:18:20 I don't think it's meant to be exported because it
98 { 119 {
99 let downloadable = new Downloadable(Prefs.notificationurl); 120 let downloadable = new Downloadable(Prefs.notificationurl);
100 if (typeof Prefs.notificationdata.lastError === "number") 121 if (typeof Prefs.notificationdata.lastError === "number")
101 downloadable.lastError = Prefs.notificationdata.lastError; 122 downloadable.lastError = Prefs.notificationdata.lastError;
102 if (typeof Prefs.notificationdata.lastCheck === "number") 123 if (typeof Prefs.notificationdata.lastCheck === "number")
103 downloadable.lastCheck = Prefs.notificationdata.lastCheck; 124 downloadable.lastCheck = Prefs.notificationdata.lastCheck;
104 if (typeof Prefs.notificationdata.data === "object" && "version" in Prefs.no tificationdata.data) 125 if (typeof Prefs.notificationdata.data === "object" && "version" in Prefs.no tificationdata.data)
105 downloadable.lastVersion = Prefs.notificationdata.data.version; 126 downloadable.lastVersion = Prefs.notificationdata.data.version;
106 if (typeof Prefs.notificationdata.softExpiration === "number") 127 if (typeof Prefs.notificationdata.softExpiration === "number")
107 downloadable.softExpiration = Prefs.notificationdata.softExpiration; 128 downloadable.softExpiration = Prefs.notificationdata.softExpiration;
(...skipping 16 matching lines...) Expand all
124 { 145 {
125 let data = JSON.parse(responseText); 146 let data = JSON.parse(responseText);
126 for (let notification of data.notifications) 147 for (let notification of data.notifications)
127 { 148 {
128 if ("severity" in notification) 149 if ("severity" in notification)
129 { 150 {
130 if (!("type" in notification)) 151 if (!("type" in notification))
131 notification.type = notification.severity; 152 notification.type = notification.severity;
132 delete notification.severity; 153 delete notification.severity;
133 } 154 }
155 initNotificationMatcher(notification);
134 } 156 }
157 remoteData = data.notifications;
sergei 2018/01/03 11:12:22 It's a bit theoretical but IMO it can be a technic
kzar 2018/01/04 17:04:09 Yea, I don't think these changes are necessary now
Thomas Greiner 2018/01/11 18:18:19 Good point. I don't remember why I made this chang
135 Prefs.notificationdata.data = data; 158 Prefs.notificationdata.data = data;
sergei 2018/01/03 11:12:22 Despite it's not directly a part of this issue, sh
kzar 2018/01/04 17:04:09 Hmm, I'm not too familiar with this code but I thi
Thomas Greiner 2018/01/11 18:18:19 By overriding existing notifications we can contro
136 } 159 }
137 catch (e) 160 catch (e)
138 { 161 {
139 Cu.reportError(e); 162 Cu.reportError(e);
140 errorCallback("synchronize_invalid_data"); 163 errorCallback("synchronize_invalid_data");
141 return; 164 return;
142 } 165 }
143 166
144 Prefs.notificationdata.lastError = 0; 167 Prefs.notificationdata.lastError = 0;
145 Prefs.notificationdata.downloadStatus = "synchronize_ok"; 168 Prefs.notificationdata.downloadStatus = "synchronize_ok";
146 [Prefs.notificationdata.softExpiration, Prefs.notificationdata.hardExpiratio n] = downloader.processExpirationInterval(EXPIRATION_INTERVAL); 169 [Prefs.notificationdata.softExpiration, Prefs.notificationdata.hardExpiratio n] = downloader.processExpirationInterval(EXPIRATION_INTERVAL);
147 saveNotificationData(); 170 saveNotificationData();
148 }, 171 },
149 172
150 _onDownloadError: function(downloadable, downloadURL, error, channelStatus, re sponseStatus, redirectCallback) 173 _onDownloadError: function(downloadable, downloadURL, error, channelStatus, re sponseStatus, redirectCallback)
151 { 174 {
152 Prefs.notificationdata.lastError = Date.now(); 175 Prefs.notificationdata.lastError = Date.now();
153 Prefs.notificationdata.downloadStatus = error; 176 Prefs.notificationdata.downloadStatus = error;
154 saveNotificationData(); 177 saveNotificationData();
155 }, 178 },
156 179
157 /** 180 /**
158 * Determines which notification is to be shown next. 181 * Determines which notification is to be shown next.
159 * @param {String} url URL to match notifications to (optional) 182 * @param {String} url URL to match notifications to (optional)
160 * @return {Object} notification to be shown, or null if there is none 183 * @return {Object} notification to be shown, or null if there is none
161 */ 184 */
162 getNextToShow: function(url) 185 getNextToShow: function(url)
kzar 2018/01/04 17:04:09 This function is confusing, each section needs a c
Thomas Greiner 2018/01/11 18:18:19 Agreed but I'd suggest not touching any code that'
kzar 2018/01/12 12:27:17 IMO I think we should tidy this code up while addr
163 { 186 {
164 function checkTarget(target, parameter, name, version) 187 function checkTarget(target, parameter, name, version)
165 { 188 {
166 let minVersionKey = parameter + "MinVersion"; 189 let minVersionKey = parameter + "MinVersion";
167 let maxVersionKey = parameter + "MaxVersion"; 190 let maxVersionKey = parameter + "MaxVersion";
168 return !((parameter in target && target[parameter] != name) || 191 return !((parameter in target && target[parameter] != name) ||
169 (minVersionKey in target && Services.vc.compare(version, target[m inVersionKey]) < 0) || 192 (minVersionKey in target && Services.vc.compare(version, target[m inVersionKey]) < 0) ||
170 (maxVersionKey in target && Services.vc.compare(version, target[m axVersionKey]) > 0)); 193 (maxVersionKey in target && Services.vc.compare(version, target[m axVersionKey]) > 0));
171 } 194 }
172 195
173 let remoteData = [];
174 if (typeof Prefs.notificationdata.data == "object" && Prefs.notificationdata .data.notifications instanceof Array)
175 remoteData = Prefs.notificationdata.data.notifications;
176
177 if (!(Prefs.notificationdata.shown instanceof Array)) 196 if (!(Prefs.notificationdata.shown instanceof Array))
178 { 197 {
179 Prefs.notificationdata.shown = []; 198 Prefs.notificationdata.shown = [];
180 saveNotificationData(); 199 saveNotificationData();
181 } 200 }
182 201
183 let notifications = localData.concat(remoteData); 202 let notifications = localData.concat(remoteData);
184 if (notifications.length === 0) 203 if (notifications.length === 0)
185 return null; 204 return null;
186 205
187 let {addonName, addonVersion, application, applicationVersion, platform, pla tformVersion} = require("info"); 206 let {addonName, addonVersion, application, applicationVersion, platform, pla tformVersion} = require("info");
188 let notificationToShow = null; 207 let notificationToShow = null;
189 for (let notification of notifications) 208 for (let notification of notifications)
190 { 209 {
191 if ((typeof notification.type === "undefined" || notification.type !== "cr itical") 210 if ((typeof notification.type === "undefined" || notification.type !== "cr itical")
192 && Prefs.notificationdata.shown.indexOf(notification.id) !== -1) 211 && Prefs.notificationdata.shown.indexOf(notification.id) !== -1)
kzar 2018/01/04 17:04:09 We can use .includes(notification.id) these days (
193 continue; 212 continue;
194 213
195 if (typeof url === "string" || notification.urlFilters instanceof Array) 214 if (typeof url === "string" || "_matcher" in notification)
kzar 2018/01/04 17:04:09 IMO this code should instead be replaced with a ca
Thomas Greiner 2018/01/11 18:18:19 I agree that splitting that off into its own funct
kzar 2018/01/12 12:27:17 Acknowledged.
196 { 215 {
197 if (typeof url === "string" && notification.urlFilters instanceof Array) 216 if (typeof url === "string" && "_matcher" in notification)
198 { 217 {
199 let matcher = new Matcher(); 218 if (!notification._matcher.matchesAny(url, "DOCUMENT", url))
200 for (let urlFilter of notification.urlFilters)
201 matcher.add(Filter.fromText(urlFilter));
202 if (!matcher.matchesAny(url, "DOCUMENT", url))
203 continue; 219 continue;
204 } 220 }
205 else 221 else
206 continue; 222 continue;
207 } 223 }
208 224
209 if (notification.targets instanceof Array) 225 if (notification.targets instanceof Array)
210 { 226 {
211 let match = false; 227 let match = false;
212 for (let target of notification.targets) 228 for (let target of notification.targets)
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after
271 return localizedTexts; 287 return localizedTexts;
272 }, 288 },
273 289
274 /** 290 /**
275 * Adds a local notification. 291 * Adds a local notification.
276 * @param {Object} notification notification to add 292 * @param {Object} notification notification to add
277 */ 293 */
278 addNotification: function(notification) 294 addNotification: function(notification)
279 { 295 {
280 if (localData.indexOf(notification) == -1) 296 if (localData.indexOf(notification) == -1)
297 {
298 initNotificationMatcher(notification);
281 localData.push(notification); 299 localData.push(notification);
300 }
282 }, 301 },
283 302
284 /** 303 /**
285 * Removes an existing local notification. 304 * Removes an existing local notification.
286 * @param {Object} notification notification to remove 305 * @param {Object} notification notification to remove
287 */ 306 */
288 removeNotification: function(notification) 307 removeNotification: function(notification)
289 { 308 {
290 let index = localData.indexOf(notification); 309 let index = localData.indexOf(notification);
291 if (index > -1) 310 if (index > -1)
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
325 triggerQuestionListeners: function(id, approved) 344 triggerQuestionListeners: function(id, approved)
326 { 345 {
327 if (!(id in listeners)) 346 if (!(id in listeners))
328 return; 347 return;
329 let questionListeners = listeners[id]; 348 let questionListeners = listeners[id];
330 for (let listener of questionListeners) 349 for (let listener of questionListeners)
331 listener(approved); 350 listener(approved);
332 } 351 }
333 }; 352 };
334 Notification.init(); 353 Notification.init();
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld