summaryrefslogtreecommitdiffstats
path: root/toolkit/components/normandy/test/unit/utils.js
diff options
context:
space:
mode:
Diffstat (limited to 'toolkit/components/normandy/test/unit/utils.js')
-rw-r--r--toolkit/components/normandy/test/unit/utils.js137
1 files changed, 137 insertions, 0 deletions
diff --git a/toolkit/components/normandy/test/unit/utils.js b/toolkit/components/normandy/test/unit/utils.js
new file mode 100644
index 0000000000..b1273d1d5e
--- /dev/null
+++ b/toolkit/components/normandy/test/unit/utils.js
@@ -0,0 +1,137 @@
+"use strict";
+/* eslint-disable no-unused-vars */
+
+// Loaded into the same scope as head_xpc.js
+/* import-globals-from head_xpc.js */
+
+const { Preferences } = ChromeUtils.importESModule(
+ "resource://gre/modules/Preferences.sys.mjs"
+);
+const { HttpServer } = ChromeUtils.importESModule(
+ "resource://testing-common/httpd.sys.mjs"
+);
+
+const { NormandyApi } = ChromeUtils.importESModule(
+ "resource://normandy/lib/NormandyApi.sys.mjs"
+);
+const { NormandyTestUtils } = ChromeUtils.importESModule(
+ "resource://testing-common/NormandyTestUtils.sys.mjs"
+);
+
+const CryptoHash = Components.Constructor(
+ "@mozilla.org/security/hash;1",
+ "nsICryptoHash",
+ "initWithString"
+);
+const FileInputStream = Components.Constructor(
+ "@mozilla.org/network/file-input-stream;1",
+ "nsIFileInputStream",
+ "init"
+);
+
+class MockResponse {
+ constructor(content) {
+ this.content = content;
+ }
+
+ async text() {
+ return this.content;
+ }
+
+ async json() {
+ return JSON.parse(this.content);
+ }
+}
+
+function withServer(server) {
+ return function (testFunction) {
+ return NormandyTestUtils.decorate(
+ NormandyTestUtils.withMockPreferences(),
+ async function inner({ mockPreferences, ...args }) {
+ const serverUrl = `http://localhost:${server.identity.primaryPort}`;
+ mockPreferences.set("app.normandy.api_url", `${serverUrl}/api/v1`);
+ NormandyApi.clearIndexCache();
+
+ try {
+ await testFunction({ ...args, serverUrl, mockPreferences, server });
+ } finally {
+ await new Promise(resolve => server.stop(resolve));
+ }
+ }
+ );
+ };
+}
+
+function makeScriptServer(scriptPath) {
+ const server = new HttpServer();
+ server.registerContentType("sjs", "sjs");
+ server.registerFile("/", do_get_file(scriptPath));
+ server.start(-1);
+ return server;
+}
+
+function withScriptServer(scriptPath) {
+ return withServer(makeScriptServer(scriptPath));
+}
+
+function makeMockApiServer(directory) {
+ const server = new HttpServer();
+ server.registerDirectory("/", directory);
+
+ server.setIndexHandler(async function (request, response) {
+ response.processAsync();
+ const dir = request.getProperty("directory");
+ const index = dir.clone();
+ index.append("index.json");
+
+ if (!index.exists()) {
+ response.setStatusLine("1.1", 404, "Not Found");
+ response.write(`Cannot find path ${index.path}`);
+ response.finish();
+ return;
+ }
+
+ try {
+ const contents = await IOUtils.readUTF8(index.path);
+ response.write(contents);
+ } catch (e) {
+ response.setStatusLine("1.1", 500, "Server error");
+ response.write(e.toString());
+ } finally {
+ response.finish();
+ }
+ });
+
+ server.start(-1);
+ return server;
+}
+
+function withMockApiServer(apiName = "mock_api") {
+ return withServer(makeMockApiServer(do_get_file(apiName)));
+}
+
+const CryptoUtils = {
+ _getHashStringForCrypto(aCrypto) {
+ // return the two-digit hexadecimal code for a byte
+ let toHexString = charCode => ("0" + charCode.toString(16)).slice(-2);
+
+ // convert the binary hash data to a hex string.
+ let binary = aCrypto.finish(false);
+ let hash = Array.from(binary, c => toHexString(c.charCodeAt(0)));
+ return hash.join("").toLowerCase();
+ },
+
+ /**
+ * Get the computed hash for a given file
+ * @param {nsIFile} file The file to be hashed
+ * @param {string} [algorithm] The hashing algorithm to use
+ */
+ getFileHash(file, algorithm = "sha256") {
+ const crypto = CryptoHash(algorithm);
+ const fis = new FileInputStream(file, -1, -1, false);
+ crypto.updateFromStream(fis, file.fileSize);
+ const hash = this._getHashStringForCrypto(crypto);
+ fis.close();
+ return hash;
+ },
+};