Skip to content

Instantly share code, notes, and snippets.

@paceaux
Last active February 12, 2026 16:40
Show Gist options
  • Select an option

  • Save paceaux/2b163c39062ec7ed4d78f70d78e5a2fc to your computer and use it in GitHub Desktop.

Select an option

Save paceaux/2b163c39062ec7ed4d78f70d78e5a2fc to your computer and use it in GitHub Desktop.
Get all CSS selectors containing a particular CSS property
/** queryCSSBySelector
* queries the CSSOM and DOM looking for rulesets containing a particular partial or whole CSS selector
* @param {string} selector - The CSS selector to search for
* @param {object} [HTMLElement=document] - the node where the search begins
* @returns {Map<String,CSSRule>} Map where the key is a string and the value is the complete CSS Rule
*/
function queryCSSBySelector(selector, root = document) {
const styleSheets = Object.assign({},root.styleSheets, root.adoptedStyleSheets); // get all the stylesheets
const results = new Map(); // set up the variable that'll store our result
if (!selector) return results;
// loop through the stylesheets
Object.values(styleSheets).forEach(styleSheet => {
// have to wrap in a try because a restricted stylesheet throws an error
try {
const rules = styleSheet.cssRules; // every styleSheet has an enumerable of rules
// loop through the rules in a stylesheet
Object.values(rules).forEach(rule => {
const {style, selectorText} = rule;
if (style && selectorText?.includes(selector)) {
results.set(selectorText, rule)
}
});
} catch (err) {
console.log(err);
}
});
// account for web components using shadow dom
for (const node of root.querySelectorAll(selector)) {
if (node.shadowRoot) {
const inner = queryCSSBySelector(selector, node.shadowRoot);
for (const [innerText, innerRule] of inner) {
results.set(innerText, innerRule);
}
}
}
return results;
}
/** queryCSSByPropertyName
* queries the CSSOM looking for CSS rulesets containing a particular CSS property.
* @param {string} queryPropName CSS property name
* @param {string} queryPropValue value of CSS property
* @returns {Map<String, String>} key is CSS selector, value is full property
*/
function queryCSSByProperty(queryPropName, queryPropValue) {
const styleSheets= document.styleSheets; // get all the stylesheets
const properties = new Map(); // set up the variable that'll store our result
if (!queryPropName) return properties;
// loop through the stylesheets
Object.values(styleSheets).forEach(styleSheet => {
// have to wrap in a try because a restricted stylesheet throws an error
try {
const rules = styleSheet.cssRules; // every styleSheet has an enumerable of rules
// loop through the rules in a stylesheet
Object.values(rules).forEach(rule => {
const {style, selectorText} = rule;
if (style) {
const propertyValue = style.getPropertyValue(queryPropName);
const hasPropValMatch = queryPropValue && propertyValue.indexOf(queryPropValue) !== -1;
// wanting exact match of css property value
if (queryPropValue && hasPropValMatch) {
properties.set(selectorText, `${queryPropName}:${propertyValue}`);
}
// don't want an exact match of css property value
if (!queryPropValue && propertyValue) properties.set(selectorText, `${queryPropName}:${propertyValue}`);
}
});
} catch (err) {
console.log(err);
}
});
return properties;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment