diff --git a/src/lib/generateRules.js b/src/lib/generateRules.js index 6b86515412f6..c3b7ad92697b 100644 --- a/src/lib/generateRules.js +++ b/src/lib/generateRules.js @@ -262,11 +262,37 @@ function parseRules(rule, cache, options = {}) { const IS_VALID_PROPERTY_NAME = /^[a-z_-]/ function isValidPropName(name) { - // TODO: properly fix this! - return IS_VALID_PROPERTY_NAME.test(name) && !name.startsWith('http') + return IS_VALID_PROPERTY_NAME.test(name) +} + +/** + * @param {string} declaration + * @returns {boolean} + */ +function looksLikeUri(declaration) { + // Quick bailout for obvious non-urls + // This doesn't support schemes that don't use a leading // but that's unlikely to be a problem + if (!declaration.includes('://')) { + return false + } + + try { + const url = new URL(declaration) + return url.scheme !== '' && url.host !== '' + } catch (err) { + // Definitely not a valid url + return false + } } function isParsableCssValue(property, value) { + // We don't want to to treat [https://example.com] as a custom property + // Even though, according to the CSS grammar, it's a totally valid CSS declaration + // So we short-circuit here by checking if the custom property looks like a url + if (looksLikeUri(`${property}:${value}`)) { + return false + } + try { postcss.parse(`a{${property}:${value}}`).toResult() return true