mirror of
https://github.com/discourse/discourse.git
synced 2024-11-29 20:04:02 +08:00
59097b207f
Over the years we accrued many spelling mistakes in the code base. This PR attempts to fix spelling mistakes and typos in all areas of the code that are extremely safe to change - comments - test descriptions - other low risk areas
303 lines
7.3 KiB
JavaScript
303 lines
7.3 KiB
JavaScript
/*eslint no-console: ["error", { allow: ["log", "error"] }] */
|
|
|
|
// Chrome QUnit Test Runner
|
|
// Author: David Taylor
|
|
// Requires chrome-launcher and chrome-remote-interface from npm
|
|
// An up-to-date version of chrome is also required
|
|
|
|
let args = process.argv.slice(2);
|
|
|
|
if (args.length < 1 || args.length > 3) {
|
|
console.log("Usage: node run-qunit.js <URL> <timeout> <result_file>");
|
|
process.exit(1);
|
|
}
|
|
|
|
const chromeLauncher = require("chrome-launcher");
|
|
const CDP = require("chrome-remote-interface");
|
|
|
|
const QUNIT_RESULT = args[2];
|
|
const fs = require("fs");
|
|
|
|
if (QUNIT_RESULT) {
|
|
(async () => {
|
|
await fs.stat(QUNIT_RESULT, (err, stats) => {
|
|
if (stats && stats.isFile()) {
|
|
fs.unlink(QUNIT_RESULT, (unlinkErr) => {
|
|
if (unlinkErr) {
|
|
console.log("Error deleting " + QUNIT_RESULT + " " + unlinkErr);
|
|
}
|
|
});
|
|
}
|
|
});
|
|
})();
|
|
}
|
|
|
|
async function runAllTests() {
|
|
function launchChrome() {
|
|
const options = {
|
|
chromeFlags: [
|
|
"--disable-gpu",
|
|
"--headless",
|
|
"--no-sandbox",
|
|
"--disable-dev-shm-usage",
|
|
"--mute-audio",
|
|
"--window-size=1440,900",
|
|
],
|
|
};
|
|
|
|
if (process.env.REMOTE_DEBUG) {
|
|
options.port = 9222;
|
|
}
|
|
|
|
return chromeLauncher.launch(options);
|
|
}
|
|
|
|
let chrome = await launchChrome();
|
|
|
|
let protocol = null;
|
|
let connectAttempts = 0;
|
|
while (!protocol) {
|
|
// Workaround for intermittent CI error caused by
|
|
// https://github.com/GoogleChrome/chrome-launcher/issues/145
|
|
try {
|
|
protocol = await CDP({ port: chrome.port });
|
|
} catch (e) {
|
|
if (e.message === "No inspectable targets" && connectAttempts < 50) {
|
|
connectAttempts++;
|
|
console.log(
|
|
"Unable to establish connection to chrome target - trying again..."
|
|
);
|
|
// eslint-disable-next-line
|
|
await new Promise((resolve) => setTimeout(resolve, 100));
|
|
} else {
|
|
throw e;
|
|
}
|
|
}
|
|
}
|
|
|
|
const { Inspector, Page, Runtime } = protocol;
|
|
|
|
// eslint-disable-next-line
|
|
await Promise.all([Inspector.enable(), Page.enable(), Runtime.enable()]);
|
|
|
|
Inspector.targetCrashed((entry) => {
|
|
console.log("Chrome target crashed:");
|
|
console.log(entry);
|
|
});
|
|
|
|
Runtime.exceptionThrown((exceptionInfo) => {
|
|
console.log(exceptionInfo.exceptionDetails.exception.description);
|
|
});
|
|
|
|
Runtime.consoleAPICalled((response) => {
|
|
const message = response["args"][0].value;
|
|
|
|
// Not finished yet, don't add a newline
|
|
if (message && message.startsWith && message.startsWith("↪")) {
|
|
process.stdout.write(message);
|
|
} else if (
|
|
message &&
|
|
message.startsWith &&
|
|
message.startsWith("AUTOSPEC:")
|
|
) {
|
|
fs.appendFileSync(QUNIT_RESULT, `${message.slice(10)}\n`);
|
|
} else {
|
|
console.log(message);
|
|
}
|
|
});
|
|
|
|
let url = args[0] + "&qunit_disable_auto_start=1";
|
|
console.log("navigate to ", url);
|
|
Page.navigate({ url });
|
|
|
|
Page.loadEventFired(async () => {
|
|
let qff = process.env.QUNIT_FAIL_FAST;
|
|
await Runtime.evaluate({
|
|
expression:
|
|
`const QUNIT_FAIL_FAST = ` +
|
|
(qff === "1" || qff === "true").toString() +
|
|
";",
|
|
});
|
|
await Runtime.evaluate({
|
|
expression: `(${qunit_script})();`,
|
|
});
|
|
|
|
if (args[0].indexOf("report_requests=1") > -1) {
|
|
await Runtime.evaluate({
|
|
expression: "QUnit.config.logAllRequests = true",
|
|
});
|
|
}
|
|
|
|
const timeout = parseInt(args[1] || 300000, 10);
|
|
let start = Date.now();
|
|
|
|
let interval;
|
|
|
|
let runTests = async function () {
|
|
if (Date.now() > start + timeout) {
|
|
console.error("\n\nTests timed out\n");
|
|
protocol.close();
|
|
chrome.kill();
|
|
process.exit(124);
|
|
}
|
|
|
|
let numFails = await Runtime.evaluate({
|
|
expression: `(${check_script})()`,
|
|
});
|
|
|
|
if (numFails && numFails.result && numFails.result.type !== "undefined") {
|
|
clearInterval(interval);
|
|
protocol.close();
|
|
chrome.kill();
|
|
|
|
if (numFails.result.value > 0) {
|
|
process.exit(1);
|
|
} else {
|
|
process.exit();
|
|
}
|
|
}
|
|
};
|
|
|
|
interval = setInterval(runTests, 250);
|
|
});
|
|
}
|
|
|
|
runAllTests().catch((e) => {
|
|
console.log("Failed to run tests: " + e);
|
|
process.exit(1);
|
|
});
|
|
|
|
// The following functions are converted to strings
|
|
// And then sent to chrome to be evaluated
|
|
function logQUnit() {
|
|
let testErrors = [];
|
|
let assertionErrors = [];
|
|
|
|
console.log("\nRunning: " + JSON.stringify(QUnit.urlParams) + "\n");
|
|
|
|
QUnit.config.testTimeout = 10000;
|
|
|
|
let durations = {};
|
|
|
|
let inTest = false;
|
|
QUnit.testStart(function (context) {
|
|
console.log("↪ " + context.module + "::" + context.name);
|
|
inTest = true;
|
|
});
|
|
|
|
QUnit.testDone(function (context) {
|
|
durations[context.module + "::" + context.name] = context.runtime;
|
|
|
|
if (context.failed) {
|
|
const msg =
|
|
" Test Failed: " +
|
|
context.name +
|
|
assertionErrors.join(" ") +
|
|
"\n" +
|
|
context.source;
|
|
testErrors.push(msg);
|
|
assertionErrors = [];
|
|
|
|
// Pass QUNIT_FAIL_FAST on the command line to quit after the first failure
|
|
// eslint-disable-next-line
|
|
if (QUNIT_FAIL_FAST) {
|
|
QUnit.config.queue.length = 0;
|
|
}
|
|
if (inTest) {
|
|
console.log(" [✘]");
|
|
}
|
|
} else {
|
|
if (inTest) {
|
|
console.log(" [✔]");
|
|
}
|
|
}
|
|
inTest = false;
|
|
});
|
|
|
|
QUnit.log(function (context) {
|
|
if (context.result) {
|
|
return;
|
|
}
|
|
|
|
let msg = "\n Assertion Failed:";
|
|
if (context.message) {
|
|
msg += " " + context.message;
|
|
}
|
|
|
|
if (context.expected) {
|
|
msg +=
|
|
"\n Expected: " + context.expected + ", Actual: " + context.actual;
|
|
}
|
|
|
|
assertionErrors.push(msg);
|
|
});
|
|
|
|
QUnit.done(function (context) {
|
|
console.log("\n");
|
|
|
|
console.log("Slowest tests");
|
|
console.log("----------------------------------------------");
|
|
let ary = Object.keys(durations).map((key) => ({
|
|
key: key,
|
|
value: durations[key],
|
|
}));
|
|
ary.sort((p1, p2) => p2.value - p1.value);
|
|
ary.slice(0, 30).forEach((pair) => {
|
|
console.log(pair.key + ": " + pair.value + "ms");
|
|
});
|
|
|
|
console.log("\n");
|
|
|
|
if (testErrors.length) {
|
|
console.log("Test Errors");
|
|
console.log("----------------------------------------------");
|
|
testErrors.forEach((e) => {
|
|
console.error(e);
|
|
});
|
|
console.log("\n");
|
|
}
|
|
|
|
let stats = [
|
|
"Time: " + context.runtime + "ms",
|
|
"Total: " + context.total,
|
|
"Passed: " + context.passed,
|
|
"Failed: " + context.failed,
|
|
];
|
|
console.log(stats.join(", "));
|
|
|
|
if (context.failed) {
|
|
console.log("\nUse this filter to run in the same order:");
|
|
console.log(
|
|
"QUNIT_FAIL_FAST=1 QUNIT_SEED=" +
|
|
QUnit.config.seed +
|
|
" rake qunit:test\n"
|
|
);
|
|
console.log("If you have a web environment running, you can visit:");
|
|
console.log(
|
|
"http://localhost:3000/qunit?hidepassed&seed=" +
|
|
QUnit.config.seed +
|
|
"\n\n"
|
|
);
|
|
}
|
|
|
|
window.qunitDone = context;
|
|
});
|
|
QUnit.start();
|
|
}
|
|
let qunit_script = logQUnit.toString();
|
|
|
|
if (QUNIT_RESULT) {
|
|
qunit_script = qunit_script.replace(
|
|
"/* QUNIT_RESULT */",
|
|
"console.log(`AUTOSPEC: ${context.module}:::${context.testId}:::${context.name}`);"
|
|
);
|
|
}
|
|
|
|
function check() {
|
|
if (window.qunitDone) {
|
|
return window.qunitDone.failed;
|
|
}
|
|
}
|
|
|
|
const check_script = check.toString();
|