如何在Express+EJS博客应用中渲染HTML标签?
在EJS中渲染含HTML标签的内容(解决直接显示标签文本的问题)
问题背景
你用Express+EJS+MongoDB开发博客时碰到的这个情况,本质是EJS的默认输出逻辑导致的:<%= %>语法会自动转义HTML字符,把<、>这类符号转换成对应的HTML实体(比如<、>),所以浏览器只会把它们当成普通文本显示,不会解析成真正的HTML元素。
快速解决方案
把EJS模板中输出HTML内容的<%= %>替换成<%- %>(注意是减号而非等号),这个语法会直接输出原始内容,不做转义处理。
修改你的singlepost.ejs文件中输出full_text的部分:
<!-- 原来的写法(会转义HTML) --> <%= post.full_text %> <!-- 修改后的写法(直接渲染HTML) --> <%- post.full_text %>
如果你的short_description或者title字段也可能包含HTML标签,同样需要把对应的<%= %>改成<%- %>——不过一般来说标题和摘要不建议包含HTML,这个可以根据你的业务需求灵活调整。
重要安全提醒
直接输出未过滤的HTML内容存在XSS攻击风险,如果你的博客允许用户提交内容(比如用户投稿),一定要对用户输入的HTML进行安全过滤,只保留<p>、<h1>、<img>这类安全标签,移除脚本、iframe这类危险标签。
举个简单的实现例子,你可以用sanitize-html包来处理:
- 先安装依赖包:
npm install sanitize-html
- 在你的
posts.js控制器中引入并处理内容:
const sanitizeHtml = require('sanitize-html'); exports.getSinglePost = (req, res) => { let id = req.params.id; Post.findById(id, function(err, post){ if(err){ console.log('Error: ', err); } else { // 过滤post中的HTML内容,只允许指定的安全标签和属性 const sanitizedFullText = sanitizeHtml(post.full_text, { allowedTags: ['p', 'h1', 'h2', 'h3', 'b', 'i', 'em', 'strong', 'a'], allowedAttributes: { 'a': ['href', 'target'] } }); res.render('singlepost', { website_name: 'MEAN Blog', post: { ...post, full_text: sanitizedFullText } }); } }); };
这样既能正常渲染HTML内容,又能有效避免恶意脚本注入的风险。
内容的提问来源于stack exchange,提问作者Razvan Zamfir
相关产品推荐
相关产品推荐

