VSCode默认不识别.njk文件为HTML导致语法高亮、Emmet补全、自动闭合等功能失效;需在settings.json中配置"files.associations": {"*.njk": "html"}绑定为HTML模式,并安装esbenp的Nunjucks插件以保留<% %>和{{ }}语义高亮。

VSCode 默认不支持 Nunjucks 模板的语法高亮、Emmet 补全、自动闭合或格式化——这不是插件没装对,而是它根本没把 .njk 文件当 HTML 处理。
为什么 Nunjucks 文件里 <div> 不高亮、Tab 不补全、双击选不中标签对
VSCode 打开 .njk 文件时,默认语言模式是 Plain Text 或 Nunjucks(如果装了插件但没配关联),此时所有 HTML 相关功能全部失效:Emmet 不触发、auto-close-tag 和 auto-rename-tag 完全不响应、括号匹配和缩进也按纯文本逻辑走。
根本原因:VSCode 的 HTML 功能(补全、高亮、格式化)只绑定在 html 语言模式上,而 Nunjucks 是模板语言,不是原生语言模式。
- 手动切换语言模式:打开任意
.njk文件 → 点右下角语言标签(如显示Plain Text)→ 选Configure File Association for '.njk'→ 输入html回车 - 或直接改
settings.json:"files.associations": { "*.njk": "html" } - 改完后,
<div>立刻被识别,Emmetdiv.tab、自动闭合</div>、标签对双击选中全部恢复
怎么保留 <% %> 和 {{ }} 的语法高亮
单纯绑成 html 模式会让 <% if (x) { %> 变成灰白色普通文本——HTML 高亮器不认识这些模板符号。
必须配合专用语法插件,且插件本身不接管文件关联,只负责着色:
- 装
Nunjucks插件(作者:esbenp):提供<% %>、{{ }}、{% %}的语义高亮 + 基础 Emmet 支持 - 确保
files.associations已设为html,否则该插件的高亮不会生效 - 注意:它不提供跳转、hover 提示或类型推导;
beforeRender这类 API 仍靠 JS/TS 语言服务识别
为什么保存时格式化会把 <% 块换行错位甚至破坏逻辑
VSCode 内置的 HTML 格式化器(包括 Prettier 的 html 解析器)把 <% 当作普通开始标签处理,强行缩进、换行,导致:
<div>
<% if(items.length) { %>
<ul><% items.forEach() %></ul>
<% } %>
</div>
变成:
<div>
<% if(items.length) { %>
<ul><% items.forEach() %></ul>
<% } %>
</div>
这在某些 Nunjucks 运行时会报错(比如空格敏感的 set 或 macro 块)。解决方法只有两个:
- 禁用保存时自动格式化 Nunjucks 文件:
"editor.formatOnSave": false, "[nunjucks]": { "editor.formatOnSave": false } - 或改用支持 Nunjucks 的外部格式化器(如
jkformat),但需手动配置editor.defaultFormatter并确保其能稳定解析嵌套逻辑块——实际项目中极少有人这么干,因为维护成本高、兼容性差
容易被忽略的关键点
文件关联必须写 "*.njk": "html",不能写 "*.njk": "nunjucks"——后者只是启用插件的高亮,HTML 功能依然关闭;files.associations 是开关,插件是颜料,两者缺一不可。另外,如果项目混用 .njk 和 .html,别给 html 语言模式全局加 Prettier,否则纯 HTML 文件也会受 Nunjucks 兼容性限制影响。


















