Element.part is a read-only instance property that returns a DOMTokenList of CSS part identifiers. These names let external stylesheets reach into shadow DOM via the ::part() pseudo-element. Learn how to read, add, remove, and toggle parts—with five examples and try-it labs.
01
Kind
Instance property
02
Access
Read-only (object)
03
Type
DOMTokenList
04
Reflects
part attribute
05
Status
Baseline widely
06
Used with
::part() CSS
Fundamentals
Introduction
Shadow DOM encapsulates styles, but sometimes the component author wants to let outside CSS customize specific pieces. That is where CSS Shadow Parts come in: add a part attribute to an element inside a shadow tree, and external selectors like my-elem::part(heading) can style it.
The Element.part property exposes those identifiers as a DOMTokenList, similar to classList. You can read, add, remove, replace, or toggle part names programmatically.
JavaScript
const el = this.shadowRoot.querySelector(".tab");
console.log(el.part); // DOMTokenList ["tab"]
el.part.add("active"); // now "tab active"
el.part = "tab selected"; // shorthand assignment
💡
Beginner tip
Think of part like classList, but for exposing shadow internals to the page’s CSS via ::part().
Concept
Understanding the Property
MDN: the read-only part property of the Element interface contains a DOMTokenList object representing the part identifier(s) of the element. It reflects the element’s part content attribute. These can be used to style parts of a shadow DOM via the ::part pseudo-element.
Read-only object — you cannot replace the DOMTokenList, but you can mutate it or assign a string to el.part.
Reflects attribute — mirrors the HTML part attribute.
Empty by default — length === 0 when no part attribute is set.
Baseline — widely available since July 2020 (MDN).
Foundation
📝 Syntax
JavaScript
element.part
Value
A DOMTokenList object. If the part attribute is not set or empty, the returned list has length === 0.
Item
Detail
Type
DOMTokenList
Access
Read-only (object), but list is mutable
Reflects
HTML part attribute
CSS companion
::part(name) pseudo-element
💡
Assignment shorthand
You can write el.part = "tab active" instead of calling add() / remove(). This replaces the entire list.
Pattern
📋 MDN Shadow Parts Example Shape
MDN’s shadow-part example finds elements with a part attribute, then toggles part identifiers on click:
Related learning: ::part(), exportparts, and innerHTML.
Cheat Sheet
⚡ Quick Reference
Goal
Code / note
Read parts
el.part → DOMTokenList
Add a part
el.part.add("active")
Remove a part
el.part.remove("active")
Toggle
el.part.toggle("active")
Replace all
el.part = "tab selected"
CSS usage
my-elem::part(tab) { color: blue; }
Snapshot
🔍 At a Glance
Four facts about Element.part.
Kind
read-only
Instance
Type
DOMTokenList
Like classList
CSS hook
::part()
Shadow styling
Baseline
widely
Jul 2020+
Hands-On
Examples Gallery
Examples follow MDN Element: part. Labs use inline shadow DOM so you can experiment safely.
📚 Getting Started
Read part names and mutate the list.
Example 1 — Read Part Names
Log the DOMTokenList returned by part.
JavaScript
const el = document.querySelector("[part]");
console.log(el.part); // DOMTokenList
console.log(el.part.length); // number of parts
console.log(el.part.value); // space-separated string
Assigning a string to el.part replaces all tokens at once. The outer CSS rule my-tabs::part(active) { font-weight: bold; } instantly highlights the active tab.
Example 5 — Support Snapshot
Feature-detect part and review key facts.
JavaScript
console.log({
supported: "part" in Element.prototype,
returns: "DOMTokenList (like classList)",
cssHook: "::part(name)",
status: "Baseline Widely available (MDN)"
});
Element.part is Baseline Widely available (MDN: across browsers since July 2020). Logos use the shared browser-image-sprite.png sprite from this project.
✓ Baseline Widely available
Element.part
Read-only — DOMTokenList of CSS shadow part identifiers; styled externally via ::part().
BaselineWidely available
Google ChromeSupported
Yes
Microsoft EdgeSupported
Yes
Mozilla FirefoxSupported
Yes
Apple SafariSupported
Yes
OperaSupported
Yes
Internet ExplorerNot supported
No
partBaseline
Bottom line: Use Element.part to expose shadow DOM internals for external CSS theming via the ::part() pseudo-element.
Wrap Up
Conclusion
Element.part returns a DOMTokenList of CSS part identifiers that let external stylesheets reach into shadow DOM via ::part(). Use it to build customizable web components without sacrificing encapsulation.
Combine part with classList for internal + external styling
Feature-detect before relying on part in legacy environments
❌ Don’t
Expose every internal element as a part (breaks encapsulation)
Rely on part for non-shadow-DOM elements (no CSS effect)
Expect ::part() to pierce nested shadows without exportparts
Use generic names like div1 or span2
Forget that IE does not support this property
Summary
Key Takeaways
Knowledge Unlocked
Five things to remember about part
DOMTokenList of CSS shadow part names—style internals from outside.
5
Core concepts
📄01
Read-only
object ref
Kind
📝02
DOMTokenList
like classList
Type
🔍03
::part()
CSS companion
Use
✅04
Baseline
widely available
Status
🎯05
Shadow only
no effect outside
Tip
❓ Frequently Asked Questions
It returns a read-only DOMTokenList of the element's CSS part identifiers (reflecting the part HTML attribute). These names let external CSS style shadow DOM internals via the ::part() pseudo-element.
No. MDN marks Element.part as Baseline Widely available (since July 2020). It is not Deprecated, Experimental, or Non-standard.
Yes. Although the property itself is read-only (you cannot replace the DOMTokenList object), you can call add(), remove(), replace(), and toggle() on it, or assign a string directly to el.part which sets its value.
It is a CSS pseudo-element that selects elements inside a shadow tree which have been exposed via the part attribute. For example, my-element::part(tab) targets elements with part="tab" inside my-element's shadow DOM.
You can set a part attribute on any element, but ::part() styling only works across shadow boundaries. On regular elements the attribute has no visual effect.
The part attribute names parts on direct shadow children. The exportparts attribute on the shadow host re-exports part names from nested shadow trees so outer CSS can reach them.
Did you know?
::part() deliberately does not match descendant parts in nested shadow trees. The exportparts attribute lets intermediate hosts forward inner part names outward, keeping the API surface explicit and intentional.