diff --git a/pyproject.toml b/pyproject.toml index 0d3d7ddb..97b7f18b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -62,6 +62,7 @@ dependencies = [ "aiofiles>=24.1.0", "aiohttp>=3.9.0", "deepagents>=0.2.5", + "json-repair>=0.54.0", ] [tool.ruff] line-length = 120 # 代码最大行宽 diff --git a/src/services/evaluation_service.py b/src/services/evaluation_service.py index 29c9aaa4..fdb01b3a 100644 --- a/src/services/evaluation_service.py +++ b/src/services/evaluation_service.py @@ -287,7 +287,9 @@ class EvaluationService: await context.set_progress(25, "生成样本") with open(data_file_path, "w", encoding="utf-8") as f: - while generated < count and attempts < count * 2: + # Allow more attempts to generate enough questions + max_attempts = max(count * 5, 50) + while generated < count and attempts < max_attempts: attempts += 1 i0 = random.randrange(len(all_chunks)) e0 = embeddings[i0] @@ -320,20 +322,27 @@ class EvaluationService: try: resp = await asyncio.to_thread(llm.call, prompt, False) content = resp.content if resp else "" - obj = json.loads(content) + + import json_repair + obj = json_repair.loads(content) q = obj.get("query") a = obj.get("gold_answer") gids = obj.get("gold_chunk_ids") if not q or not a or not isinstance(gids, list): + logger.warning(f"Generated JSON missing fields or invalid format: {obj}") continue + gids = [str(x) for x in gids if str(x) in allowed_ids] if not gids: + logger.warning("Generated gold_chunk_ids not found in allowed context") continue + line = {"query": q, "gold_chunk_ids": gids, "gold_answer": a} f.write(json.dumps(line, ensure_ascii=False) + "\n") generated += 1 await context.set_progress(0 + int(99 * generated / max(count, 1)), f"已生成 {generated}/{count}") - except Exception: + except Exception as e: + logger.warning(f"Benchmark generation failed for one item: {e}") continue meta = { diff --git a/web/src/components/RAGEvaluationTab.vue b/web/src/components/RAGEvaluationTab.vue index 2aa53a78..036759e9 100644 --- a/web/src/components/RAGEvaluationTab.vue +++ b/web/src/components/RAGEvaluationTab.vue @@ -9,7 +9,7 @@ @@ -202,48 +202,53 @@ - - -
-
{{ JSON.stringify(selectedResult.retrieval_config, null, 2) }}
-
-
+ + + + + +
+
{{ JSON.stringify(selectedResult.retrieval_config, null, 2) }}
+
+
+
- -
-

整体评估报告

- - - + + + + +
+
检索指标
- {{ getMetricTitle(key) }} + {{ getMetricTitle(key) }}: {{ formatMetricValue(value) }}
- - - - - +
+ + +
+
答案准确性
- 正确答案数 + 正确答案数: {{ evaluationStats.correctAnswers || 0 }} / {{ evaluationStats.totalQuestions || 0 }}
- 准确率 + 准确率: {{ (evaluationStats.answerAccuracy * 100).toFixed(1) }}%
- - - -
+
+ + +

详细评估结果

@@ -317,6 +322,7 @@ import { evaluationApi } from '@/apis/knowledge_api'; import ModelSelectorComponent from '@/components/ModelSelectorComponent.vue'; import SearchConfigModal from './SearchConfigModal.vue'; import { SettingOutlined, ReloadOutlined } from '@ant-design/icons-vue'; +import { useTaskerStore } from '@/stores/tasker'; const props = defineProps({ databaseId: { @@ -327,6 +333,9 @@ const props = defineProps({ const emit = defineEmits(['switch-to-benchmarks']); +// 使用任务中心 store +const taskerStore = useTaskerStore(); + // 状态 const selectedBenchmarkId = ref(null); const selectedBenchmark = ref(null); @@ -539,6 +548,8 @@ const startEvaluation = async () => { if (response.message === 'success') { message.success('评估任务已开始'); loadEvaluationHistory(); + // 刷新任务中心的任务列表 + taskerStore.loadTasks(); } else { message.error(response.message || '启动评估失败'); } @@ -1178,6 +1189,7 @@ onMounted(() => { .metric-label { font-size: 14px; + padding-right: 18px; color: var(--gray-700); } diff --git a/web/src/views/DataBaseInfoView.vue b/web/src/views/DataBaseInfoView.vue index ca5c3f9e..a5e5d342 100644 --- a/web/src/views/DataBaseInfoView.vue +++ b/web/src/views/DataBaseInfoView.vue @@ -42,14 +42,14 @@ ref="mindmapSectionRef" /> - + - +