feat: 热点穿透题材数从50提升到100,支持缓存定向清理

- 热点穿透top由50提升到100(涨幅榜+热度榜各取前100合并),保证题材数≥100
- themes.py graph路由top上限le由60放宽到200
- daily_collector HOTMAP_TOP_N同步到100与页面一致
- auvops.sh新增cache-clear-graph子命令定向清理theme_graph缓存
This commit is contained in:
Sakurasan
2026-08-18 04:14:17 +08:00
parent 48522cbfea
commit bb2be17ae2
5 changed files with 23 additions and 5 deletions
+18
View File
@@ -6,6 +6,7 @@
#
# 用法(容器内):
# ./auvops.sh cache-clear # 清空全部缓存(当日数据全新)
# ./auvops.sh cache-clear-graph # 只清空热点穿透(theme_graph)缓存
# ./auvops.sh clean-expired # 只清理已过期的缓存
# ./auvops.sh cache-count # 查看缓存条数
# ./auvops.sh recollect [DATE] # 删除并重采指定交易日(默认当天)
@@ -57,6 +58,22 @@ EOF
echo "✅ 缓存已清空"
}
# 仅清空热点穿透(theme_graph)缓存:改写 top/排序后旧图数据过期,删掉让下次请求重建
cmd_cache_clear_graph() {
echo "① 清空热点穿透(theme_graph)缓存"
"${PY}" - <<'EOF'
from database import get_connection
conn = get_connection()
try:
cur = conn.execute("DELETE FROM cache WHERE key LIKE 'theme_graph:%'")
conn.commit()
print(f" 已删除 {cur.rowcount} 条 theme_graph 缓存")
finally:
conn.close()
EOF
echo "✅ 热点穿透缓存已清空"
}
# 只清理已过期缓存
cmd_clean_expired() {
echo "① 清理过期缓存"
@@ -138,6 +155,7 @@ main() {
local cmd="$1"; shift
case "${cmd}" in
cache-clear|cc) cmd_cache_clear "$@" ;;
cache-clear-graph) cmd_cache_clear_graph "$@" ;;
clean-expired) cmd_clean_expired "$@" ;;
cache-count) cmd_cache_count "$@" ;;
recollect) cmd_recollect "$@" ;;
+1 -1
View File
@@ -29,7 +29,7 @@ async def theme_list(
@router.get("/graph", summary="热点穿透:题材-股票网状关系图")
async def theme_graph(
sort_field: int = Query(1, description="题材排序:1=涨幅 4=热度"),
top: int = Query(30, ge=1, le=60, description="题材数量"),
top: int = Query(30, ge=1, le=200, description="题材数量"),
limit: int = Query(1000, ge=100, le=2000, description="下发的股票节点上限(按穿透度取前 N 只)"),
):
if sort_field not in (1, 4):
+1 -1
View File
@@ -19,7 +19,7 @@ CHECK_INTERVAL_SECONDS = 300
COLLECT_AFTER_TIME = dtime(15, 1) # 收盘后 15:01 开始允许采集(留 1 分钟等收盘数据稳定)
CORE_STOCK_LIMIT = 100 # 题材领涨股涨幅前100
TOP_THEME_LIMIT = 20 # 题材涨幅前20
HOTMAP_TOP_N = 50 # 热点穿透采样题材数:涨幅榜+热度榜各取前50,合并(与热点穿透页一致)
HOTMAP_TOP_N = 100 # 热点穿透采样题材数:涨幅榜+热度榜各取前100,合并(与热点穿透页一致)
HOTMAP_CORE_LIMIT = 100 # 热点穿透核心股前100(按覆盖题材数降序)
CORE_COVER_THRESHOLD = 2 # 热点穿透核心股门槛:覆盖题材数 ≥2
+2 -2
View File
@@ -308,7 +308,7 @@ async def _build_theme_graph(sort_field: int, top_n: int) -> dict:
Args:
sort_field: 题材排序 1=涨幅, 4=热度(当前榜在前,另一榜合并补充)
top_n: 每个榜单的题材数量(1-60)
top_n: 每个榜单的题材数量(1-200)
Returns:
{
@@ -422,7 +422,7 @@ async def fetch_theme_graph(sort_field: int = 1, top_n: int = 30, limit: int = 1
Args:
sort_field: 题材排序 1=涨幅, 4=热度
top_n: 每个榜单的题材数量(1-60)
top_n: 每个榜单的题材数量(1-200)
limit: 下发 stocks 上限(穿透度最高的 N 只)
"""
cache_key = f"theme_graph:{sort_field}:{top_n}"
+1 -1
View File
@@ -52,7 +52,7 @@ function HotMapPage() {
const { data: graph, isLoading, isFetching, isError, refetch } = useQuery({
queryKey: ["themeGraph", mode],
queryFn: () => fetchThemeGraph(mode, 50),
queryFn: () => fetchThemeGraph(mode, 100),
staleTime: 60_000,
retry: false,
});