MVP: 按 07 风格重写前端 + Go 后端落地(长文/短文、编辑器、后台管理)

This commit is contained in:
Sakurasan
2026-09-20 20:56:03 +08:00
parent edee708802
commit 4d8f2de3a4
96 changed files with 6005 additions and 2602 deletions
+159
View File
@@ -0,0 +1,159 @@
<script setup>
import { site } from '../site'
import { publicApi } from '../api'
import { onMounted, ref } from 'vue'
const tags = ref([])
onMounted(async () => {
try {
const data = await publicApi.tags()
tags.value = (data.tags || []).slice(0, 8)
} catch (e) {
tags.value = []
}
})
</script>
<template>
<aside class="rail-left">
<div class="inner">
<RouterLink to="/" class="brand">
<span class="mark">○</span>
<span class="name">{{ site.site_title || 'ONE' }}</span>
</RouterLink>
<p class="desc">{{ site.site_desc }}</p>
<nav class="nav">
<RouterLink to="/" class="item">
<span class="ico">◴</span><span>时间线</span>
</RouterLink>
<RouterLink to="/archive" class="item">
<span class="ico">▤</span><span>归档</span>
</RouterLink>
<RouterLink to="/tags" class="item">
<span class="ico">#</span><span>标签</span>
</RouterLink>
<RouterLink to="/about" class="item">
<span class="ico">◍</span><span>关于</span>
</RouterLink>
</nav>
<a class="subscribe" href="/rss.xml">订阅 RSS</a>
<div v-if="tags.length" class="tagbox">
<p class="eyebrow">常读标签</p>
<div class="tags">
<RouterLink v-for="t in tags" :key="t.id" :to="`/tag/${t.slug}`" class="tag-chip">
{{ t.name }}
</RouterLink>
</div>
</div>
</div>
</aside>
</template>
<style scoped>
.rail-left {
position: sticky;
top: 0;
align-self: start;
padding: 28px 0 40px;
}
.inner {
display: flex;
flex-direction: column;
gap: 16px;
}
.brand {
display: flex;
align-items: center;
gap: 8px;
}
.mark {
color: var(--accent);
font-size: 18px;
}
.name {
font-family: var(--serif);
font-size: 21px;
letter-spacing: 0.02em;
}
.desc {
margin: -6px 0 0;
font-size: 13px;
line-height: 1.75;
color: var(--muted);
}
.nav {
display: flex;
flex-direction: column;
gap: 2px;
margin-top: 4px;
}
.item {
display: flex;
align-items: center;
gap: 10px;
padding: 7px 10px;
margin-left: -10px;
border-radius: 3px;
font-size: 15px;
color: var(--ink-soft);
}
.item:hover {
background: var(--paper-sunken);
color: var(--ink);
}
.item.router-link-exact-active {
color: var(--accent);
font-weight: 500;
}
.ico {
width: 16px;
text-align: center;
color: var(--faint);
font-size: 13px;
}
.item.router-link-exact-active .ico {
color: var(--accent);
}
.subscribe {
align-self: flex-start;
padding: 7px 20px;
border-radius: 999px;
background: var(--accent);
color: #fff;
font-size: 14px;
border: 1px solid var(--accent);
}
.subscribe:hover {
background: #356f88;
color: #fff;
}
.tagbox {
border-top: 1px solid var(--line);
padding-top: 14px;
}
.tags {
display: flex;
flex-wrap: wrap;
gap: 6px;
margin-top: 8px;
}
</style>