slot name属性必须完全字符串匹配,大小写、空格、连字符均敏感,仅直系子元素生效,不支持动态绑定,具名与默认插槽互斥,多同名slot仅首个多生效,无匹配则内容静默丢弃。

slot name属性必须完全字符串匹配
具名插槽生效的唯一条件是:slot 属性值和 <slot name="xxx"></slot> 中的 name 值**逐字符完全一致**。大小写、空格、连字符全部敏感,浏览器不做任何转换。
常见错误现象:
-
<h2 slot="Header">标题</h2>不会进入<slot name="header"></slot> -
<p slot="footer ">版权</p>(末尾空格)匹配失败,内容进默认插槽或丢弃 -
<div slot="sidebar-2"></div>对不上<slot name="sidebar"></slot>
调试建议:检查 shadowRoot.querySelector('slot[name="header"]').assignedNodes() 是否为空数组——这是最直接的验证方式。
slot属性只对直系子元素生效
插槽分发逻辑只扫描自定义元素的**直接子节点**,嵌套一层就失效。
使用场景:
- ✅ 正确:
<my-card><h2 slot="title">Hello</h2></my-card> - ❌ 无效:
<my-card><div><h2 slot="title">Hello</h2></div></my-card>——<h2></h2>是孙节点,slot属性被忽略
性能影响:不触发重排或重绘,但结构错位会导致内容静默丢失,且无任何报错提示。
name属性不支持动态值或表达式
name 是纯静态 HTML 属性,不能绑定变量、模板字符串或 JS 表达式。
容易踩的坑:
-
<slot :name="headerName"></slot>(Vue 中未用v-bind)→ 实际解析为字面量name="headerName" -
<slot name="${slotName}"></slot>在 HTML 源码中无效,仅在 JS 字符串拼接或模板引擎中起作用 - 用
setAttribute('name', 'footer')动态修改 → 分发已在connectedCallback阶段完成,后续改名不触发重分发
真正可用的只有编译/运行时已确定的字面量,比如 <slot name="user-avatar"></slot>。
具名插槽与默认插槽严格分区
它们不是“备选”关系,而是互不干扰的独立通道。
关键规则:
- 带
slot="xxx"的节点,只尝试匹配<slot name="xxx"></slot>,**永远不会 fallback 到默认插槽** - 没写
slot属性的节点(如<p>正文</p>),只进第一个无name的<slot></slot> -
<slot name="aside">侧边栏默认内容</slot>中的 fallback 文本,仅在assignedNodes().length === 0时显示;哪怕传了个空<div slot="aside"></div>,fallback 也不会出现
最容易被忽略的是:内容“看不见”却没有任何错误提示——这时候得同时核对四件事:自定义元素定义、Shadow DOM 构建时机、Light DOM 子节点层级、以及每一个字符是否完全一致。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











