v-html的问题及解决办法
1、v-html和v-text(简写:{{}})相比,可以识别字符串中的标签
data() { return { html1: '<p>HTML1</p>' } }
<p v-html="html1"></p> <p v-text="html1"></p> <p>{{html1}}</p>
结果:
2、v-html会覆盖当前标签内的子元素
<div v-html="html1"> <h1>标题</h1> </div>
结果:
3、样式问题
scoped的样式不会应用在v-html内部,因为v-html的内容没有经过vue的模板编译器处理
解决办法:
①使用scoped时用深度选择器(>>>),scss和less使用 /deep/
data() { return { html1: '<p class="my-p">HTML1</p>' } }
<div v-html="html1"></div>
<style lang="less" scoped> #app { /deep/ .my-p { color: red; } } </style>
②不使用scoped,另写一个style标签针对全局样式,这里要使用BEM命名规则
<style lang='less'> #app { .my-p { font-size: 30px; } } </style>
4、XSS
data() { return { test: `<a onclick="alert('攻击你')">连接</a>`, message: `hello vue<img src="xx" onerror="alert('这里也可以攻击你')">` } }
<div v-html="test"></div> <div v-html="message"></div>
当图片加载错误时:
点击【连接】时:
如何解决:
①安装xss插件:npm i xss
②main.js中引入
import xss from 'xss'
Vue.prototype.xss = xss
③vue.config.js
chainWebpack: (config) => { config.module .rule('vue') .use('vue-loader') .loader('vue-loader') .tap((options) => { options.compilerOptions.directives = { html(node, directiveMeta) { ;(node.props || (node.props = [])).push({ name: 'innerHTML', value: `xss(_s(${directiveMeta.value}))` }) } } return options }) },
④重启后这些事件就没了
⑤vue官网强调了永远不要让用户输入的内容通过v-html渲染出来!
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· 10年+ .NET Coder 心语 ── 封装的思维:从隐藏、稳定开始理解其本质意义
· 【设计模式】告别冗长if-else语句:使用策略模式优化代码结构
· 提示词工程——AI应用必不可少的技术
· 字符编码:从基础到乱码解决
· 地球OL攻略 —— 某应届生求职总结
2019-08-19 说几条JavaScript的基本规范