feat(admin): 用户排行榜每日快照——手动刷新当天 + 凌晨自动定稿前一天
- 新增 POST /api/admin/users/leaderboard/refresh-today:同步强制重建当天快照 并返回合并区间;前端 useRefreshTodayLeaderboard + AdminUserLeaderboardPage 「刷新当天」按钮 - Gateway 调度循环在每日 ADMIN_LEADERBOARD_FINALIZE_HOUR(默认凌晨1点)对前一天 强制重算一次,避免临近午夜落库的 runs/tool-calls 漏统计;判定逻辑下沉为纯函数 deerflow.persistence.admin_stats.finalize.should_finalize_previous_day - 新增 scripts/sql/column_additions_mysql.sql:既有 MySQL 库手动补列的幂等脚本 (Alembic 自动迁移已禁用,create_all 不改既有表) - CLAUDE.md 补充排行榜快照、Schema 迁移约定,并补齐技能/知识库选模型的文档 Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
1 parent
96e0d695c0
commit
d61aa853f1
8 files changed
+356
-3
No files matched your search
@@ -9,6 +9,7 @@ import {
|
||||
getUserMemory,
|
||||
getUserAnalytics,
|
||||
getUserLeaderboard,
|
||||
refreshTodayLeaderboard,
|
||||
listUserQa,
|
||||
listUserThreadMessages,
|
||||
listUserThreads,
|
||||
@@ -41,6 +42,36 @@ export function useUserLeaderboard(
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Force-rebuild today's snapshot, then prime + invalidate the matching
|
||||
* leaderboard query so the page shows the freshly recomputed numbers.
|
||||
*/
|
||||
export function useRefreshTodayLeaderboard() {
|
||||
const qc = useQueryClient();
|
||||
return useMutation({
|
||||
mutationFn: ({
|
||||
range,
|
||||
limit = 20,
|
||||
}: {
|
||||
range: { since: string; until: string; days?: number };
|
||||
limit?: number;
|
||||
}) => refreshTodayLeaderboard(range, limit),
|
||||
onSuccess: (data, variables) => {
|
||||
qc.setQueryData(
|
||||
[
|
||||
"admin-activity",
|
||||
"leaderboard",
|
||||
variables.range.since,
|
||||
variables.range.until,
|
||||
variables.limit ?? 20,
|
||||
],
|
||||
data,
|
||||
);
|
||||
qc.invalidateQueries({ queryKey: ["admin-activity", "leaderboard"] });
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
export function useUserAnalytics(
|
||||
userId: string | null,
|
||||
range: { since: string; until: string; days?: number },
|
||||
|
||||
Reference in new issue
Block a user