| Index: issue-reporter.js |
| =================================================================== |
| --- a/issue-reporter.js |
| +++ b/issue-reporter.js |
| @@ -21,16 +21,19 @@ |
| "text/xml"); |
| let pages = { |
| typeSelectorPage: [initTypeSelector, leaveTypeSelector], |
| commentPage: [initCommentPage, leaveCommentPage], |
| sendPage: [initSendPage, leaveSendPage] |
| }; |
| +let dataGatheringTabId = null; |
| +let isMinimumTimeMet = false; |
| + |
| document.addEventListener("DOMContentLoaded", () => |
| { |
| document.getElementById("cancel").addEventListener("click", () => |
| { |
| closeMe(); |
| }); |
| document.getElementById("continue").addEventListener("click", () => |
| @@ -44,30 +47,36 @@ |
| let blacklisted = new Set(["textarea", "button", "a"]); |
| if (event.key == "Enter" && !blacklisted.has(event.target.localName)) |
| document.getElementById("continue").click(); |
| else if (event.key == "Escape") |
| document.getElementById("cancel").click(); |
| }); |
| + document.getElementById("hide-notification").addEventListener("click", () => |
| + { |
| + document.getElementById("notification").setAttribute("aria-hidden", true); |
| + }); |
| + |
| browser.runtime.sendMessage({ |
| type: "app.get", |
| what: "doclink", |
| link: "reporter_privacy" |
| }).then(url => |
| { |
| document.getElementById("privacyPolicy").href = url; |
| }); |
| initDataCollector(); |
| }); |
| function closeMe() |
| { |
| + closeRequestsCollectingTab(); |
| browser.runtime.sendMessage({ |
| type: "app.get", |
| what: "senderId" |
| }).then(tabId => browser.tabs.remove(tabId)); |
| } |
| function getCurrentPage() |
| { |
| @@ -79,16 +88,17 @@ |
| if (!pages.hasOwnProperty(pageId)) |
| return; |
| let previousPage = document.querySelector(".page:not([hidden])"); |
| if (previousPage) |
| previousPage.hidden = true; |
| document.getElementById(pageId).hidden = false; |
| + document.body.dataset.page = pageId; |
| pages[pageId][0](); |
| } |
| function censorURL(url) |
| { |
| return url.replace(/([?;&/#][^?;&/#]+?=)[^?;&/#]+/g, "$1*"); |
| } |
| @@ -230,26 +240,60 @@ |
| subscriptionElement.setAttribute("disabledFilters", |
| subscription.disabledFilters.length); |
| element.appendChild(subscriptionElement); |
| } |
| reportData.documentElement.appendChild(element); |
| }); |
| } |
| +function collectRequests(tabId) |
| +{ |
| + return browser.tabs.get(tabId).then(tab => |
| + { |
| + return browser.tabs.create({active: false, url: tab.url}); |
| + }).then((dataCollectingTab) => |
| + { |
| + dataGatheringTabId = dataCollectingTab.id; |
| + browser.runtime.sendMessage({ |
| + type: "app.collectHits", |
| + tab: dataCollectingTab |
| + }); |
| + |
| + function minimumTimeMet() |
| + { |
| + isMinimumTimeMet = true; |
| + document.getElementById("showData").disabled = false; |
| + validateCommentsPage(); |
| + } |
| + browser.tabs.onUpdated.addListener((shadowTabId, changeInfo) => |
| + { |
| + if (shadowTabId == dataGatheringTabId && changeInfo.status == "complete") |
| + minimumTimeMet(); |
| + }); |
| + window.setTimeout(minimumTimeMet, 5000); |
| + }); |
| +} |
| + |
| +function closeRequestsCollectingTab() |
| +{ |
| + browser.tabs.remove(dataGatheringTabId); |
| +} |
| + |
| function initDataCollector() |
| { |
| Promise.resolve().then(() => |
| { |
| let tabId = parseInt(location.search.replace(/^\?/, ""), 10) || 0; |
| let handlers = [ |
| retrieveAddonInfo(), |
| retrieveApplicationInfo(), |
| retrievePlatformInfo(), |
| retrieveTabURL(tabId), |
| + collectRequests(tabId), |
| retrieveSubscriptions() |
| ]; |
| return Promise.all(handlers); |
| }).then(() => |
| { |
| setCurrentPage("typeSelectorPage"); |
| }).catch(e => |
| { |
| @@ -276,50 +320,50 @@ |
| function leaveTypeSelector() |
| { |
| let checkbox = document.querySelector("input[name='type']:checked"); |
| reportData.documentElement.setAttribute("type", checkbox.value); |
| setCurrentPage("commentPage"); |
| } |
| -function initCommentPage() |
| +function validateCommentsPage() |
| { |
| - let continueButton = document.getElementById("continue"); |
| - let label = browser.i18n.getMessage("issueReporter_sendButton_label"); |
| - continueButton.textContent = label; |
| - continueButton.disabled = true; |
| - |
| + let sendButton = document.getElementById("send"); |
| let emailElement = reportData.createElement("email"); |
| let emailField = document.getElementById("email"); |
| let anonymousSubmissionField = document.getElementById("anonymousSubmission"); |
| - let validateEmail = () => |
| + document.getElementById("anonymousSubmissionWarning") |
| + .setAttribute("data-invisible", !anonymousSubmissionField.checked); |
| + if (anonymousSubmissionField.checked) |
| + { |
| + emailField.value = ""; |
| + emailField.disabled = true; |
| + sendButton.disabled = !isMinimumTimeMet; |
| + if (emailElement.parentNode) |
| + emailElement.parentNode.removeChild(emailElement); |
| + } |
| + else |
| { |
| - document.getElementById("anonymousSubmissionWarning") |
| - .setAttribute("data-invisible", !anonymousSubmissionField.checked); |
| - if (anonymousSubmissionField.checked) |
| - { |
| - emailField.value = ""; |
| - emailField.disabled = true; |
| - continueButton.disabled = false; |
| - if (emailElement.parentNode) |
| - emailElement.parentNode.removeChild(emailElement); |
| - } |
| - else |
| - { |
| - emailField.disabled = false; |
| + emailField.disabled = false; |
| - let value = emailField.value.trim(); |
| - emailElement.textContent = value; |
| - reportData.documentElement.appendChild(emailElement); |
| - continueButton.disabled = value == "" || !emailField.validity.valid; |
| - } |
| - }; |
| - emailField.addEventListener("input", validateEmail); |
| - anonymousSubmissionField.addEventListener("click", validateEmail); |
| + let value = emailField.value.trim(); |
| + emailElement.textContent = value; |
| + reportData.documentElement.appendChild(emailElement); |
| + sendButton.disabled = (value == "" || !emailField.validity.valid || |
| + !isMinimumTimeMet); |
| + } |
| +} |
| + |
| +function initCommentPage() |
| +{ |
| + let anonymousSubmissionField = document.getElementById("anonymousSubmission"); |
| + let emailField = document.getElementById("email"); |
| + emailField.addEventListener("input", validateCommentsPage); |
| + anonymousSubmissionField.addEventListener("click", validateCommentsPage); |
| let commentElement = reportData.createElement("comment"); |
| document.getElementById("comment").addEventListener("input", event => |
| { |
| if (commentElement.parentNode) |
| commentElement.parentNode.removeChild(commentElement); |
| let value = event.target.value.trim(); |
| @@ -329,16 +373,17 @@ |
| document.getElementById("commentLengthWarning") |
| .setAttribute("data-invisible", value.length <= 1000); |
| }); |
| let showDataOverlay = document.getElementById("showDataOverlay"); |
| document.getElementById("showData").addEventListener("click", event => |
| { |
| event.preventDefault(); |
| + closeRequestsCollectingTab(); |
| showDataOverlay.hidden = false; |
| let element = document.getElementById("showDataValue"); |
| element.value = serializeReportData(); |
| element.focus(); |
| }); |
| @@ -509,8 +554,65 @@ |
| }); |
| request.send(serializeReportData()); |
| } |
| function leaveSendPage() |
| { |
| closeMe(); |
| } |
| + |
| +let port = browser.runtime.connect({name: "ui"}); |
| + |
| +port.onMessage.addListener((message) => |
| +{ |
| + switch (message.type) |
| + { |
| + case "app.respond": |
| + switch (message.action) |
| + { |
| + case "devLog": |
| + const [request, filter, subscriptions] = message.args; |
| + |
| + let existingRequest = reportData.querySelector(`[location="${request.url}"]`); |
| + // TODO: refactor the implementation |
| + if (existingRequest) |
| + { |
| + let countNum = Number(existingRequest.getAttribute("count")); |
| + existingRequest.setAttribute("count", countNum + 1); |
| + } |
| + else |
| + { |
| + let requestElem = reportData.createElement("request"); |
| + requestElem.setAttribute("location", request.url); |
| + requestElem.setAttribute("type", request.type); |
| + requestElem.setAttribute("docDomain", request.docDomain); |
| + requestElem.setAttribute("thirdParty", request.thirdParty); |
| + requestElem.setAttribute("count", 1); |
| + reportData.documentElement.appendChild(requestElem); |
| + } |
| + if (filter) |
| + { |
| + let existingFilter = reportData.querySelector(`[text="${filter.text}"]`); |
| + if (existingFilter) |
| + { |
| + let countNum = Number(existingFilter.getAttribute("hitcount")); |
| + existingFilter.setAttribute("hitcount", countNum + 1); |
| + } |
| + else |
| + { |
| + let filterElem = reportData.createElement("filter"); |
| + filterElem.setAttribute("text", filter.text); |
| + filterElem.setAttribute("subscriptions", subscriptions.join(",")); |
| + filterElem.setAttribute("hitcount", 1); |
| + reportData.documentElement.appendChild(filterElem); |
| + } |
| + } |
| + break; |
| + } |
| + break; |
| + } |
| +}); |
| + |
| +port.postMessage({ |
| + type: "app.listen", |
| + filter: ["devLog"] |
| +}); |