feat(web): 前端集成 LLM 预警推送与二次判断结果展示

This commit is contained in:
2026-06-16 11:26:53 +08:00
parent b097983f1b
commit fe2b569046
2 changed files with 69 additions and 0 deletions
@@ -346,6 +346,9 @@ import {
} from '@element-plus/icons-vue' } from '@element-plus/icons-vue'
import { detectionApi } from '@/api/detection' import { detectionApi } from '@/api/detection'
import DetectionConfig from './DetectionConfig.vue' import DetectionConfig from './DetectionConfig.vue'
import { useAlertStore } from '@/stores/alertStore'
const alertStore = useAlertStore()
const props = defineProps({ const props = defineProps({
models: { models: {
@@ -787,6 +790,23 @@ const handleFightVideoSuccess = (response) => {
const detCount = response.data.stats?.total_detections || 0 const detCount = response.data.stats?.total_detections || 0
ElMessage.success(`检测完成:${detCount} 个目标,已提取 ${kfCount} 张关键帧`) ElMessage.success(`检测完成:${detCount} 个目标,已提取 ${kfCount} 张关键帧`)
// MVP-3: 将 LLM 管道产出的预警推送到 AlertList
const frameResults = response.data.frame_results || []
let llmAlertCount = 0
for (const fr of frameResults) {
const alerts = fr.alert_events || []
for (const alert of alerts) {
alertStore.addAlert({
...alert,
llm_results: fr.llm_results || [],
})
llmAlertCount++
}
}
if (llmAlertCount > 0) {
ElMessage.success(`LLM 二次判断完成,已生成 ${llmAlertCount} 条预警记录`)
}
// 如果后端提示编码不兼容,自动标记视频错误 // 如果后端提示编码不兼容,自动标记视频错误
if (response.data.video_codec_warning) { if (response.data.video_codec_warning) {
console.warn('视频编码不兼容浏览器,将以关键帧形式展示') console.warn('视频编码不兼容浏览器,将以关键帧形式展示')
+49
View File
@@ -156,6 +156,28 @@
<span v-if="det.track_id" class="track-id">#{{ det.track_id }}</span> <span v-if="det.track_id" class="track-id">#{{ det.track_id }}</span>
</span> </span>
</div> </div>
<!-- MVP-3: LLM 二次判断结果 -->
<div v-if="alert.llm_results && alert.llm_results.length > 0" class="llm-result">
<el-tag
:type="alert.llm_results[0].llm_confirmed ? 'success' : 'danger'"
effect="light"
round
size="small"
>
{{ alert.llm_results[0].llm_confirmed ? 'LLM确认' : 'LLM否决' }}
</el-tag>
<span class="llm-confidence">
LLM置信度: {{ ((alert.llm_results[0].llm_confidence || 0) * 100).toFixed(0) }}%
</span>
<span
v-if="alert.llm_results[0].llm_reasoning"
class="llm-reasoning"
:title="alert.llm_results[0].llm_reasoning"
>
{{ alert.llm_results[0].llm_reasoning.slice(0, 50) }}...
</span>
</div>
</div> </div>
<div class="alert-actions"> <div class="alert-actions">
@@ -534,6 +556,33 @@ onMounted(() => {
opacity: 0.8; opacity: 0.8;
} }
/* MVP-3: LLM 二次判断结果样式 */
.llm-result {
display: flex;
align-items: center;
gap: 8px;
margin-top: 8px;
padding: 6px 10px;
background: rgba(99, 102, 241, 0.06);
border-left: 3px solid #818CF8;
border-radius: 4px;
}
.llm-confidence {
font-size: 12px;
color: #A5B4FC;
}
.llm-reasoning {
font-size: 12px;
color: #9CA3AF;
max-width: 200px;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
cursor: help;
}
.alert-actions { .alert-actions {
display: flex; display: flex;
align-items: center; align-items: center;