Archived
feat(routes): 迁移解析端点 /song /playlist /album + 响应卫生中间件
迁移路由(/api/v1/*,与 Flask 同端点逐字段对齐): - song(type: url/name/lyric/json)、playlist、album 个人账号路径实现全局账号冒用拦截(同 Flask 口径);json 模式 asyncio.gather 并发 song/url/lyric(歌词失败不阻断,与 Flask 线程池语义一致) - core/media.py:format_file_size/quality_display_name/parse_cookie_str 纯函数复用 web/middleware.py(镜像 Flask after_request): - 音频直链 → HMAC 签名代理地址(密钥同源,两栈 token 互认) - 安全头 nosniff/DENY/Referrer-Policy/CSP 基线;Server 抹为 NeteaseUrl;429 带 Retry-After - 纯 ASGI 逐段转发(不破坏流式下载);JSON 200 延迟 start 并**重算 Content-Length** ——修实测 IncompleteRead(原实现转发旧长度 + 新 body) 契约奇偶校验:12 项全 OK(新增 album/playlist/song×3); token/CDN 主机归一化(均为易变值,非契约漂移)。 验证:pytest 36/36;ruff All checks passed;pyright 0 errors; uvicorn 实跑 /api/v1/song 直链已代理、CSP/Server 头正确。
This commit is contained in:
1 parent
2c55b55e03
commit
a2758aa0da
5 files changed
+452
-8
No files matched your search
+18
@@ -18,7 +18,9 @@ from contextlib import asynccontextmanager
|
||||
from fastapi import FastAPI
|
||||
|
||||
from core.config import APP_VERSION
|
||||
from core.security import init_secret_key
|
||||
from web.errors import install_error_handlers
|
||||
from web.middleware import ResponseHygieneMiddleware
|
||||
from web.routers import music as music_router
|
||||
from web.routers import site as site_router
|
||||
from web.routers import system as system_router
|
||||
@@ -30,14 +32,27 @@ async def _lifespan(app: FastAPI):
|
||||
yield
|
||||
try:
|
||||
from core import aiohttp_compat, http_client
|
||||
|
||||
await http_client.client.close()
|
||||
await aiohttp_compat.close()
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
|
||||
def _init_audio_secret() -> None:
|
||||
"""注入音频签名密钥(与 Flask 同源,令两栈 token 互认)。"""
|
||||
try:
|
||||
import auth_system
|
||||
|
||||
init_secret_key(auth_system.get_secret_key())
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
|
||||
def create_app(serve_flask_fallback: bool = False) -> FastAPI:
|
||||
"""创建 FastAPI 应用。"""
|
||||
_init_audio_secret()
|
||||
|
||||
app = FastAPI(
|
||||
title='云村小助手API服务',
|
||||
version=APP_VERSION,
|
||||
@@ -47,6 +62,9 @@ def create_app(serve_flask_fallback: bool = False) -> FastAPI:
|
||||
lifespan=_lifespan,
|
||||
)
|
||||
|
||||
# 响应侧统一处理:安全头 + 音频直链签名保护 + 版本指纹抹除
|
||||
app.add_middleware(ResponseHygieneMiddleware)
|
||||
|
||||
# 已迁移路由:统一挂 /api/v1(迁移期与 Flask 根路径并存,便于对比)
|
||||
app.include_router(system_router.router, prefix='/api/v1', tags=['system'])
|
||||
app.include_router(site_router.router, prefix='/api/v1', tags=['site'])
|
||||
|
||||
Reference in new issue
Block a user