fix(incidents): batch decision token lookup
All checks were successful
Code Review / ai-code-review (push) Successful in 11s
CD Pipeline / tests (push) Successful in 1m5s
CD Pipeline / build-and-deploy (push) Successful in 3m20s
CD Pipeline / post-deploy-checks (push) Successful in 1m19s

This commit is contained in:
Your Name
2026-05-06 21:27:35 +08:00
parent 780a742110
commit edef1aa4c7
4 changed files with 60 additions and 1 deletions

View File

@@ -2953,6 +2953,52 @@ class DecisionManager:
return None
async def _find_existing_tokens_for_incidents(
self,
incident_ids: list[str],
) -> dict[str, DecisionToken]:
"""
批次查找現有決策令牌。
2026-05-06 Codex: GET /api/v1/incidents 是前端輪詢路徑,不可對每個
incident 都掃描一次 decision:*。這裡只掃一次 Redis keyspace避免
200+ incidents 時形成 O(N×M) 延遲與前端控制台卡死。
"""
wanted = set(incident_ids)
if not wanted:
return {}
import json
redis_client = get_redis()
found: dict[str, DecisionToken] = {}
cursor = 0
while True:
cursor, keys = await redis_client.scan(
cursor=cursor,
match=f"{DECISION_TOKEN_PREFIX}*",
count=500,
)
for key in keys:
try:
data = await redis_client.get(key)
if not data:
continue
token_data = json.loads(data)
incident_id = token_data.get("incident_id")
if incident_id in wanted and incident_id not in found:
found[incident_id] = DecisionToken.from_dict(token_data)
if len(found) == len(wanted):
return found
except Exception:
continue
if cursor == 0:
break
return found
async def _persist_decision_to_db(
self, incident_id: str, proposal_data: dict
) -> None: