Files
go-jdenticon/jdenticon-js/test/e2e/browser/test.js
Kevin McIntyre f84b511895 init
2025-06-18 01:00:00 -04:00

187 lines
5.9 KiB
JavaScript

const express = require("express");
const fs = require("fs");
const tap = require("tap");
const webdriver = require("selenium-webdriver");
const screenshot = require("./screenshooter");
const BlinkDiff = require("blink-diff");
const path = require("path");
// Command line arguments examples:
// node test.js win ie11,chrome
// node test.js macos safari,chrome,firefox
const environmentId = process.argv[2] || "";
const enabledBrowsers = (process.argv[3] || "").split(/[,;]/g).filter(name => name);
if (!enabledBrowsers.length) {
throw new Error("Expected browser names");
}
const screenshotDir = process.env.BROWSER_SCREENSHOT_DIR || path.join(__dirname, "artifacts/screenshots");
const diffDir = process.env.BROWSER_DIFF_DIR || path.join(__dirname, "artifacts/diffs");
const expectedDir = process.env.BROWSER_EXPECTED_DIR || path.join(__dirname, "expected");
// fs.mkdirSync(_ , { recursive: true }) did not work on GitHub Actions using Node v12.18.2 (Windows and macOS).
// Worked fine locally however. Replacing it with a custom recursive implementation.
// Ignored GitHub issue for tracking any status:
// https://github.com/nodejs/node/issues/27293
function mkdirRecursive(dirPath) {
if (!fs.existsSync(dirPath)) {
const parent = path.dirname(dirPath)
if (parent && parent !== dirPath) {
mkdirRecursive(parent);
}
fs.mkdirSync(dirPath);
}
}
mkdirRecursive(screenshotDir);
mkdirRecursive(diffDir);
const BROWSER_DEFINITIONS = [
{
name: "ie11",
uaCompatible: "IE=Edge",
capabilities: {
"browserName": webdriver.Browser.INTERNET_EXPLORER,
"ie.ensureCleanSession": true,
},
},
{
name: "ie10",
uaCompatible: "IE=10",
capabilities: {
"browserName": webdriver.Browser.INTERNET_EXPLORER,
"ie.ensureCleanSession": true,
},
},
{
name: "ie9",
uaCompatible: "IE=9",
capabilities: {
"browserName": webdriver.Browser.INTERNET_EXPLORER,
"ie.ensureCleanSession": true,
},
},
{
name: "firefox",
capabilities: {
"browserName": webdriver.Browser.FIREFOX,
},
},
{
name: "chrome",
capabilities: {
"browserName": webdriver.Browser.CHROME,
},
},
{
name: "edge",
capabilities: {
"browserName": webdriver.Browser.EDGE,
"ms:edgeChromium": true,
},
},
{
name: "safari",
capabilities: {
"browserName": webdriver.Browser.SAFARI,
},
},
]
async function serve(root, options, asyncCallback) {
const app = express();
app.use(express.static(root, options));
await new Promise((resolve, reject) => {
const listener = app.listen(async () => {
try {
await asyncCallback(listener);
resolve();
} catch (e) {
reject(e);
} finally {
listener.close();
}
});
});
}
async function testBrowser(browserName) {
const browser = BROWSER_DEFINITIONS.find(x => x.name === browserName);
await tap.test(browserName, async t => {
if (!browser) {
t.fail(`Could not find a browser with the name ${browserName}.`);
return;
}
await serve(
path.join(__dirname, "../../"),
{
"index": ["index.html"],
setHeaders: resp => {
// Prevent stale files
resp.setHeader("Cache-Control", "no-store");
if (browser.uaCompatible) {
resp.setHeader("X-UA-Compatible", browser.uaCompatible);
}
}
},
async listener => {
const url = "http://localhost:" + listener.address().port + "/e2e/browser/assets/";
console.log(`Screenshot in ${browserName}`);
console.log(url);
const driver = await new webdriver.Builder()
.withCapabilities(browser.capabilities)
.build();
await driver.manage().window().setRect({ width: 1000, height: 2000 });
const documentInitialised = () => driver.executeScript("return true");
try {
await driver.get(url);
await driver.wait(() => documentInitialised(), 10000);
await driver.sleep(2500);
const screenshotBuffer = await screenshot(driver);
fs.writeFileSync(path.join(screenshotDir, `${environmentId}-${browserName}.png`), screenshotBuffer);
} finally {
await driver.quit();
}
var diff = new BlinkDiff({
imageAPath: path.join(expectedDir, `${environmentId}-${browserName}.png`),
imageBPath: path.join(screenshotDir, `${environmentId}-${browserName}.png`),
thresholdType: BlinkDiff.THRESHOLD_PIXEL,
threshold: 1000,
imageOutputPath: path.join(diffDir, `${environmentId}-${browserName}.png`),
// Ignore test metadata area containing browser versions etc.
blockOut: [{ x: 0, y: 0, width: 20000, height: 100 }],
});
const diffResult = await diff.runWithPromise();
t.ok(diff.hasPassed(diffResult.code), `Found ${diffResult.differences} differences.`);
},
);
});
}
async function testBrowsers(enabledBrowsers) {
for (var i = 0; i < enabledBrowsers.length; i++) {
await testBrowser(enabledBrowsers[i]);
}
}
testBrowsers(enabledBrowsers);