feat: render markdown in posts and comments

This commit is contained in:
Tim
2025-07-04 15:59:57 +08:00
parent c6c34b201a
commit cdc9b412fe
5 changed files with 104 additions and 37 deletions

View File

@@ -9,6 +9,7 @@
"version": "0.1.0",
"dependencies": {
"core-js": "^3.8.3",
"markdown-it": "^14.1.0",
"vditor": "^3.8.7",
"vue": "^3.2.13",
"vue-router": "^4.5.1"
@@ -7507,6 +7508,15 @@
"dev": true,
"license": "MIT"
},
"node_modules/linkify-it": {
"version": "5.0.0",
"resolved": "https://registry.npmjs.org/linkify-it/-/linkify-it-5.0.0.tgz",
"integrity": "sha512-5aHCbzQRADcdP+ATqnDuhhJ/MRIqDkZX5pyjFHRRysS8vZ5AbqGEoFIb6pYHPZ+L/OC2Lc+xT8uHVVR5CAK/wQ==",
"license": "MIT",
"dependencies": {
"uc.micro": "^2.0.0"
}
},
"node_modules/loader-runner": {
"version": "4.3.0",
"resolved": "https://registry.npmmirror.com/loader-runner/-/loader-runner-4.3.0.tgz",
@@ -7826,6 +7836,29 @@
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/markdown-it": {
"version": "14.1.0",
"resolved": "https://registry.npmjs.org/markdown-it/-/markdown-it-14.1.0.tgz",
"integrity": "sha512-a54IwgWPaeBCAAsv13YgmALOF1elABB08FxO9i+r4VFk5Vl4pKokRPeX8u5TCgSsPi6ec1otfLjdOpVcgbpshg==",
"license": "MIT",
"dependencies": {
"argparse": "^2.0.1",
"entities": "^4.4.0",
"linkify-it": "^5.0.0",
"mdurl": "^2.0.0",
"punycode.js": "^2.3.1",
"uc.micro": "^2.1.0"
},
"bin": {
"markdown-it": "bin/markdown-it.mjs"
}
},
"node_modules/markdown-it/node_modules/argparse": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz",
"integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==",
"license": "Python-2.0"
},
"node_modules/math-intrinsics": {
"version": "1.1.0",
"resolved": "https://registry.npmmirror.com/math-intrinsics/-/math-intrinsics-1.1.0.tgz",
@@ -7843,6 +7876,12 @@
"dev": true,
"license": "CC0-1.0"
},
"node_modules/mdurl": {
"version": "2.0.0",
"resolved": "https://registry.npmjs.org/mdurl/-/mdurl-2.0.0.tgz",
"integrity": "sha512-Lf+9+2r+Tdp5wXDXC4PcIBjTDtq4UKjCPMQhKIuzpJNW0b96kVqSwW0bT7FhRSfmAiFYgP+SCRvdrDozfh0U5w==",
"license": "MIT"
},
"node_modules/media-typer": {
"version": "0.3.0",
"resolved": "https://registry.npmmirror.com/media-typer/-/media-typer-0.3.0.tgz",
@@ -9580,6 +9619,15 @@
"node": ">=6"
}
},
"node_modules/punycode.js": {
"version": "2.3.1",
"resolved": "https://registry.npmjs.org/punycode.js/-/punycode.js-2.3.1.tgz",
"integrity": "sha512-uxFIHU0YlHYhDQtV4R9J6a52SLx28BCjT+4ieh7IGbgwVJWO+km431c4yRlREUAsAmt/uMjQUyQHNEPf0M39CA==",
"license": "MIT",
"engines": {
"node": ">=6"
}
},
"node_modules/qs": {
"version": "6.13.0",
"resolved": "https://registry.npmmirror.com/qs/-/qs-6.13.0.tgz",
@@ -11074,6 +11122,12 @@
"node": ">= 0.6"
}
},
"node_modules/uc.micro": {
"version": "2.1.0",
"resolved": "https://registry.npmjs.org/uc.micro/-/uc.micro-2.1.0.tgz",
"integrity": "sha512-ARDJmphmdvUk6Glw7y9DQ2bFkKBHwQHLi2lsaH6PPmz/Ka9sFOBsBluozhDltWmnv9u/cF6Rt87znRTPV+yp/A==",
"license": "MIT"
},
"node_modules/undici-types": {
"version": "7.8.0",
"resolved": "https://registry.npmmirror.com/undici-types/-/undici-types-7.8.0.tgz",

View File

@@ -9,6 +9,7 @@
},
"dependencies": {
"core-js": "^3.8.3",
"markdown-it": "^14.1.0",
"vditor": "^3.8.7",
"vue": "^3.2.13",
"vue-router": "^4.5.1"

View File

@@ -15,9 +15,7 @@
<div class="user-name">{{ comment.userName }}</div>
<div class="post-time">{{ comment.time }}</div>
</div>
<div class="info-content-text">
{{ comment.text }}
</div>
<div class="info-content-text" v-html="renderMarkdown(comment.text)"></div>
<div class="article-footer-container">
<div class="reactions-container">
<div class="reactions-viewer">
@@ -60,6 +58,7 @@
<script>
import { ref } from 'vue'
import CommentEditor from './CommentEditor.vue'
import { renderMarkdown } from '../utils/markdown'
const CommentItem = {
name: 'CommentItem',
props: {
@@ -94,7 +93,7 @@ const CommentItem = {
})
showEditor.value = false
}
return { showReplies, toggleReplies, showEditor, toggleEditor, submitReply }
return { showReplies, toggleReplies, showEditor, toggleEditor, submitReply, renderMarkdown }
}
}
CommentItem.components = { CommentItem, CommentEditor }

