--- a/browser/base/content/test/general/browser_parsable_css.js
+++ b/browser/base/content/test/general/browser_parsable_css.js
@@ -4,64 +4,74 @@
/* This list allows pre-existing or 'unfixable' CSS issues to remain, while we
* detect newly occurring issues in shipping CSS. It is a list of objects
* specifying conditions under which an error should be ignored.
*
* Every property of the objects in it needs to consist of a regular expression
* matching the offending error. If an object has multiple regex criteria, they
* ALL need to match an error in order for that error not to cause a test
* failure. */
-const kWhitelist = [
+let whitelist = [
// CodeMirror is imported as-is, see bug 1004423.
- {sourceName: /codemirror\.css$/i},
+ {sourceName: /codemirror\.css$/i,
+ isFromDevTools: true},
// PDFjs is futureproofing its pseudoselectors, and those rules are dropped.
{sourceName: /web\/viewer\.css$/i,
- errorMessage: /Unknown pseudo-class.*(fullscreen|selection)/i},
+ errorMessage: /Unknown pseudo-class.*(fullscreen|selection)/i,
+ isFromDevTools: false},
// Tracked in bug 1004428.
- {sourceName: /aboutaccounts\/(main|normalize)\.css$/i},
+ {sourceName: /aboutaccounts\/(main|normalize)\.css$/i,
+ isFromDevTools: false},
// TokBox SDK assets, see bug 1032469.
- {sourceName: /loop\/.*sdk-content\/.*\.css$/i},
+ {sourceName: /loop\/.*sdk-content\/.*\.css$/i,
+ isFromDevTools: false},
// Loop standalone client CSS uses placeholder cross browser pseudo-element
{sourceName: /loop\/.*\.css$/i,
- errorMessage: /Unknown pseudo-class.*placeholder/i},
+ errorMessage: /Unknown pseudo-class.*placeholder/i,
+ isFromDevTools: false},
{sourceName: /loop\/.*shared\/css\/common.css$/i,
- errorMessage: /Unknown property .user-select./i},
+ errorMessage: /Unknown property .user-select./i,
+ isFromDevTools: false},
// Highlighter CSS uses a UA-only pseudo-class, see bug 985597.
{sourceName: /highlighters\.css$/i,
- errorMessage: /Unknown pseudo-class.*moz-native-anonymous/i},
+ errorMessage: /Unknown pseudo-class.*moz-native-anonymous/i,
+ isFromDevTools: true},
// Responsive Design Mode CSS uses a UA-only pseudo-class, see Bug 1241714.
{sourceName: /responsive-ua\.css$/i,
- errorMessage: /Unknown pseudo-class.*moz-dropdown-list/i},
+ errorMessage: /Unknown pseudo-class.*moz-dropdown-list/i,
+ isFromDevTools: true},
];
var moduleLocation = gTestPath.replace(/\/[^\/]*$/i, "/parsingTestHelpers.jsm");
var {generateURIsFromDirTree} = Cu.import(moduleLocation, {});
// Add suffix to stylesheets' URI so that we always load them here and
// have them parsed. Add a random number so that even if we run this
// test multiple times, it would be unlikely to affect each other.
const kPathSuffix = "?always-parse-css-" + Math.random();
/**
* Check if an error should be ignored due to matching one of the whitelist
- * objects defined in kWhitelist
+ * objects defined in whitelist
*
* @param aErrorObject the error to check
* @return true if the error should be ignored, false otherwise.
*/
function ignoredError(aErrorObject) {
- for (let whitelistItem of kWhitelist) {
+ for (let whitelistItem of whitelist) {
let matches = true;
- for (let prop in whitelistItem) {
- if (!whitelistItem[prop].test(aErrorObject[prop] || "")) {
+ for (let prop of ["sourceName", "errorMessage"]) {
+ if (whitelistItem.hasOwnProperty(prop) &&
+ !whitelistItem[prop].test(aErrorObject[prop] || "")) {
matches = false;
break;
}
}
if (matches) {
+ whitelistItem.used = true;
return true;
}
}
return false;
}
function once(target, name) {
return new Promise((resolve, reject) => {
@@ -145,17 +155,17 @@ function convertToChromeUri(fileUri) {
function messageIsCSSError(msg) {
// Only care about CSS errors generated by our iframe:
if ((msg instanceof Ci.nsIScriptError) &&
msg.category.includes("CSS") &&
msg.sourceName.endsWith(kPathSuffix)) {
let sourceName = msg.sourceName.slice(0, -kPathSuffix.length);
let msgInfo = { sourceName, errorMessage: msg.errorMessage };
- // Check if this error is whitelisted in kWhitelist
+ // Check if this error is whitelisted in whitelist
if (!ignoredError(msgInfo)) {
ok(false, `Got error message for ${sourceName}: ${msg.errorMessage}`);
return true;
}
info(`Ignored error for ${sourceName} because of filter.`);
}
return false;
}
@@ -229,16 +239,25 @@ add_task(function* checkAllTheCSS() {
yield Promise.all(allPromises);
let messages = Services.console.getMessageArray();
// Count errors (the test output will list actual issues for us, as well
// as the ok(false) in messageIsCSSError.
let errors = messages.filter(messageIsCSSError);
is(errors.length, 0, "All the styles (" + allPromises.length + ") loaded without errors.");
+ // Confirm that all whitelist rules have been used.
+ for (let item of whitelist) {
+ if (!item.used && isDevtools == item.isFromDevTools) {
+ ok(false, "Unused whitelist item. " +
+ (item.sourceName ? " sourceName: " + item.sourceName : "") +
+ (item.errorMessage ? " errorMessage: " + item.errorMessage : ""));
+ }
+ }
+
// Clean up to avoid leaks:
iframe.remove();
doc.head.innerHTML = '';
doc = null;
iframe = null;
windowless.close();
windowless = null;
});