template.content 是只读 DocumentFragment,必须通过它访问内部结构;克隆需用 cloneNode(true) 深克隆,否则为空;查询、填值、事件等操作均须作用于克隆后的内容,且需手动处理 ID 冲突与事件绑定。

template.content 是只读 DocumentFragment,不能直接插入 DOM
直接 appendChild(template.content) 会导致内容被“剪切”走,第二次再调用就拿到空 fragment;更糟的是,它不会报错,只是静默失败。这是因为 DocumentFragment 只能有一个父节点,移动操作本质是转移而非复制。
常见错误现象:template.children 永远为空、template.querySelector('div') 返回 null、template.innerHTML 始终是空字符串——这些都不是 bug,而是规范行为。
- 必须通过
template.content访问内部结构,这是唯一合法入口 -
template.content是只读的,不能直接appendChild到页面容器中 - 所有 DOM 查询(如
querySelector)必须作用于template.content,而不是template元素本身
克隆必须用 cloneNode(true),true 不可省略
浅克隆(cloneNode(false))只复制 DocumentFragment 本身,不包含任何子节点,结果是个空壳;深克隆(true)才真正复制全部嵌套结构、属性、文本和表单当前值。
- 不加
true→ 得到空 fragment,后续querySelector找不到任何元素 - 加
true→ 完整复制 input 的value、checked状态、textarea光标位置等真实 DOM 状态 - 克隆后原
template不受影响,可反复使用
克隆后的内容需手动填值,脚本/样式默认不生效
<template></template> 内部的 <script></script>、<style></style>、<img src alt="HTML template的content属性用法?通过JS读取并克隆内容" > 在离线状态下完全静默:不执行、不请求、不参与样式计算。克隆后插入 DOM 才触发,但也不会自动重连事件或激活 slot。
立即学习“前端免费学习笔记(深入)”;
- 填文本优先用
textContent,不是innerHTML(防 XSS + 保事件) - 设表单值用
input.value = 'xxx',不是textContent或setAttribute('value', ...) - 需要运行脚本?得手动创建新
script元素并插入,不能依赖模板里原有的<script></script> - 含
<slot></slot>的模板在普通 DOM 中无意义,仅对 Shadow DOM 有效
高频渲染必须用 DocumentFragment 批量中转
循环中每轮都 container.appendChild(clone),浏览器会频繁触发重排重绘,100 条以上明显卡顿。这不是优化建议,是性能断崖点。
- 先创建中转对象:
const frag = document.createDocumentFragment() - 循环内:克隆 → 填值 →
frag.appendChild(clone) - 循环外:一次性
container.appendChild(frag) - 注意:
frag不在真实 DOM 中,querySelector查不到它,放心用
最容易被忽略的是 ID 冲突和事件绑定缺失:模板里带 id="submit-btn",克隆多次就会重复;内联 onclick 或已绑定的事件监听器,克隆后全丢失——这两点必须在克隆后显式处理。


