View File

@@ -0,0 +1,11 @@
import MarkdownIt from 'markdown-it'
const md = new MarkdownIt({
html: false,
linkify: true,
breaks: true
})
export function renderMarkdown(text) {
return md.render(text || '')
}

View File

@@ -30,38 +30,7 @@
<div class="user-name">Nagisa77</div>
<div class="post-time">{{ postTime }}</div>
</div>
<div class="info-content-text">
# 📢 社区公告
是的L 站目前每天都有不少各色各样的佬友加入对于一个在线社区来说 断壮大和涌入新的血液是一件好事
但我每天都要问问自己**这里面有没有问题真的完全是好事吗**
在这个过程中我嗅到了一丝危险的气息有人试图**同质化**这里把这里当作互联网上**另一个可以随意发泄情绪**的地方甚至试图占领舆论高地把这里堂而皇之地变成**另一个垃圾场**
> 这是要万分警惕并坚决予以打击的
L 站的愿景是成为新的**理想型社区**让每一个一身疲惫的佬友在这里得到放松哪怕只有一刻能放松手中攥紧的武器徜徉在和谐的氛围中得到喘息与治愈
我和管理团队始终**坚定这一点丝毫不会放松**
千里之堤溃于蚁穴如果任由戾气蔓延争端四起最终这里的愿景将会完全破产**有病要医不是同路人不必强行融合**任何把戾气带来这里试图在此建立另一个互联网垃圾场的人**都是不受欢迎的都要被驱逐出社区**
请好好说话友善交流我们完全支持并鼓励友好交流与分享每个人都可以**键盘**是你与人沟通互通有无的桥梁不只是你谋取私利的工具更不是肆意挥舞用来攻击的武器
---
## 🚫 自本公告发布之日起我们将严肃处理以下 3 类发言
1. **傲慢轻蔑回复**
2. **阴阳怪气回复**
3. **攻击谩骂回复**
如有以上发言我们将视言论破坏程度采取但不限于**删帖临时封禁永久封禁**等举措
> 请各位佬友积极监督感谢你们为共建美好社区做出的贡献
> **请一定一定不要把互联网上的戾气带来这里这里就要做不一样**
**持续时间** *直至最后一个不会好好说话的账号持有者被请出社区为止*
</div>
<div class="info-content-text" v-html="renderMarkdown(postContent)"></div>
<div class="article-footer-container">
<div class="reactions-container">
@@ -118,11 +87,42 @@
import { ref, computed, onMounted } from 'vue'
import CommentItem from '../components/CommentItem.vue'
import CommentEditor from '../components/CommentEditor.vue'
import { renderMarkdown } from '../utils/markdown'
export default {
name: 'PostPageView',
components: { CommentItem, CommentEditor },
setup() {
const postContent = ref(`# 📢 社区公告
是的L 站目前每天都有不少各色各样的佬友加入。对于一个在线社区来说,不断壮大和涌入新的血液是一件好事。
但我每天都要问问自己:**这里面有没有问题?真的完全是好事吗?**
在这个过程中我嗅到了一丝危险的气息——有人试图**同质化**这里,把这里当作互联网上**另一个可以随意发泄情绪**的地方!甚至试图占领舆论高地,把这里堂而皇之地变成**另一个垃圾场**。
> 这是要万分警惕并坚决予以打击的!
L 站的愿景是成为新的**理想型社区**,让每一个一身疲惫的佬友在这里得到放松。哪怕只有一刻能放松手中攥紧的武器,徜徉在和谐的氛围中得到喘息与治愈。
我和管理团队始终**坚定这一点,丝毫不会放松**
千里之堤,溃于蚁穴——如果任由戾气蔓延、争端四起,最终这里的愿景将会完全破产。**有病要医,不是同路人不必强行融合。**任何把戾气带来这里、试图在此建立另一个互联网垃圾场的人,**都是不受欢迎的,都要被驱逐出社区。**
请好好说话,友善交流!我们完全支持并鼓励友好交流与分享,每个人都可以。**键盘**是你与人沟通、互通有无的桥梁,不只是你谋取私利的工具,更不是肆意挥舞用来攻击的武器。
---
## 🚫 自本公告发布之日起,我们将严肃处理以下 3 类发言:
1. **傲慢轻蔑回复**
2. **阴阳怪气回复**
3. **攻击谩骂回复**
如有以上发言,我们将视言论破坏程度采取(但不限于)**删帖、临时封禁、永久封禁**等举措。
> 请各位佬友积极监督,感谢你们为共建美好社区做出的贡献!
> **请一定一定不要把互联网上的戾气带来这里,这里就要做不一样。**
**持续时间:** *直至最后一个不会好好说话的账号持有者被请出社区为止。*`)
const tags = ref(['AI', 'Python', 'Java'])
const comments = ref([
{
@@ -241,6 +241,7 @@ export default {
})
return {
postContent,
tags,
comments,
postTime,
@@ -251,7 +252,8 @@ export default {
totalPosts,
postComment,
onSliderInput,
onScroll: updateCurrentIndex
onScroll: updateCurrentIndex,
renderMarkdown
}
}
}