fix: 修复 JSON 解析中正则贪婪匹配导致的数组截断问题 (#126)

- 将解析 JSON 数组的正则模式从非贪婪 `.*?` 改为贪婪匹配 `.*`,防止内容中包含方括号(如 [UID])时导致 JSON 截断。
- 优化话题、称号、金句等分析逻辑中的正则表达式,使用更严谨的模式处理转义双引号和特殊格式。
This commit is contained in:
SXP-Simon
2026-03-25 16:15:51 +08:00
parent 72ead04182
commit 82c5cc4cef
@@ -97,7 +97,7 @@ def parse_json_response(
fixed_json_text = None fixed_json_text = None
try: try:
# 1. 提取JSON部分 # 1. 提取JSON部分
json_match = re.search(r"\[.*?\]", result_text, re.DOTALL) json_match = re.search(r"\[.*\]", result_text, re.DOTALL)
if not json_match: if not json_match:
error_msg = f"{data_type}响应中未找到JSON格式" error_msg = f"{data_type}响应中未找到JSON格式"
logger.warning(error_msg) logger.warning(error_msg)
@@ -220,12 +220,12 @@ def extract_topics_with_regex(result_text: str, max_topics: int) -> list[dict]:
try: try:
# 更强的正则表达式提取话题信息,处理转义字符 # 更强的正则表达式提取话题信息,处理转义字符
# 匹配每个完整的话题对象 # 匹配每个完整的话题对象
topic_pattern = r'\{\s*"topic":\s*"([^"]+)"\s*,\s*"contributors":\s*\[([^\]]+)\]\s*,\s*"detail":\s*"([^"]*(?:\\.[^"]*)*)"\s*\}' topic_pattern = r'\{\s*"topic":\s*"([^"]*(?:\\.[^"]*)*)"\s*,\s*"contributors":\s*\[(.*?)\],?\s*"detail":\s*"([^"]*(?:\\.[^"]*)*)"\s*\}'
matches = re.findall(topic_pattern, result_text, re.DOTALL) matches = re.findall(topic_pattern, result_text, re.DOTALL)
if not matches: if not matches:
# 尝试更宽松的匹配 # 尝试更宽松的匹配
topic_pattern = r'"topic":\s*"([^"]+)"[^}]*"contributors":\s*\[([^\]]+)\][^}]*"detail":\s*"([^"]*(?:\\.[^"]*)*)"' topic_pattern = r'"topic":\s*"([^"]*(?:\\.[^"]*)*)"[^}]*"contributors":\s*\[(.*?)\][^}]*"detail":\s*"([^"]*(?:\\.[^"]*)*)"'
matches = re.findall(topic_pattern, result_text, re.DOTALL) matches = re.findall(topic_pattern, result_text, re.DOTALL)
topics = [] topics = []
@@ -274,12 +274,12 @@ def extract_user_titles_with_regex(result_text: str, max_count: int) -> list[dic
titles = [] titles = []
# 正则模式:匹配完整的用户称号对象 # 正则模式:匹配完整的用户称号对象
pattern = r'\{\s*"name":\s*"([^"]+)"\s*,\s*"user_id":\s*"([^"]+)"\s*,\s*"title":\s*"([^"]+)"\s*,\s*"mbti":\s*"([^"]+)"\s*,\s*"reason":\s*"([^"]*(?:\\.[^"]*)*)"\s*\}' pattern = r'\{\s*"name":\s*"([^"]*(?:\\.[^"]*)*)"\s*,\s*"user_id":\s*"([^"]+)"\s*,\s*"title":\s*"([^"]*(?:\\.[^"]*)*)"\s*,\s*"mbti":\s*"([^"]+)"\s*,\s*"reason":\s*"([^"]*(?:\\.[^"]*)*)"\s*\}'
matches = re.findall(pattern, result_text, re.DOTALL) matches = re.findall(pattern, result_text, re.DOTALL)
if not matches: if not matches:
# 尝试更宽松的匹配(字段顺序可变) # 尝试更宽松的匹配(字段顺序可变)
pattern = r'"name":\s*"([^"]+)"[^}]*"user_id":\s*"([^"]+)"[^}]*"title":\s*"([^"]+)"[^}]*"mbti":\s*"([^"]+)"[^}]*"reason":\s*"([^"]*(?:\\.[^"]*)*)"' pattern = r'"name":\s*"([^"]*(?:\\.[^"]*)*)"[^}]*"user_id":\s*"([^"]+)"[^}]*"title":\s*"([^"]*(?:\\.[^"]*)*)"[^}]*"mbti":\s*"([^"]+)"[^}]*"reason":\s*"([^"]*(?:\\.[^"]*)*)"'
matches = re.findall(pattern, result_text, re.DOTALL) matches = re.findall(pattern, result_text, re.DOTALL)
for match in matches[:max_count]: for match in matches[:max_count]:
@@ -325,12 +325,12 @@ def extract_golden_quotes_with_regex(result_text: str, max_count: int) -> list[d
quotes = [] quotes = []
# 正则模式:匹配完整的金句对象 # 正则模式:匹配完整的金句对象
pattern = r'\{\s*"content":\s*"([^"]*(?:\\.[^"]*)*)"\s*,\s*"sender":\s*"([^"]+)"\s*,\s*"reason":\s*"([^"]*(?:\\.[^"]*)*)"\s*\}' pattern = r'\{\s*"content":\s*"([^"]*(?:\\.[^"]*)*)"\s*,\s*"sender":\s*"([^"]*(?:\\.[^"]*)*)"\s*,\s*"reason":\s*"([^"]*(?:\\.[^"]*)*)"\s*\}'
matches = re.findall(pattern, result_text, re.DOTALL) matches = re.findall(pattern, result_text, re.DOTALL)
if not matches: if not matches:
# 尝试更宽松的匹配(字段顺序可变) # 尝试更宽松的匹配(字段顺序可变)
pattern = r'"content":\s*"([^"]*(?:\\.[^"]*)*)"[^}]*"sender":\s*"([^"]+)"[^}]*"reason":\s*"([^"]*(?:\\.[^"]*)*)"' pattern = r'"content":\s*"([^"]*(?:\\.[^"]*)*)"[^}]*"sender":\s*"([^"]*(?:\\.[^"]*)*)"[^}]*"reason":\s*"([^"]*(?:\\.[^"]*)*)"'
matches = re.findall(pattern, result_text, re.DOTALL) matches = re.findall(pattern, result_text, re.DOTALL)
for match in matches[:max_count]: for match in matches[:max_count]:
@@ -372,7 +372,7 @@ def extract_quality_with_regex(result_text: str) -> dict | None:
summary_m = re.search(r'"summary"\s*:\s*"([^"]*(?:\\.[^"]*)*)"', result_text) summary_m = re.search(r'"summary"\s*:\s*"([^"]*(?:\\.[^"]*)*)"', result_text)
# Extract dimensions array # Extract dimensions array
dims_match = re.search(r'"dimensions"\s*:\s*\[(.*?)\]', result_text, re.DOTALL) dims_match = re.search(r'"dimensions"\s*:\s*\[(.*)\]', result_text, re.DOTALL)
dims = [] dims = []
if dims_match: if dims_match:
dim_objects = re.findall( dim_objects = re.findall(