| OLD | NEW | 
|    1 /* |    1 /* | 
|    2  * This file is part of Adblock Plus <https://adblockplus.org/>, |    2  * This file is part of Adblock Plus <https://adblockplus.org/>, | 
|    3  * Copyright (C) 2006-present eyeo GmbH |    3  * Copyright (C) 2006-present 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 | 
|   11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the |   11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the | 
|   12  * GNU General Public License for more details. |   12  * GNU General Public License for more details. | 
|   13  * |   13  * | 
|   14  * You should have received a copy of the GNU General Public License |   14  * You should have received a copy of the GNU General Public License | 
|   15  * along with Adblock Plus.  If not, see <http://www.gnu.org/licenses/>. |   15  * along with Adblock Plus.  If not, see <http://www.gnu.org/licenses/>. | 
|   16  */ |   16  */ | 
|   17  |   17  | 
|   18 "use strict"; |   18 "use strict"; | 
|   19  |   19  | 
|   20 window.ext = {}; |   20 window.ext = {}; | 
|   21  |   21  | 
|   22 let reportData = new DOMParser().parseFromString("<report></report>", "text/xml"
     ); |   22 let reportData = new DOMParser().parseFromString("<report></report>", | 
 |   23                                                  "text/xml"); | 
|   23  |   24  | 
|   24 let pages = { |   25 let pages = { | 
|   25   "typeSelectorPage": [initTypeSelector, leaveTypeSelector], |   26   typeSelectorPage: [initTypeSelector, leaveTypeSelector], | 
|   26   "commentPage": [initCommentPage, leaveCommentPage], |   27   commentPage: [initCommentPage, leaveCommentPage], | 
|   27   "sendPage": [initSendPage, leaveSendPage] |   28   sendPage: [initSendPage, leaveSendPage] | 
|   28 }; |   29 }; | 
|   29  |   30  | 
|   30 document.addEventListener("DOMContentLoaded", () => |   31 document.addEventListener("DOMContentLoaded", () => | 
|   31 { |   32 { | 
|   32   document.getElementById("cancel").addEventListener("click", () => |   33   document.getElementById("cancel").addEventListener("click", () => | 
|   33   { |   34   { | 
|   34     window.close(); |   35     window.close(); | 
|   35   }); |   36   }); | 
|   36  |   37  | 
|   37   document.getElementById("continue").addEventListener("click", () => |   38   document.getElementById("continue").addEventListener("click", () => | 
|   38   { |   39   { | 
|   39     if (!document.getElementById("continue").disabled) |   40     if (!document.getElementById("continue").disabled) | 
|   40       pages[getCurrentPage()][1](); |   41       pages[getCurrentPage()][1](); | 
|   41   }); |   42   }); | 
|   42  |   43  | 
|   43   document.addEventListener("keydown", event => |   44   document.addEventListener("keydown", event => | 
|   44   { |   45   { | 
|   45     let blacklistedElements = new Set(["textarea", "button", "a"]) |   46     let blacklisted = new Set(["textarea", "button", "a"]); | 
|   46  |   47  | 
|   47     if (event.key == "Enter" && !blacklistedElements.has(event.target.localName)
     ) |   48     if (event.key == "Enter" && !blacklisted.has(event.target.localName)) | 
|   48       document.getElementById("continue").click(); |   49       document.getElementById("continue").click(); | 
|   49     else if (event.key == "Escape") |   50     else if (event.key == "Escape") | 
|   50       document.getElementById("cancel").click(); |   51       document.getElementById("cancel").click(); | 
|   51   }); |   52   }); | 
|   52  |   53  | 
|   53   browser.runtime.sendMessage({ |   54   browser.runtime.sendMessage({ | 
|   54     type: "app.get", |   55     type: "app.get", | 
|   55     what: "doclink", |   56     what: "doclink", | 
|   56     link: "reporter_privacy" |   57     link: "reporter_privacy" | 
|   57   }).then(url => |   58   }).then(url => | 
| (...skipping 17 matching lines...) Expand all  Loading... | 
|   75   let previousPage = document.querySelector(".page:not([hidden])"); |   76   let previousPage = document.querySelector(".page:not([hidden])"); | 
|   76   if (previousPage) |   77   if (previousPage) | 
|   77     previousPage.hidden = true; |   78     previousPage.hidden = true; | 
|   78  |   79  | 
|   79   document.getElementById(pageId).hidden = false; |   80   document.getElementById(pageId).hidden = false; | 
|   80   pages[pageId][0](); |   81   pages[pageId][0](); | 
|   81 } |   82 } | 
|   82  |   83  | 
|   83 function censorURL(url) |   84 function censorURL(url) | 
|   84 { |   85 { | 
|   85   return url.replace(/([?;&\/#][^?;&\/#]+?=)[^?;&\/#]+/g, "$1*"); |   86   return url.replace(/([?;&/#][^?;&/#]+?=)[^?;&/#]+/g, "$1*"); | 
|   86 } |   87 } | 
|   87  |   88  | 
|   88 function encodeHTML(str) |   89 function encodeHTML(str) | 
|   89 { |   90 { | 
|   90   return str.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").
     replace(/"/g, """); |   91   return str.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").
     replace(/"/g, """); | 
|   91 } |   92 } | 
|   92  |   93  | 
|   93 function serializeReportData() |   94 function serializeReportData() | 
|   94 { |   95 { | 
|   95   let result = new XMLSerializer().serializeToString(reportData); |   96   let result = new XMLSerializer().serializeToString(reportData); | 
|   96  |   97  | 
|   97   // Insert line breaks before each new tag |   98   // Insert line breaks before each new tag | 
|   98   result = result.replace(/(<[^\/]([^"<>]*|"[^"]*")*>)/g, "\n$1"); |   99   result = result.replace(/(<[^/]([^"<>]*|"[^"]*")*>)/g, "\n$1"); | 
|   99   result = result.replace(/^\n+/, ""); |  100   result = result.replace(/^\n+/, ""); | 
|  100   return result; |  101   return result; | 
|  101 } |  102 } | 
|  102  |  103  | 
|  103 function retrieveAddonInfo() |  104 function retrieveAddonInfo() | 
|  104 { |  105 { | 
|  105   let element = reportData.createElement("adblock-plus"); |  106   let element = reportData.createElement("adblock-plus"); | 
|  106   return browser.runtime.sendMessage({ |  107   return browser.runtime.sendMessage({ | 
|  107     type: "app.get", |  108     type: "app.get", | 
|  108     what: "addonVersion" |  109     what: "addonVersion" | 
| (...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  183     let element = reportData.createElement("subscriptions"); |  184     let element = reportData.createElement("subscriptions"); | 
|  184     for (let subscription of subscriptions) |  185     for (let subscription of subscriptions) | 
|  185     { |  186     { | 
|  186       if (!/^(http|https|ftp):/.test(subscription.url)) |  187       if (!/^(http|https|ftp):/.test(subscription.url)) | 
|  187         continue; |  188         continue; | 
|  188  |  189  | 
|  189       let now = Math.round(Date.now() / 1000); |  190       let now = Math.round(Date.now() / 1000); | 
|  190       let subscriptionElement = reportData.createElement("subscription"); |  191       let subscriptionElement = reportData.createElement("subscription"); | 
|  191       subscriptionElement.setAttribute("id", subscription.url); |  192       subscriptionElement.setAttribute("id", subscription.url); | 
|  192       if (subscription.lastDownload) |  193       if (subscription.lastDownload) | 
|  193         subscriptionElement.setAttribute("lastDownloadAttempt", subscription.las
     tDownload - now); |  194       { | 
|  194       subscriptionElement.setAttribute("downloadStatus", subscription.downloadSt
     atus); |  195         subscriptionElement.setAttribute("lastDownloadAttempt", | 
 |  196                                          subscription.lastDownload - now); | 
 |  197       } | 
 |  198       subscriptionElement.setAttribute("downloadStatus", | 
 |  199                                        subscription.downloadStatus); | 
|  195       element.appendChild(subscriptionElement); |  200       element.appendChild(subscriptionElement); | 
|  196     } |  201     } | 
|  197     reportData.documentElement.appendChild(element); |  202     reportData.documentElement.appendChild(element); | 
|  198   }); |  203   }); | 
|  199 } |  204 } | 
|  200  |  205  | 
|  201 function initDataCollector() |  206 function initDataCollector() | 
|  202 { |  207 { | 
|  203   Promise.resolve().then(() => |  208   Promise.resolve().then(() => | 
|  204   { |  209   { | 
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  241 function leaveTypeSelector() |  246 function leaveTypeSelector() | 
|  242 { |  247 { | 
|  243   let checkbox = document.querySelector("input[name='type']:checked"); |  248   let checkbox = document.querySelector("input[name='type']:checked"); | 
|  244   reportData.documentElement.setAttribute("type", checkbox.value); |  249   reportData.documentElement.setAttribute("type", checkbox.value); | 
|  245   setCurrentPage("commentPage"); |  250   setCurrentPage("commentPage"); | 
|  246 } |  251 } | 
|  247  |  252  | 
|  248 function initCommentPage() |  253 function initCommentPage() | 
|  249 { |  254 { | 
|  250   let continueButton = document.getElementById("continue"); |  255   let continueButton = document.getElementById("continue"); | 
 |  256   let label = browser.i18n.getMessage("issueReporter_sendButton_label"); | 
 |  257   continueButton.textContent = label; | 
|  251   continueButton.disabled = true; |  258   continueButton.disabled = true; | 
|  252   continueButton.textContent = browser.i18n.getMessage("issueReporter_sendButton
     _label"); |  | 
|  253  |  259  | 
|  254   let emailElement = reportData.createElement("email"); |  260   let emailElement = reportData.createElement("email"); | 
|  255   let emailField = document.getElementById("email"); |  261   let emailField = document.getElementById("email"); | 
|  256   let anonymousSubmissionField = document.getElementById("anonymousSubmission"); |  262   let anonymousSubmissionField = document.getElementById("anonymousSubmission"); | 
|  257   let validateEmail = () => |  263   let validateEmail = () => | 
|  258   { |  264   { | 
|  259     document.getElementById("anonymousSubmissionWarning").setAttribute("data-inv
     isible", !anonymousSubmissionField.checked); |  265     document.getElementById("anonymousSubmissionWarning") | 
 |  266             .setAttribute("data-invisible", !anonymousSubmissionField.checked); | 
|  260     if (anonymousSubmissionField.checked) |  267     if (anonymousSubmissionField.checked) | 
|  261     { |  268     { | 
|  262       emailField.value = ""; |  269       emailField.value = ""; | 
|  263       emailField.disabled = true; |  270       emailField.disabled = true; | 
|  264       continueButton.disabled = false; |  271       continueButton.disabled = false; | 
|  265       if (emailElement.parentNode) |  272       if (emailElement.parentNode) | 
|  266         emailElement.parentNode.removeChild(emailElement); |  273         emailElement.parentNode.removeChild(emailElement); | 
|  267     } |  274     } | 
|  268     else |  275     else | 
|  269     { |  276     { | 
| (...skipping 11 matching lines...) Expand all  Loading... | 
|  281   let commentElement = reportData.createElement("comment"); |  288   let commentElement = reportData.createElement("comment"); | 
|  282   document.getElementById("comment").addEventListener("input", event => |  289   document.getElementById("comment").addEventListener("input", event => | 
|  283   { |  290   { | 
|  284     if (commentElement.parentNode) |  291     if (commentElement.parentNode) | 
|  285       commentElement.parentNode.removeChild(commentElement); |  292       commentElement.parentNode.removeChild(commentElement); | 
|  286  |  293  | 
|  287     let value = event.target.value.trim(); |  294     let value = event.target.value.trim(); | 
|  288     commentElement.textContent = value.substr(0, 1000); |  295     commentElement.textContent = value.substr(0, 1000); | 
|  289     if (value) |  296     if (value) | 
|  290       reportData.documentElement.appendChild(commentElement); |  297       reportData.documentElement.appendChild(commentElement); | 
|  291     document.getElementById("commentLengthWarning").setAttribute("data-invisible
     ", value.length <= 1000); |  298     document.getElementById("commentLengthWarning") | 
 |  299             .setAttribute("data-invisible", value.length <= 1000); | 
|  292   }); |  300   }); | 
|  293  |  301  | 
|  294   document.getElementById("showData").addEventListener("click", event => |  302   document.getElementById("showData").addEventListener("click", event => | 
|  295   { |  303   { | 
|  296     event.preventDefault(); |  304     event.preventDefault(); | 
|  297  |  305  | 
|  298     // window.open() won't open data: URIs in Chrome |  306     // window.open() won't open data: URIs in Chrome | 
|  299     browser.tabs.getCurrent().then(tab => |  307     browser.tabs.getCurrent().then(tab => | 
|  300     { |  308     { | 
|  301       browser.tabs.create({ |  309       browser.tabs.create({ | 
|  302         url: "data:text/xml;charset=utf-8," + encodeURIComponent(serializeReport
     Data()), |  310         url: "data:text/xml;charset=utf-8," + | 
 |  311              encodeURIComponent(serializeReportData()), | 
|  303         openerTabId: tab.id |  312         openerTabId: tab.id | 
|  304       }); |  313       }); | 
|  305     }) |  314     }); | 
|  306   }); |  315   }); | 
|  307  |  316  | 
|  308   emailField.focus(); |  317   emailField.focus(); | 
|  309 } |  318 } | 
|  310  |  319  | 
|  311 function leaveCommentPage() |  320 function leaveCommentPage() | 
|  312 { |  321 { | 
|  313   setCurrentPage("sendPage"); |  322   setCurrentPage("sendPage"); | 
|  314 } |  323 } | 
|  315  |  324  | 
|  316 function initSendPage() |  325 function initSendPage() | 
|  317 { |  326 { | 
|  318   document.getElementById("cancel").hidden = true; |  327   document.getElementById("cancel").hidden = true; | 
|  319  |  328  | 
|  320   let continueButton = document.getElementById("continue"); |  329   let continueButton = document.getElementById("continue"); | 
|  321   continueButton.textContent = browser.i18n.getMessage("issueReporter_doneButton
     _label"); |  330   let label = browser.i18n.getMessage("issueReporter_doneButton_label"); | 
 |  331   continueButton.textContent = label; | 
|  322   continueButton.disabled = true; |  332   continueButton.disabled = true; | 
|  323  |  333  | 
|  324   let uuid = new Uint16Array(8); |  334   let uuid = new Uint16Array(8); | 
|  325   window.crypto.getRandomValues(uuid); |  335   window.crypto.getRandomValues(uuid); | 
|  326   uuid[3] = uuid[3] & 0x0FFF | 0x4000;  // version 4 |  336   uuid[3] = uuid[3] & 0x0FFF | 0x4000;  // version 4 | 
|  327   uuid[4] = uuid[4] & 0x3FFF | 0x8000;  // variant 1 |  337   uuid[4] = uuid[4] & 0x3FFF | 0x8000;  // variant 1 | 
|  328  |  338  | 
|  329   let uuidString = ""; |  339   let uuidString = ""; | 
|  330   for (let i = 0; i < uuid.length; i++) |  340   for (let i = 0; i < uuid.length; i++) | 
|  331   { |  341   { | 
|  332     let component = uuid[i].toString(16); |  342     let component = uuid[i].toString(16); | 
|  333     while (component.length < 4) |  343     while (component.length < 4) | 
|  334       component = "0" + component; |  344       component = "0" + component; | 
|  335     uuidString += component; |  345     uuidString += component; | 
|  336     if (i >= 1 && i<= 4) |  346     if (i >= 1 && i <= 4) | 
|  337       uuidString += "-"; |  347       uuidString += "-"; | 
|  338   } |  348   } | 
|  339  |  349  | 
|  340   let params = new URLSearchParams({ |  350   let params = new URLSearchParams({ | 
|  341     version: 1, |  351     version: 1, | 
|  342     guid: uuidString, |  352     guid: uuidString, | 
|  343     lang: reportData.getElementsByTagName("adblock-plus")[0].getAttribute("local
     e") |  353     lang: reportData.getElementsByTagName("adblock-plus")[0] | 
 |  354                     .getAttribute("locale") | 
|  344   }); |  355   }); | 
|  345   let url = "https://reports.adblockplus.org/submitReport?" + params; |  356   let url = "https://reports.adblockplus.org/submitReport?" + params; | 
|  346  |  357  | 
|  347   let reportSent = event => |  358   let reportSent = event => | 
|  348   { |  359   { | 
|  349     let success = false; |  360     let success = false; | 
|  350     let errorMessage = browser.i18n.getMessage("filters_subscription_lastDownloa
     d_connectionError"); |  361     let errorMessage = browser.i18n.getMessage( | 
 |  362       "filters_subscription_lastDownload_connectionError" | 
 |  363     ); | 
|  351     try |  364     try | 
|  352     { |  365     { | 
|  353       success = request.status == 200; |  366       success = request.status == 200; | 
|  354       if (request.status != 0) |  367       if (request.status != 0) | 
|  355         errorMessage = request.status + " " + request.statusText; |  368         errorMessage = request.status + " " + request.statusText; | 
|  356     } |  369     } | 
|  357     catch (e) |  370     catch (e) | 
|  358     { |  371     { | 
|  359       // Getting request status might throw if no connection was established |  372       // Getting request status might throw if no connection was established | 
|  360     } |  373     } | 
| (...skipping 19 matching lines...) Expand all  Loading... | 
|  380  |  393  | 
|  381       while (errorElement.firstChild) |  394       while (errorElement.firstChild) | 
|  382         errorElement.removeChild(errorElement.firstChild); |  395         errorElement.removeChild(errorElement.firstChild); | 
|  383  |  396  | 
|  384       let link = document.createElement("a"); |  397       let link = document.createElement("a"); | 
|  385       link.textContent = linkText; |  398       link.textContent = linkText; | 
|  386       browser.runtime.sendMessage({ |  399       browser.runtime.sendMessage({ | 
|  387         type: "app.get", |  400         type: "app.get", | 
|  388         what: "doclink", |  401         what: "doclink", | 
|  389         link: "reporter_connect_issue" |  402         link: "reporter_connect_issue" | 
|  390       }).then(url => |  403       }).then(supportUrl => | 
|  391       { |  404       { | 
|  392         link.href = url; |  405         link.href = supportUrl; | 
|  393       }); |  406       }); | 
|  394  |  407  | 
|  395  |  408  | 
|  396       errorElement.appendChild(document.createTextNode(beforeLink)); |  409       errorElement.appendChild(document.createTextNode(beforeLink)); | 
|  397       errorElement.appendChild(link); |  410       errorElement.appendChild(link); | 
|  398       errorElement.appendChild(document.createTextNode(afterLink)); |  411       errorElement.appendChild(document.createTextNode(afterLink)); | 
|  399  |  412  | 
|  400       errorElement.hidden = false; |  413       errorElement.hidden = false; | 
|  401     } |  414     } | 
|  402  |  415  | 
|  403     result = result.replace(/%CONFIRMATION%/g, encodeHTML(browser.i18n.getMessag
     e("issueReporter_confirmationMessage"))); |  416     result = result.replace(/%CONFIRMATION%/g, encodeHTML(browser.i18n.getMessag
     e("issueReporter_confirmationMessage"))); | 
|  404     result = result.replace(/%KNOWNISSUE%/g, encodeHTML(browser.i18n.getMessage(
     "issueReporter_knownIssueMessage"))); |  417     result = result.replace(/%KNOWNISSUE%/g, encodeHTML(browser.i18n.getMessage(
     "issueReporter_knownIssueMessage"))); | 
|  405     result = result.replace(/(<html)\b/, '$1 dir="' + encodeHTML(window.getCompu
     tedStyle(document.documentElement, "").direction + '"')); |  418     result = result.replace(/(<html)\b/, '$1 dir="' + encodeHTML(window.getCompu
     tedStyle(document.documentElement, "").direction + '"')); | 
|  406  |  419  | 
|  407     document.getElementById("sendReportMessage").hidden = true; |  420     document.getElementById("sendReportMessage").hidden = true; | 
|  408     document.getElementById("sendingProgressContainer").hidden = true; |  421     document.getElementById("sendingProgressContainer").hidden = true; | 
|  409  |  422  | 
|  410     let resultFrame = document.getElementById("result"); |  423     let resultFrame = document.getElementById("result"); | 
|  411     resultFrame.setAttribute("src", "data:text/html;charset=utf-8," + encodeURIC
     omponent(result)); |  424     resultFrame.setAttribute("src", "data:text/html;charset=utf-8," + | 
 |  425                                     encodeURIComponent(result)); | 
|  412     resultFrame.hidden = false; |  426     resultFrame.hidden = false; | 
|  413  |  427  | 
|  414     document.getElementById("continue").disabled = false; |  428     document.getElementById("continue").disabled = false; | 
|  415   }; |  429   }; | 
|  416  |  430  | 
|  417   let request = new XMLHttpRequest(); |  431   let request = new XMLHttpRequest(); | 
|  418   request.open("POST", url); |  432   request.open("POST", url); | 
|  419   request.setRequestHeader("Content-Type", "text/xml"); |  433   request.setRequestHeader("Content-Type", "text/xml"); | 
|  420   request.setRequestHeader("X-Adblock-Plus", "1"); |  434   request.setRequestHeader("X-Adblock-Plus", "1"); | 
|  421   request.addEventListener("load", reportSent); |  435   request.addEventListener("load", reportSent); | 
|  422   request.addEventListener("error", reportSent); |  436   request.addEventListener("error", reportSent); | 
|  423   request.upload.addEventListener("progress", event => |  437   request.upload.addEventListener("progress", event => | 
|  424   { |  438   { | 
|  425     if (!event.lengthComputable) |  439     if (!event.lengthComputable) | 
|  426       return; |  440       return; | 
|  427  |  441  | 
|  428     let progress = Math.round(event.loaded / event.total * 100); |  | 
|  429     if (event.loaded > 0) |  442     if (event.loaded > 0) | 
|  430     { |  443     { | 
|  431       let progress = document.getElementById("sendingProgress"); |  444       let progress = document.getElementById("sendingProgress"); | 
|  432       progress.max = event.total; |  445       progress.max = event.total; | 
|  433       progress.value = event.loaded; |  446       progress.value = event.loaded; | 
|  434     } |  447     } | 
|  435   }); |  448   }); | 
|  436   request.send(serializeReportData()); |  449   request.send(serializeReportData()); | 
|  437 } |  450 } | 
|  438  |  451  | 
|  439 function leaveSendPage() |  452 function leaveSendPage() | 
|  440 { |  453 { | 
|  441   window.close(); |  454   window.close(); | 
|  442 } |  455 } | 
| OLD | NEW |