How to write a CSS Selector selecting elements NOT having a certain attribute?

That's the code you're looking for:

div:not([style]) button{
  background-color: red;
}

Now let's break it down. We have have four selectors in this example:

  1. div and button - these select html elements. We can replace it for example with a class selector like .weEq5.
  2. :not() - indicates that we want everything that does not qualify as the selector inside the brackets.
  3. [style] - an attribute selector which is very powerful. We can place inside the not any other css selector like html tag names (button or div), class names or ids.

The combination of div:not([style]) means that we want all divs that do not have a style attribute. After which we have a space and a button means that we want all the buttons that are inside the above selector.

Adding a > before the button div:not([style]) > button will only select button elements which are direct children of the selected div. It will exclude from selection buttons that are deeper inside the div.


Normally, you would write :not([style]) to match an element that does not have a style attribute, as described here which emphasizes the use of both () and [] brackets, in that order.

But if this isn't working in Selenium WebDriver, and worse still if :not(style) works exactly like how I would expect :not([style]) to, then that's a bug with its CSS selector parser, since :not(style) actually means "not a style element" which makes div:not(style) redundant as an element can only either be a div or a style but not both at the same time. Unless you absolutely require a selector, I strongly recommend using the XPath locator strategy instead of relying on quirks like this with Selenium WebDriver's CSS selector engine that force you to write selectors that are both incorrect and don't work anywhere else that accepts a selector.


I think more accurate CSS Selector is:

div[class]:not([style])>button

because the button element is a child of div element.

Hope it helps you!