refactor(audit): split list detail flows

This commit is contained in:
caoxiaozhu
2026-05-29 09:44:03 +08:00
parent 064eeb614f
commit 99e90798d2
28 changed files with 2636 additions and 2142 deletions

View File

@@ -1,23 +1,5 @@
<template>
<section class="json-risk-editor-shell panel digital-worker-detail-shell">
<header class="json-risk-editor-head asset-detail-topbar list-toolbar">
<div class="json-risk-editor-title asset-detail-topbar-main filter-set">
<div class="json-risk-head-copy">
<div class="json-risk-head-title-row">
<h2>{{ selectedSkill.name }}</h2>
</div>
<p class="json-risk-head-subtitle">
{{ selectedSkill.summary || '后台自动执行的数字员工技能。' }}
</p>
<div class="json-risk-head-meta">
<span>技能编号{{ selectedSkill.code || '-' }}</span>
<span>执行计划{{ digitalEmployee.scheduleLabel || selectedSkill.scope || '-' }}</span>
<span>最近更新{{ selectedSkill.updatedAt || '-' }}</span>
</div>
</div>
</div>
</header>
<div class="json-risk-editor-body">
<section class="json-risk-main-stage">
<article class="detail-card panel json-risk-summary-card">

View File

@@ -1,31 +1,5 @@
<template>
<section class="json-risk-editor-shell panel">
<header class="json-risk-editor-head asset-detail-topbar list-toolbar">
<div class="json-risk-editor-title asset-detail-topbar-main filter-set">
<div class="json-risk-head-copy">
<div class="json-risk-head-title-row">
<h2>{{ selectedSkill.name }}</h2>
</div>
<p class="json-risk-head-subtitle">
{{ selectedSkill.riskRuleSubtitle || '平台通用风险规则' }}
</p>
<div class="json-risk-head-meta">
<span v-if="selectedSkill.riskCategory">适用场景{{ selectedSkill.riskCategory }}</span>
<span>业务域{{ selectedSkill.category || '-' }}</span>
<span>最近更新{{ selectedSkill.updatedAt || '-' }}</span>
</div>
</div>
</div>
<div
class="json-risk-score-ring"
:class="selectedSkill.riskRuleScoreLevel || selectedSkill.riskRuleSeverity"
>
<strong>{{ selectedSkill.riskRuleScore ?? '--' }}</strong>
<span>风险分</span>
<em>{{ selectedSkill.riskRuleScoreLabel || selectedSkill.riskRuleSeverityLabel }}</em>
</div>
</header>
<div
v-if="selectedSkill.riskRuleGenerationFailed"
class="json-risk-generation-failure"

View File

