From a0143e805f3b33a3af1c89d816296cd584c8523a Mon Sep 17 00:00:00 2001 From: Cccc_ Date: Mon, 5 Jan 2026 23:18:19 +0800 Subject: [PATCH] =?UTF-8?q?perf(admin):=20optimize=20token=20expiry=20quer?= =?UTF-8?q?y=20in=20stats=20endpoint=20Replace=20N+1=20loop=20with=20SQL-l?= =?UTF-8?q?evel=20filtering=20using=20cast=20and=20and=5F=20operators=20to?= =?UTF-8?q?=20count=20users=20with=20expiring=20tokens.=20Performance=20im?= =?UTF-8?q?provement:=20O(N)=20=E2=86=92=20O(1).?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- backend/api/admin.py | 24 ++++++++++++++---------- 1 file changed, 14 insertions(+), 10 deletions(-) diff --git a/backend/api/admin.py b/backend/api/admin.py index 5e66667..1565d85 100644 --- a/backend/api/admin.py +++ b/backend/api/admin.py @@ -188,20 +188,24 @@ async def get_system_stats( ).count() # Token 即将过期的用户数(7天内) - from backend.services.auth_service import AuthService - + # 使用 SQL 直接查询,避免 N+1 问题 current_timestamp = int(datetime.now().timestamp()) expiring_soon_timestamp = current_timestamp + (7 * 24 * 60 * 60) # 7天后 - expiring_users = 0 - for user in db.query(User).all(): - # 使用统一的验证方法 - result = AuthService.verify_checkin_authorization(user) + # 直接在数据库层面筛选即将过期的用户 + # 条件:authorization 不为空、jwt_exp 不为 "0"、且在未来 7 天内过期 + from sqlalchemy import cast, Integer, and_ - if result["is_valid"]: - exp_timestamp = result.get("expires_at") - if exp_timestamp and current_timestamp < exp_timestamp < expiring_soon_timestamp: - expiring_users += 1 + expiring_users = db.query(User).filter( + and_( + User.authorization.isnot(None), + User.authorization != "", + User.jwt_exp.isnot(None), + User.jwt_exp != "0", + cast(User.jwt_exp, Integer) > current_timestamp, # 未过期 + cast(User.jwt_exp, Integer) < expiring_soon_timestamp # 7天内过期 + ) + ).count() return { "users": {