fix: stabilize idempotent decorator cache key

This commit is contained in:
caoqianming 2026-03-19 21:55:09 +08:00
parent fbe12249f8
commit 71e91efe29
1 changed files with 13 additions and 7 deletions

View File

@ -2,6 +2,7 @@ import logging
from functools import wraps from functools import wraps
from apps.utils.tasks import send_mail_task from apps.utils.tasks import send_mail_task
import traceback import traceback
import hashlib
import json import json
from django.core.cache import cache from django.core.cache import cache
from rest_framework.exceptions import ParseError from rest_framework.exceptions import ParseError
@ -30,18 +31,23 @@ def idempotent(seconds=4):
def decorate(func): def decorate(func):
@wraps(func) @wraps(func)
def wrapper(*args, **kwargs): def wrapper(*args, **kwargs):
rdata = args[1].data request = args[1]
rdata['request_userid'] = getattr(args[1], 'user').id rdata = dict(request.data)
rdata['request_path'] = getattr(args[1], 'path') rdata['request_userid'] = getattr(request, 'user').id
hash_k = hash(json.dumps(rdata)) rdata['request_path'] = getattr(request, 'path')
payload = json.dumps(rdata, sort_keys=True, ensure_ascii=False, default=str)
hash_k = hashlib.sha256(payload.encode('utf-8')).hexdigest()
hash_v_e = cache.get(hash_k, None) hash_v_e = cache.get(hash_k, None)
if hash_v_e is None: if hash_v_e is None:
cache.set(hash_k, 'o', seconds) cache.set(hash_k, 'o', seconds)
real_func = func(*args, **kwargs) real_func = func(*args, **kwargs)
# real_func.render() if hasattr(real_func, 'data'):
# cache.set(hash_k, real_func, seconds) cache.set(hash_k, real_func.data, seconds)
else:
cache.delete(hash_k)
return real_func return real_func
elif hash_v_e == 'o': # 说明请求正在处理 elif hash_v_e == 'o': # 说明请求正在处理
raise ParseError(f'请求忽略,请{seconds}秒后重试') raise ParseError(f'请求忽略,请{seconds}秒后重试')
return hash_v_e
return wrapper return wrapper
return decorate return decorate