@@ -1,21 +1,5 @@
<template>
<section class="spreadsheet-editor-shell panel">
<header class="spreadsheet-editor-head asset-detail-topbar list-toolbar">
<div class="spreadsheet-editor-title asset-detail-topbar-main filter-set">
<div class="skill-badge" :class="selectedSkill.badgeTone">{{ selectedSkill.typeLabel }}</div>
<div>
<h2>{{ selectedSkill.name }}</h2>
<p>{{ selectedSkill.summary || '当前资产尚未补充说明。' }}</p>
</div>
</div>
<div class="spreadsheet-editor-actions asset-detail-topbar-meta toolbar-actions">
<span class="spreadsheet-mode-pill">
{{ selectedSpreadsheetModeLabel }}
</span>
</div>
</header>
<input
ref="fileInput"
class="spreadsheet-upload-input"
@@ -126,7 +110,6 @@ defineOptions({
defineProps({
selectedSkill: { type: Object, required: true },
selectedSpreadsheetModeLabel: { type: String, default: '' },
selectedSpreadsheetFileName: { type: String, default: '' },
selectedSpreadsheetChangeRecords: { type: Array, default: () => [] },
spreadsheetOnlyOfficeHostId: { type: String, required: true },

View File

@@ -175,32 +175,6 @@
<!-- 详情视图 (全屏样式参考 AuditJsonRiskRuleDetail) -->
<div v-else key="detail" class="json-risk-editor-shell panel work-records-detail-stage">
<header class="json-risk-editor-head asset-detail-topbar list-toolbar">
<div class="json-risk-editor-title asset-detail-topbar-main filter-set">
<div class="json-risk-head-copy">
<div class="json-risk-head-title-row">
<h2>{{ resolveWorkRecordTitle(selectedRunDetail) }}</h2>
</div>
<p class="json-risk-head-subtitle">
执行工作流{{ resolveWorkRecordModuleLabel(selectedRunDetail) }}
</p>
<div class="json-risk-head-meta">
<span>Run ID{{ selectedRunDetail.run_id }}</span>
<span>触发来源{{ resolveWorkRecordSourceLabel(selectedRunDetail.source) }}</span>
<span>开始时间{{ formatWorkRecordDateTime(selectedRunDetail.started_at) }}</span>
</div>
</div>
</div>
<div
class="json-risk-score-ring"
:class="selectedRunDetail.status"
>
<strong style="font-size: 16px; font-weight: 900;">{{ resolveWorkRecordStatusLabel(selectedRunDetail) }}</strong>
<span>运行状态</span>
<em>{{ resolveWorkRecordStatusNote(selectedRunDetail) || '执行完毕' }}</em>
</div>
</header>
<div v-if="detailLoading" class="work-record-detail-state panel" style="min-height: 200px; display: grid; place-items: center; border: 0;">
<TableLoadingState
variant="panel"
@@ -345,7 +319,7 @@ defineOptions({
name: 'DigitalEmployeeWorkRecords'
})
const emit = defineEmits(['summary-change', 'detail-open-change'])
const emit = defineEmits(['summary-change', 'detail-open-change', 'detail-topbar-change'])
const { toast } = useToast()
const runs = ref([])
@@ -362,9 +336,57 @@ watch(detailOpen, (newVal) => {
}, { immediate: true })
let pollTimer = 0
const totalCount = computed(() => runs.value.length)
const successCount = computed(() => runs.value.filter((run) => run.status === 'succeeded').length)
const failedCount = computed(() => runs.value.filter((run) => run.status === 'failed').length)
const workRecordSummary = computed(() =>
runs.value.reduce(
(summary, run) => {
summary.total += 1
if (run.status === 'succeeded') {
summary.succeeded += 1
} else if (run.status === 'failed') {
summary.failed += 1
}
return summary
},
{ total: 0, succeeded: 0, failed: 0 }
)
)
const workRecordDetailTopBar = computed(() => {
const detail = selectedRunDetail.value
if (!detail) return null
const status = String(detail.status || '').toLowerCase()
const statusColor =
status === 'failed'
? '#ef4444'
: status === 'succeeded'
? 'var(--success)'
: '#3b82f6'
return {
view: {
title: resolveWorkRecordTitle(detail),
desc: `执行工作流:${resolveWorkRecordModuleLabel(detail)}`
},
kpis: [
{
label: '运行状态',
value: resolveWorkRecordStatusLabel(detail),
unit: '',
meta: resolveWorkRecordStatusNote(detail) || '执行完毕',
trend: status === 'failed' ? 'down' : 'up',
color: statusColor
}
]
}
})
watch(
workRecordDetailTopBar,
(value) => {
emit('detail-topbar-change', value)
},
{ immediate: true, deep: true }
)
const listKeyword = ref('')
const activeModule = ref('全部')
@@ -479,9 +501,9 @@ async function loadWorkRecords(showToast = false) {
const payload = await fetchAgentRuns({ agent: 'hermes', limit: 100 })
runs.value = Array.isArray(payload) ? payload : []
emit('summary-change', {
total: totalCount.value,
succeeded: successCount.value,
failed: failedCount.value
total: workRecordSummary.value.total,
succeeded: workRecordSummary.value.succeeded,
failed: workRecordSummary.value.failed
})
} catch (error) {
errorMessage.value = error?.message || '工作记录加载失败,请稍后重试。'
@@ -646,19 +668,4 @@ onBeforeUnmount(() => {
min-height: 0;
}
/* 风险环的成功、失败、执行中状态配色 */
.json-risk-score-ring.succeeded {
--score-ring: #16a34a;
--score-ring-bg: #f0fdf4;
}
.json-risk-score-ring.failed {
--score-ring: #dc2626;
--score-ring-bg: #fef2f2;
}
.json-risk-score-ring.running {
--score-ring: #2563eb;
--score-ring-bg: #eff6ff;
}
</style>