The CSS [attribute] selector
The CSS attribute selector targets elements by an attribute, written in square brackets — [disabled] matches elements with that attribute, and [type="email"] matches a specific value. Operators like ^= (starts with), $= (ends with) and *= (contains) match parts of a value, which is great for styling links and inputs by their attributes.
Overview
The attribute selector matches elements based on their HTML attributes, written in square brackets. At its simplest, [disabled] selects every element that has a disabled attribute at all, and [type="email"] selects those whose type is exactly email — handy for styling form fields by their kind.
Where it gets powerful is the substring operators. [href^="https"] matches links whose href starts with https; [href$=".pdf"] matches those that end with .pdf; and [href*="example"] matches any that contain example. With these you can, say, add a lock icon to secure links or a document icon to PDFs, purely from CSS.
There are a couple more: [lang|="en"] matches a value that is exactly en or starts with en-, and [class~="card"] matches a whitespace-separated word in the value. You can also add a case-insensitive flag — [type="email" i] — when the attribute value's case should not matter.
Syntax
/* has the attribute */
[disabled] { opacity: 0.5; }
/* exact value */
input[type="email"] { … }
/* starts with / ends with / contains */
a[href^="https"] { … }
a[href$=".pdf"] { … }
a[href*="example"] { … }
Example
<style>
a { display: inline-block; margin-right: 16px; font: 600 15px system-ui, sans-serif; }
a[href^="https"] { color: #16a34a; }
a[href$=".pdf"]::after { content: " (PDF)"; color: #dc2626; }
a[href*="example"] { text-decoration: underline; }
</style>
<a href="https://example.com">Secure example link (green + underlined)</a>
<a href="/guide.pdf">Download guide</a>
Best practices
- Use the substring operators (
^=,$=,*=) to style links and inputs by their attribute values — e.g. flag external or PDF links. - Combine it with an element or class, like
input[type="email"], to keep the match precise. - Add the
iflag for case-insensitive matching when the value's case is unpredictable. - Remember its specificity matches a class (0,1,0), so it is easy to override.
Frequently asked questions
How do I select an element by attribute in CSS?
[type="email"] or just [disabled] to match elements that have the attribute.How do I select links that start with https?
a[href^="https"] { … }. Similarly $= matches the end and *= matches anywhere in the value.What is the difference between ^=, $= and *= ?
^= matches a value that starts with the string, $= one that ends with it, and *= one that contains it anywhere.How do I make an attribute selector case-insensitive?
i before the closing bracket, e.g. [type="email" i].