fix: 修复邮件Token时间解析错误
问题:数据库中的时间戳包含微秒(如 2025-12-11 14:31:20.307257), 但代码使用 '%Y-%m-%d %H:%M:%S' 格式解析会报错。 解决:添加 parse_datetime() 函数,支持带微秒和不带微秒两种格式。 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
@@ -33,6 +33,24 @@ import db_pool
|
|||||||
from crypto_utils import encrypt_password, decrypt_password, is_encrypted
|
from crypto_utils import encrypt_password, decrypt_password, is_encrypted
|
||||||
|
|
||||||
|
|
||||||
|
def parse_datetime(dt_str: str) -> datetime:
|
||||||
|
"""解析数据库中的时间字符串,支持带微秒和不带微秒的格式"""
|
||||||
|
if not dt_str:
|
||||||
|
return datetime.min
|
||||||
|
# 尝试多种格式
|
||||||
|
formats = [
|
||||||
|
'%Y-%m-%d %H:%M:%S.%f', # 带微秒
|
||||||
|
'%Y-%m-%d %H:%M:%S', # 不带微秒
|
||||||
|
]
|
||||||
|
for fmt in formats:
|
||||||
|
try:
|
||||||
|
return datetime.strptime(dt_str, fmt)
|
||||||
|
except ValueError:
|
||||||
|
continue
|
||||||
|
# 如果都失败,返回最小时间(视为过期)
|
||||||
|
return datetime.min
|
||||||
|
|
||||||
|
|
||||||
# ============ 常量配置 ============
|
# ============ 常量配置 ============
|
||||||
|
|
||||||
# 邮件类型
|
# 邮件类型
|
||||||
@@ -1062,7 +1080,7 @@ def verify_email_token(token: str, token_type: str) -> Optional[Dict[str, Any]]:
|
|||||||
return None
|
return None
|
||||||
|
|
||||||
# 检查是否过期
|
# 检查是否过期
|
||||||
if datetime.strptime(expires_at, '%Y-%m-%d %H:%M:%S') < datetime.now():
|
if parse_datetime(expires_at) < datetime.now():
|
||||||
return None
|
return None
|
||||||
|
|
||||||
# 标记为已使用
|
# 标记为已使用
|
||||||
@@ -1100,7 +1118,7 @@ def check_rate_limit(email: str, token_type: str) -> bool:
|
|||||||
if not row:
|
if not row:
|
||||||
return True
|
return True
|
||||||
|
|
||||||
last_sent = datetime.strptime(row[0], '%Y-%m-%d %H:%M:%S')
|
last_sent = parse_datetime(row[0])
|
||||||
elapsed = (datetime.now() - last_sent).total_seconds()
|
elapsed = (datetime.now() - last_sent).total_seconds()
|
||||||
|
|
||||||
return elapsed >= limit_seconds
|
return elapsed >= limit_seconds
|
||||||
@@ -1376,7 +1394,7 @@ def verify_password_reset_token(token: str) -> Optional[Dict[str, Any]]:
|
|||||||
return None
|
return None
|
||||||
|
|
||||||
# 检查是否过期
|
# 检查是否过期
|
||||||
if datetime.strptime(expires_at, '%Y-%m-%d %H:%M:%S') < datetime.now():
|
if parse_datetime(expires_at) < datetime.now():
|
||||||
return None
|
return None
|
||||||
|
|
||||||
return {'user_id': user_id, 'email': email, 'token_id': token_id}
|
return {'user_id': user_id, 'email': email, 'token_id': token_id}
|
||||||
|
|||||||
Reference in New Issue
Block a user