96 lines
2.4 KiB
Python
96 lines
2.4 KiB
Python
# -*- coding: utf-8 -*-
|
|
"""
|
|
个人博客 - Flask 应用入口
|
|
"""
|
|
import os
|
|
import re
|
|
from datetime import datetime
|
|
from flask import Flask, render_template, abort
|
|
import markdown
|
|
|
|
app = Flask(__name__)
|
|
|
|
BASE_DIR = os.path.dirname(os.path.abspath(__file__))
|
|
POSTS_DIR = os.path.join(BASE_DIR, 'posts')
|
|
|
|
|
|
def parse_front_matter(text):
|
|
"""解析 Markdown 文件的 YAML front matter(简单实现)"""
|
|
meta = {}
|
|
body = text
|
|
match = re.match(r'^---\s*\n(.*?)\n---\s*\n(.*)$', text, re.DOTALL)
|
|
if match:
|
|
raw_meta, body = match.group(1), match.group(2)
|
|
for line in raw_meta.strip().splitlines():
|
|
if ':' in line:
|
|
key, value = line.split(':', 1)
|
|
meta[key.strip()] = value.strip()
|
|
return meta, body
|
|
|
|
|
|
def load_posts():
|
|
"""加载所有文章,返回按日期倒序的列表"""
|
|
posts = []
|
|
if not os.path.isdir(POSTS_DIR):
|
|
return posts
|
|
for filename in os.listdir(POSTS_DIR):
|
|
if not filename.endswith('.md'):
|
|
continue
|
|
slug = filename[:-3]
|
|
path = os.path.join(POSTS_DIR, filename)
|
|
with open(path, 'r', encoding='utf-8') as f:
|
|
raw = f.read()
|
|
meta, body = parse_front_matter(raw)
|
|
posts.append({
|
|
'slug': slug,
|
|
'title': meta.get('title', slug),
|
|
'date': meta.get('date', ''),
|
|
'summary': meta.get('summary', ''),
|
|
'content': body,
|
|
})
|
|
posts.sort(key=lambda p: p['date'], reverse=True)
|
|
return posts
|
|
|
|
|
|
def get_post(slug):
|
|
"""根据 slug 获取单篇文章"""
|
|
for post in load_posts():
|
|
if post['slug'] == slug:
|
|
return post
|
|
return None
|
|
|
|
|
|
@app.route('/')
|
|
def index():
|
|
"""首页:文章列表"""
|
|
posts = load_posts()
|
|
return render_template('index.html', posts=posts)
|
|
|
|
|
|
@app.route('/post/<slug>')
|
|
def post_detail(slug):
|
|
"""文章详情页"""
|
|
post = get_post(slug)
|
|
if not post:
|
|
abort(404)
|
|
html_content = markdown.markdown(
|
|
post['content'],
|
|
extensions=['fenced_code', 'codehilite', 'tables']
|
|
)
|
|
return render_template('post.html', post=post, content=html_content)
|
|
|
|
|
|
@app.route('/about')
|
|
def about():
|
|
"""关于页面"""
|
|
return render_template('about.html')
|
|
|
|
|
|
@app.errorhandler(404)
|
|
def not_found(e):
|
|
return render_template('404.html'), 404
|
|
|
|
|
|
if __name__ == '__main__':
|
|
app.run(debug=True, host='127.0.0.1', port=5000)
|