michael@0: /* This Source Code Form is subject to the terms of the Mozilla Public michael@0: * License, v. 2.0. If a copy of the MPL was not distributed with this michael@0: * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ michael@0: michael@0: Cu.import("resource://gre/modules/Services.jsm"); michael@0: michael@0: const CRASH_URL = "http://example.com/browser/browser/base/content/test/plugins/plugin_crashCommentAndURL.html"; michael@0: michael@0: const SERVER_URL = "http://example.com/browser/toolkit/crashreporter/test/browser/crashreport.sjs"; michael@0: michael@0: function test() { michael@0: // Crashing the plugin takes up a lot of time, so extend the test timeout. michael@0: requestLongerTimeout(runs.length); michael@0: waitForExplicitFinish(); michael@0: setTestPluginEnabledState(Ci.nsIPluginTag.STATE_ENABLED); michael@0: michael@0: // The test harness sets MOZ_CRASHREPORTER_NO_REPORT, which disables plugin michael@0: // crash reports. This test needs them enabled. The test also needs a mock michael@0: // report server, and fortunately one is already set up by toolkit/ michael@0: // crashreporter/test/Makefile.in. Assign its URL to MOZ_CRASHREPORTER_URL, michael@0: // which CrashSubmit.jsm uses as a server override. michael@0: let env = Cc["@mozilla.org/process/environment;1"]. michael@0: getService(Components.interfaces.nsIEnvironment); michael@0: let noReport = env.get("MOZ_CRASHREPORTER_NO_REPORT"); michael@0: let serverURL = env.get("MOZ_CRASHREPORTER_URL"); michael@0: env.set("MOZ_CRASHREPORTER_NO_REPORT", ""); michael@0: env.set("MOZ_CRASHREPORTER_URL", SERVER_URL); michael@0: michael@0: let tab = gBrowser.loadOneTab("about:blank", { inBackground: false }); michael@0: let browser = gBrowser.getBrowserForTab(tab); michael@0: browser.addEventListener("PluginCrashed", onCrash, false); michael@0: Services.obs.addObserver(onSubmitStatus, "crash-report-status", false); michael@0: michael@0: registerCleanupFunction(function cleanUp() { michael@0: env.set("MOZ_CRASHREPORTER_NO_REPORT", noReport); michael@0: env.set("MOZ_CRASHREPORTER_URL", serverURL); michael@0: gBrowser.selectedBrowser.removeEventListener("PluginCrashed", onCrash, michael@0: false); michael@0: Services.obs.removeObserver(onSubmitStatus, "crash-report-status"); michael@0: gBrowser.removeCurrentTab(); michael@0: }); michael@0: michael@0: doNextRun(); michael@0: } michael@0: michael@0: let runs = [ michael@0: { michael@0: shouldSubmissionUIBeVisible: true, michael@0: comment: "", michael@0: urlOptIn: false, michael@0: }, michael@0: { michael@0: shouldSubmissionUIBeVisible: true, michael@0: comment: "a test comment", michael@0: urlOptIn: true, michael@0: }, michael@0: { michael@0: width: 300, michael@0: height: 300, michael@0: shouldSubmissionUIBeVisible: false, michael@0: }, michael@0: ]; michael@0: michael@0: let currentRun = null; michael@0: michael@0: function doNextRun() { michael@0: try { michael@0: if (!runs.length) { michael@0: finish(); michael@0: return; michael@0: } michael@0: currentRun = runs.shift(); michael@0: let args = ["width", "height"].reduce(function (memo, arg) { michael@0: if (arg in currentRun) michael@0: memo[arg] = currentRun[arg]; michael@0: return memo; michael@0: }, {}); michael@0: gBrowser.loadURI(CRASH_URL + "?" + michael@0: encodeURIComponent(JSON.stringify(args))); michael@0: // And now wait for the crash. michael@0: } michael@0: catch (err) { michael@0: failWithException(err); michael@0: finish(); michael@0: } michael@0: } michael@0: michael@0: function onCrash() { michael@0: try { michael@0: let plugin = gBrowser.contentDocument.getElementById("plugin"); michael@0: let elt = gPluginHandler.getPluginUI.bind(gPluginHandler, plugin); michael@0: let style = michael@0: gBrowser.contentWindow.getComputedStyle(elt("pleaseSubmit")); michael@0: is(style.display, michael@0: currentRun.shouldSubmissionUIBeVisible ? "block" : "none", michael@0: "Submission UI visibility should be correct"); michael@0: if (!currentRun.shouldSubmissionUIBeVisible) { michael@0: // Done with this run. michael@0: doNextRun(); michael@0: return; michael@0: } michael@0: elt("submitComment").value = currentRun.comment; michael@0: elt("submitURLOptIn").checked = currentRun.urlOptIn; michael@0: elt("submitButton").click(); michael@0: // And now wait for the submission status notification. michael@0: } michael@0: catch (err) { michael@0: failWithException(err); michael@0: doNextRun(); michael@0: } michael@0: } michael@0: michael@0: function onSubmitStatus(subj, topic, data) { michael@0: try { michael@0: // Wait for success or failed, doesn't matter which. michael@0: if (data != "success" && data != "failed") michael@0: return; michael@0: michael@0: let extra = getPropertyBagValue(subj.QueryInterface(Ci.nsIPropertyBag), michael@0: "extra"); michael@0: ok(extra instanceof Ci.nsIPropertyBag, "Extra data should be property bag"); michael@0: michael@0: let val = getPropertyBagValue(extra, "PluginUserComment"); michael@0: if (currentRun.comment) michael@0: is(val, currentRun.comment, michael@0: "Comment in extra data should match comment in textbox"); michael@0: else michael@0: ok(val === undefined, michael@0: "Comment should be absent from extra data when textbox is empty"); michael@0: michael@0: val = getPropertyBagValue(extra, "PluginContentURL"); michael@0: if (currentRun.urlOptIn) michael@0: is(val, gBrowser.currentURI.spec, michael@0: "URL in extra data should match browser URL when opt-in checked"); michael@0: else michael@0: ok(val === undefined, michael@0: "URL should be absent from extra data when opt-in not checked"); michael@0: } michael@0: catch (err) { michael@0: failWithException(err); michael@0: } michael@0: doNextRun(); michael@0: } michael@0: michael@0: function getPropertyBagValue(bag, key) { michael@0: try { michael@0: var val = bag.getProperty(key); michael@0: } michael@0: catch (e if e.result == Cr.NS_ERROR_FAILURE) {} michael@0: return val; michael@0: } michael@0: michael@0: function failWithException(err) { michael@0: ok(false, "Uncaught exception: " + err + "\n" + err.stack); michael@0: }