browser/experiments/test/xpcshell/head.js

changeset 0
6474c204b198
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/browser/experiments/test/xpcshell/head.js	Wed Dec 31 06:09:35 2014 +0100
     1.3 @@ -0,0 +1,248 @@
     1.4 +/* Any copyright is dedicated to the Public Domain.
     1.5 + * http://creativecommons.org/publicdomain/zero/1.0/ */
     1.6 +
     1.7 +const {classes: Cc, interfaces: Ci, utils: Cu, results: Cr} = Components;
     1.8 +
     1.9 +Cu.import("resource://gre/modules/Services.jsm");
    1.10 +Cu.import("resource://gre/modules/XPCOMUtils.jsm");
    1.11 +Cu.import("resource://gre/modules/Promise.jsm");
    1.12 +Cu.import("resource://gre/modules/Task.jsm");
    1.13 +Cu.import("resource://gre/modules/osfile.jsm");
    1.14 +Cu.import("resource://services-sync/healthreport.jsm", this);
    1.15 +Cu.import("resource://testing-common/services/healthreport/utils.jsm", this);
    1.16 +Cu.import("resource://gre/modules/services/healthreport/providers.jsm");
    1.17 +Cu.import("resource://testing-common/AddonManagerTesting.jsm");
    1.18 +
    1.19 +const PREF_EXPERIMENTS_ENABLED  = "experiments.enabled";
    1.20 +const PREF_LOGGING_LEVEL        = "experiments.logging.level";
    1.21 +const PREF_LOGGING_DUMP         = "experiments.logging.dump";
    1.22 +const PREF_MANIFEST_URI         = "experiments.manifest.uri";
    1.23 +const PREF_FETCHINTERVAL        = "experiments.manifest.fetchIntervalSeconds";
    1.24 +const PREF_TELEMETRY_ENABLED    = "toolkit.telemetry.enabled";
    1.25 +const PREF_HEALTHREPORT_ENABLED = "datareporting.healthreport.service.enabled";
    1.26 +
    1.27 +function getExperimentPath(base) {
    1.28 +  let p = do_get_cwd();
    1.29 +  p.append(base);
    1.30 +  return p.path;
    1.31 +}
    1.32 +
    1.33 +function sha1File(path) {
    1.34 +  let f = Cc["@mozilla.org/file/local;1"]
    1.35 +            .createInstance(Ci.nsILocalFile);
    1.36 +  f.initWithPath(path);
    1.37 +  let hasher = Cc["@mozilla.org/security/hash;1"]
    1.38 +                 .createInstance(Ci.nsICryptoHash);
    1.39 +  hasher.init(hasher.SHA1);
    1.40 +
    1.41 +  let is = Cc["@mozilla.org/network/file-input-stream;1"]
    1.42 +             .createInstance(Ci.nsIFileInputStream);
    1.43 +  is.init(f, -1, 0, 0);
    1.44 +  hasher.updateFromStream(is, Math.pow(2, 32) - 1);
    1.45 +  is.close();
    1.46 +  let bytes = hasher.finish(false);
    1.47 +
    1.48 +  return [("0" + bytes.charCodeAt(byte).toString(16)).slice(-2)
    1.49 +          for (byte in bytes)]
    1.50 +         .join("");
    1.51 +}
    1.52 +
    1.53 +const EXPERIMENT1_ID       = "test-experiment-1@tests.mozilla.org";
    1.54 +const EXPERIMENT1_XPI_NAME = "experiment-1.xpi";
    1.55 +const EXPERIMENT1_NAME     = "Test experiment 1";
    1.56 +const EXPERIMENT1_PATH     = getExperimentPath(EXPERIMENT1_XPI_NAME);
    1.57 +const EXPERIMENT1_XPI_SHA1 = "sha1:" + sha1File(EXPERIMENT1_PATH);
    1.58 +
    1.59 +
    1.60 +const EXPERIMENT1A_XPI_NAME = "experiment-1a.xpi";
    1.61 +const EXPERIMENT1A_NAME     = "Test experiment 1.1";
    1.62 +const EXPERIMENT1A_PATH     = getExperimentPath(EXPERIMENT1A_XPI_NAME);
    1.63 +const EXPERIMENT1A_XPI_SHA1 = "sha1:" + sha1File(EXPERIMENT1A_PATH);
    1.64 +
    1.65 +const EXPERIMENT2_ID       = "test-experiment-2@tests.mozilla.org"
    1.66 +const EXPERIMENT2_XPI_NAME = "experiment-2.xpi";
    1.67 +const EXPERIMENT2_PATH     = getExperimentPath(EXPERIMENT2_XPI_NAME);
    1.68 +const EXPERIMENT2_XPI_SHA1 = "sha1:" + sha1File(EXPERIMENT2_PATH);
    1.69 +
    1.70 +const EXPERIMENT3_ID       = "test-experiment-3@tests.mozilla.org";
    1.71 +const EXPERIMENT4_ID       = "test-experiment-4@tests.mozilla.org";
    1.72 +
    1.73 +const DEFAULT_BUILDID      = "2014060601";
    1.74 +
    1.75 +const FAKE_EXPERIMENTS_1 = [
    1.76 +  {
    1.77 +    id: "id1",
    1.78 +    name: "experiment1",
    1.79 +    description: "experiment 1",
    1.80 +    active: true,
    1.81 +    detailUrl: "https://dummy/experiment1",
    1.82 +    branch: "foo",
    1.83 +  },
    1.84 +];
    1.85 +
    1.86 +const FAKE_EXPERIMENTS_2 = [
    1.87 +  {
    1.88 +    id: "id2",
    1.89 +    name: "experiment2",
    1.90 +    description: "experiment 2",
    1.91 +    active: false,
    1.92 +    endDate: new Date(2014, 2, 11, 2, 4, 35, 42).getTime(),
    1.93 +    detailUrl: "https://dummy/experiment2",
    1.94 +    branch: null,
    1.95 +  },
    1.96 +  {
    1.97 +    id: "id1",
    1.98 +    name: "experiment1",
    1.99 +    description: "experiment 1",
   1.100 +    active: false,
   1.101 +    endDate: new Date(2014, 2, 10, 0, 0, 0, 0).getTime(),
   1.102 +    detailURL: "https://dummy/experiment1",
   1.103 +    branch: null,
   1.104 +  },
   1.105 +];
   1.106 +
   1.107 +let gAppInfo = null;
   1.108 +
   1.109 +function getReporter(name, uri, inspected) {
   1.110 +  return Task.spawn(function init() {
   1.111 +    let reporter = getHealthReporter(name, uri, inspected);
   1.112 +    yield reporter.init();
   1.113 +
   1.114 +    yield reporter._providerManager.registerProviderFromType(
   1.115 +      HealthReportProvider);
   1.116 +
   1.117 +    throw new Task.Result(reporter);
   1.118 +  });
   1.119 +}
   1.120 +
   1.121 +function removeCacheFile() {
   1.122 +  let path = OS.Path.join(OS.Constants.Path.profileDir, "experiments.json");
   1.123 +  return OS.File.remove(path);
   1.124 +}
   1.125 +
   1.126 +function disableCertificateChecks() {
   1.127 +  let pref = "experiments.manifest.cert.checkAttributes";
   1.128 +  Services.prefs.setBoolPref(pref, false);
   1.129 +  do_register_cleanup(() => Services.prefs.clearUserPref(pref));
   1.130 +}
   1.131 +
   1.132 +function patchPolicy(policy, data) {
   1.133 +  for (let key of Object.keys(data)) {
   1.134 +    Object.defineProperty(policy, key, {
   1.135 +      value: data[key],
   1.136 +      writable: true,
   1.137 +    });
   1.138 +  }
   1.139 +}
   1.140 +
   1.141 +function defineNow(policy, time) {
   1.142 +  patchPolicy(policy, { now: () => new Date(time) });
   1.143 +}
   1.144 +
   1.145 +function futureDate(date, offset) {
   1.146 +  return new Date(date.getTime() + offset);
   1.147 +}
   1.148 +
   1.149 +function dateToSeconds(date) {
   1.150 +  return date.getTime() / 1000;
   1.151 +}
   1.152 +
   1.153 +let gGlobalScope = this;
   1.154 +function loadAddonManager() {
   1.155 +  let ns = {};
   1.156 +  Cu.import("resource://gre/modules/Services.jsm", ns);
   1.157 +  let head = "../../../../toolkit/mozapps/extensions/test/xpcshell/head_addons.js";
   1.158 +  let file = do_get_file(head);
   1.159 +  let uri = ns.Services.io.newFileURI(file);
   1.160 +  ns.Services.scriptloader.loadSubScript(uri.spec, gGlobalScope);
   1.161 +  createAppInfo("xpcshell@tests.mozilla.org", "XPCShell", "1", "1.9.2");
   1.162 +  startupManager();
   1.163 +}
   1.164 +
   1.165 +function getExperimentAddons(previous=false) {
   1.166 +  let deferred = Promise.defer();
   1.167 +
   1.168 +  AddonManager.getAddonsByTypes(["experiment"], (addons) => {
   1.169 +    if (previous) {
   1.170 +      deferred.resolve(addons);
   1.171 +    } else {
   1.172 +      deferred.resolve([a for (a of addons) if (!a.appDisabled)]);
   1.173 +    }
   1.174 +  });
   1.175 +
   1.176 +  return deferred.promise;
   1.177 +}
   1.178 +
   1.179 +function createAppInfo(optionsIn) {
   1.180 +  const XULAPPINFO_CONTRACTID = "@mozilla.org/xre/app-info;1";
   1.181 +  const XULAPPINFO_CID = Components.ID("{c763b610-9d49-455a-bbd2-ede71682a1ac}");
   1.182 +
   1.183 +  let options = optionsIn || {};
   1.184 +  let id = options.id || "xpcshell@tests.mozilla.org";
   1.185 +  let name = options.name || "XPCShell";
   1.186 +  let version = options.version || "1.0";
   1.187 +  let platformVersion = options.platformVersion || "1.0";
   1.188 +  let date = options.date || new Date();
   1.189 +
   1.190 +  let buildID = options.buildID || DEFAULT_BUILDID;
   1.191 +
   1.192 +  gAppInfo = {
   1.193 +    // nsIXULAppInfo
   1.194 +    vendor: "Mozilla",
   1.195 +    name: name,
   1.196 +    ID: id,
   1.197 +    version: version,
   1.198 +    appBuildID: buildID,
   1.199 +    platformVersion: platformVersion ? platformVersion : "1.0",
   1.200 +    platformBuildID: buildID,
   1.201 +
   1.202 +    // nsIXULRuntime
   1.203 +    inSafeMode: false,
   1.204 +    logConsoleErrors: true,
   1.205 +    OS: "XPCShell",
   1.206 +    XPCOMABI: "noarch-spidermonkey",
   1.207 +    invalidateCachesOnRestart: function invalidateCachesOnRestart() {
   1.208 +      // Do nothing
   1.209 +    },
   1.210 +
   1.211 +    // nsICrashReporter
   1.212 +    annotations: {},
   1.213 +
   1.214 +    annotateCrashReport: function(key, data) {
   1.215 +      this.annotations[key] = data;
   1.216 +    },
   1.217 +
   1.218 +    QueryInterface: XPCOMUtils.generateQI([Ci.nsIXULAppInfo,
   1.219 +                                           Ci.nsIXULRuntime,
   1.220 +                                           Ci.nsICrashReporter,
   1.221 +                                           Ci.nsISupports])
   1.222 +  };
   1.223 +
   1.224 +  let XULAppInfoFactory = {
   1.225 +    createInstance: function (outer, iid) {
   1.226 +      if (outer != null) {
   1.227 +        throw Cr.NS_ERROR_NO_AGGREGATION;
   1.228 +      }
   1.229 +      return gAppInfo.QueryInterface(iid);
   1.230 +    }
   1.231 +  };
   1.232 +
   1.233 +  let registrar = Components.manager.QueryInterface(Ci.nsIComponentRegistrar);
   1.234 +  registrar.registerFactory(XULAPPINFO_CID, "XULAppInfo",
   1.235 +                            XULAPPINFO_CONTRACTID, XULAppInfoFactory);
   1.236 +}
   1.237 +
   1.238 +/**
   1.239 + * Replace the experiments on an Experiments with a new list.
   1.240 + *
   1.241 + * This monkeypatches getExperiments(). It doesn't monkeypatch the internal
   1.242 + * experiments list. So its utility is not as great as it could be.
   1.243 + */
   1.244 +function replaceExperiments(experiment, list) {
   1.245 +  Object.defineProperty(experiment, "getExperiments", {
   1.246 +    writable: true,
   1.247 +    value: () => {
   1.248 +      return Promise.resolve(list);
   1.249 +    },
   1.250 +  });
   1.251 +}

mercurial