在不允许 HTML 标签的情况下将 Markdown 转换为 HTML
Convert Markdown to HTML without allowing HTML Tags
我正在尝试构建一个支持 markdown 的 textarea
。我已成功将 markdown 转换为 HTML 以显示预览,使用以下管道:
import { Pipe, PipeTransform } from '@angular/core';
import * as marked from 'marked';
import * as DOMPurify from 'dompurify';
@Pipe({ name: 'markdown' })
export class MarkdownPipe implements PipeTransform {
markdownToSafeHtml(value: string): string {
const html = marked(value);
const safeHtml = DOMPurify.sanitize(html);
return safeHtml;
}
transform(str: string): string {
if (str && str.length > 0) {
const html = this.markdownToSafeHtml(str);
return html.toString();
}
return str;
}
}
以及以下 HTML:
<div [innerHTML]="value | markdown">
它正在工作并显示降价设计,但问题是我可以在降价字符串中添加任何 HTML 标签,因为我使用的是 innerHTML
div将使用它们,例如在此标签的预览中使用 <h1>hello</h1>
呈现,它应该将其呈现为文本。
- 如果没有其他 HTML 标签,我如何转换为 markdown?
- 我已经尝试过对HTML字母进行编码(例如
&
等),问题是在使用code markdown时,转换为:<div>example</div>
是 <div>example</div>
使用下面的管道终于成功了。
解决方案是创建一个包含 HTML 的元素,并使用 unescapeCodes
函数反转 <code>
元素中的 HTML 转义。
import { Pipe, PipeTransform } from '@angular/core';
import * as marked from 'marked';
import * as DOMPurify from 'dompurify';
@Pipe({ name: 'markdown' })
export class MarkdownPipe implements PipeTransform {
constructor() {
}
private escapeHTML(str: string) {
return str.replace(/&/g, "&")
.replace(/</g, "<")
.replace(/>/g, ">")
.replace(/"/g, """)
.replace(/'/g, "'");
}
private unescapeHTML(str: string) {
return str.replace(/&/g, "&")
.replace(/</g, "<")
.replace(/>/g, ">")
.replace(/"/g, "\"")
.replace(/'/g, "'");
}
private markdownToSafeHtml(value: string): string {
const html = marked(value);
return DOMPurify.sanitize(html);
}
private unescapeCodes(value: string) {
const el = document.createElement("div");
el.innerHTML = value;
const codes = el.getElementsByTagName('code');
for (let i = 0; i < codes.length; i++) {
codes.item(i).innerText = this.unescapeHTML(codes.item(i).innerText);
}
return el.innerHTML.toString();
}
transform(str: string): string {
if (!str || str.length == 0) return str;
str = this.escapeHTML(str);
let html = this.markdownToSafeHtml(str);
html = this.unescapeCodes(html);
return html;
}
}
我正在尝试构建一个支持 markdown 的 textarea
。我已成功将 markdown 转换为 HTML 以显示预览,使用以下管道:
import { Pipe, PipeTransform } from '@angular/core';
import * as marked from 'marked';
import * as DOMPurify from 'dompurify';
@Pipe({ name: 'markdown' })
export class MarkdownPipe implements PipeTransform {
markdownToSafeHtml(value: string): string {
const html = marked(value);
const safeHtml = DOMPurify.sanitize(html);
return safeHtml;
}
transform(str: string): string {
if (str && str.length > 0) {
const html = this.markdownToSafeHtml(str);
return html.toString();
}
return str;
}
}
以及以下 HTML:
<div [innerHTML]="value | markdown">
它正在工作并显示降价设计,但问题是我可以在降价字符串中添加任何 HTML 标签,因为我使用的是 innerHTML
div将使用它们,例如在此标签的预览中使用 <h1>hello</h1>
呈现,它应该将其呈现为文本。
- 如果没有其他 HTML 标签,我如何转换为 markdown?
- 我已经尝试过对HTML字母进行编码(例如
&
等),问题是在使用code markdown时,转换为:<div>example</div>
是<div>example</div>
使用下面的管道终于成功了。
解决方案是创建一个包含 HTML 的元素,并使用 unescapeCodes
函数反转 <code>
元素中的 HTML 转义。
import { Pipe, PipeTransform } from '@angular/core';
import * as marked from 'marked';
import * as DOMPurify from 'dompurify';
@Pipe({ name: 'markdown' })
export class MarkdownPipe implements PipeTransform {
constructor() {
}
private escapeHTML(str: string) {
return str.replace(/&/g, "&")
.replace(/</g, "<")
.replace(/>/g, ">")
.replace(/"/g, """)
.replace(/'/g, "'");
}
private unescapeHTML(str: string) {
return str.replace(/&/g, "&")
.replace(/</g, "<")
.replace(/>/g, ">")
.replace(/"/g, "\"")
.replace(/'/g, "'");
}
private markdownToSafeHtml(value: string): string {
const html = marked(value);
return DOMPurify.sanitize(html);
}
private unescapeCodes(value: string) {
const el = document.createElement("div");
el.innerHTML = value;
const codes = el.getElementsByTagName('code');
for (let i = 0; i < codes.length; i++) {
codes.item(i).innerText = this.unescapeHTML(codes.item(i).innerText);
}
return el.innerHTML.toString();
}
transform(str: string): string {
if (!str || str.length == 0) return str;
str = this.escapeHTML(str);
let html = this.markdownToSafeHtml(str);
html = this.unescapeCodes(html);
return html;
}
}