Files
ebiz-ai-knowledge-manage/src/views/riskCheck/result.vue
du.meimei c838c966b8 feat(riskCheck): 新增风险筛查结果页面
- 添加历史风险筛查结果页面组件
- 实现风险筛查结果的展示和详情加载功能
- 优化页面样式和布局
2025-07-28 10:37:22 +08:00

580 lines
14 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
<template>
<div class="main" id="main">
<div class="left-nav">
<div class="nav-header">历史风险筛查结果</div>
<div class="nav-body" id="navBody">
<div v-if="loadingNav" class="loading">
<span class="loading-spinner"></span>
数据加载中...
</div>
<div v-else-if="navList.length === 0" class="empty-message">
暂无历史记录
</div>
<a
v-else
v-for="(navItem, i) in navList"
:key="i"
href="javascript:void(0)"
:class="['link', { active: activeNavIndex === i }]"
@click="handleNavClick(i)"
>
<img
:src="navItem.hasRisk === 1 ? errorIcon : rightIcon"
class="png-icon"
/>
{{ navItem.taSubmitDate }}
<span>{{ navItem.hasRisk === 1 ? '【有风险】' : '【无风险】' }}</span>
</a>
</div>
</div>
<div class="right-container">
<div class="top-container">
<div class="custom-container">
<span id="custom">{{ navCheckRecord.orgName || '未知客户' }}</span>
<span id="time">{{ detailTimeInfo }}</span>
</div>
<h4 id="insured">
被保险人名称{{ navCheckRecord.insuredName || '未知' }}
</h4>
<div id="docs" v-html="currentCheckSummary"></div>
</div>
<div style="overflow: auto;">
<div id="detail-container">
<div v-if="detailLoading" class="loading">
<span class="loading-spinner"></span>
正在加载详情...
</div>
<div v-else-if="arrs.length === 0" class="empty-message">
<img
src="@/assets/images/empty.png"
alt=""
style="width:200px;margin: 0 auto"
/>
<p>暂无风险</p>
</div>
<template v-else>
<div v-for="(resultDetail, ind) in arrs" :key="ind">
<h4 v-if="resultDetail.tabName" class="section-title">
{{ resultDetail.tabName }}
</h4>
<div
:class="['tree-item-header', { expanded: expandedItems[ind] }]"
@click="toggleItem(ind)"
>
{{
resultDetail.typeName
? resultDetail.typeName
: resultDetail.dictLabel
}}
</div>
<div
:id="'result-container-' + ind"
class="result-container-item"
:style="{ display: expandedItems[ind] ? 'block' : 'none' }"
>
<ul class="result-container-item-child-ul">
<li
v-if="
!(
resultDetail.children &&
resultDetail.children.length > 0
)
"
class="result-container-item-child"
style="color: #95a5a6; font-style: italic;"
>
暂无数据
</li>
<li
v-for="(child, childIndex) in resultDetail.children"
:key="childIndex"
class="result-container-item-child"
@click="handleChildClick(child)"
>
<span class="index">{{ childIndex + 1 }}</span>
{{
(child.ruleName ? child.ruleName : child.fileName) ||
'未知项目'
}}
</li>
</ul>
</div>
</div>
</template>
</div>
</div>
</div>
<div style="clear: both"></div>
</div>
</template>
<script>
import { queryResult, queryResultDetail } from '@/api/riskCheck/record'
import errorIcon from '@/assets/images/error.png'
import rightIcon from '@/assets/images/right.png'
export default {
name: 'RiskHistory',
data() {
return {
errorIcon,
rightIcon,
loadingNav: true,
detailLoading: false,
navList: [],
navCheckRecord: {},
activeNavIndex: -1,
arrs: [],
expandedItems: {},
ipConfig: {
ip: this.$route.query.ip || 'http://39.104.123.256:7196'
},
serviceUrl: {
download: {
url: '/bpic/image/download'
}
}
}
},
computed: {
currentCheckSummary() {
if (this.activeNavIndex >= 0 && this.navList[this.activeNavIndex]) {
return (
this.navList[this.activeNavIndex].checkSummary ||
'<p>暂无风险摘要信息</p>'
)
}
return '<p>请选择左侧记录查看详细信息</p>'
},
detailTimeInfo() {
if (this.activeNavIndex >= 0 && this.navList[this.activeNavIndex]) {
return (
(this.navCheckRecord.taLatestSubmitDate || '未知时间') +
' 共【' +
(this.arrs ? this.arrs.length : 0) +
'】条风险提示'
)
}
return ''
}
},
mounted() {
// 处理noPT参数
if (this.$route.query.noPT) {
const main = document.getElementById('main')
if (main) {
main.style.padding = '0'
}
}
this.getNavList()
},
methods: {
getNavList() {
const taCode = this.$route.query.taCode || 'C123504032025600027'
queryResult({ taCode })
.then(response => {
this.loadingNav = false
if (response.code !== 200) {
this.$message.error(response.message || '请求失败')
throw new Error(response.message || '请求失败')
}
const data = response.content || response.data
this.navList = data.resultList || []
this.navCheckRecord = data.riskCheckRecord || {}
// 默认点击第一个导航项
if (this.navList.length > 0) {
this.$nextTick(() => {
this.handleNavClick(0)
})
}
})
.catch(error => {
this.loadingNav = false
this.$message.error('获取数据失败: ' + error.message)
this.navList = []
})
},
handleNavClick(index) {
// 更新活动索引
this.activeNavIndex = index
// 格式化checkSummary
if (
this.navList[index].checkSummary &&
typeof this.navList[index].checkSummary === 'string'
) {
let text = this.navList[index].checkSummary
text = text.replace(/\n\n/g, '</p><p>') // 段落
text = text.replace(/\n/g, '<br/>') // 剩余单换行
text = '<p>' + text + '</p>'
text = text.replace(/<p><\/p>/g, '<p>&nbsp;</p>') // 防止空段落出错
this.navList[index].checkSummary = text
} else {
this.navList[index].checkSummary = '<p>暂无风险摘要信息</p>'
}
// 获取详情
this.getDetail(this.navList[index])
},
getDetail(navItem) {
this.detailLoading = true
const taCode = this.$route.query.taCode || this.navCheckRecord.taCode
const params = {
resultId: navItem.id,
recordId: navItem.recordId,
taCode: taCode
}
queryResultDetail(params)
.then(response => {
this.detailLoading = false
if (response.code !== 200) {
this.$message.error(response.message || '请求失败')
throw new Error(response.message || '请求失败')
}
const data = response.content || response.data
const result = data.ruleTypeList || []
const fileStorageInfoList = data.fileBizTypeDictList || []
this.arrs = []
if (result && result.length > 0) {
result[0].tabName = '风险筛查结果'
for (let i = 0; i < result.length; i++) {
this.arrs.push(result[i])
}
}
if (fileStorageInfoList && fileStorageInfoList.length > 0) {
fileStorageInfoList[0].tabName = '影像件'
for (let i = 0; i < fileStorageInfoList.length; i++) {
this.arrs.push(fileStorageInfoList[i])
}
}
// 默认展开第一个项目
if (this.arrs.length > 0) {
this.$set(this.expandedItems, 0, true)
}
})
.catch(error => {
this.detailLoading = false
this.$message.error('获取详情失败: ' + error.message)
this.arrs = []
})
},
toggleItem(index) {
this.$set(this.expandedItems, index, !this.expandedItems[index])
},
handleChildClick(item) {
if (item.filePath) {
window.open(
this.ipConfig.ip + this.serviceUrl.download.url + '?fileId=' + item.id
)
}
}
}
}
</script>
<style scoped lang="scss">
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
.main {
width: 100%;
height: 100%;
padding: 1%;
font-size: 0; /* 消除 inline-block 间隙 */
}
.left-nav {
width: 20%;
float: left;
height: 100%;
display: inline-block;
vertical-align: top;
background: #fff;
border-radius: 10px;
font-size: 16px; /* 恢复字体 */
border: 1px solid #ddd;
/* IE8兼容的阴影效果 */
filter: progid:DXImageTransform.Microsoft.Shadow(color='#cccccc', Direction=135, Strength=3);
box-shadow: 0 2px 6px rgba(0, 0, 0, 0.1);
}
.nav-header {
font-size: 18px;
font-weight: bold;
text-align: center;
padding: 20px 0;
border-bottom: 1px solid #eee;
background: #f8f9fa;
color: #2c3e50;
border-radius: 10px 10px 0 0;
}
.link {
display: block;
margin: 15px auto;
text-align: center;
background: #fff;
text-decoration: none;
color: #000;
font-size: 14px;
border-radius: 4px;
padding: 12px 10px;
width: 85%;
transition: all 0.3s ease;
/* IE8兼容样式 */
border: 1px solid transparent;
}
.link:hover {
background: #f5f9ff;
border-color: #3498db;
color: #000;
}
.link.active {
background: #f0f4fa;
color: #3498db;
}
.right-container {
width: 79%;
height: 100%;
display: inline-block;
float: right;
background: #fff;
border-radius: 10px;
font-size: 16px;
overflow-y: auto;
overflow-x: hidden;
border: 1px solid #ddd;
/* IE8兼容的阴影效果 */
filter: progid:DXImageTransform.Microsoft.Shadow(color='#cccccc', Direction=135, Strength=3);
box-shadow: 0 2px 6px rgba(0, 0, 0, 0.1);
}
.top-container,
#detail-container {
width: 100%;
background: #fff;
margin-bottom: 10px;
border: 1px solid #eee;
}
.top-container {
border-bottom: 1px solid #eee;
padding: 20px;
background: #fafbfc;
}
#detail-container {
padding: 20px;
}
#custom {
display: inline-block;
font-size: 22px;
font-weight: bold;
margin-right: 15px;
color: #2c3e50;
}
#time {
font-size: 14px;
margin-top: 8px;
color: #7f8c8d;
}
.custom-container {
display: block;
margin: 10px 0 20px 0;
}
#docs {
padding: 15px 20px;
font-size: 14px;
line-height: 1.6;
background: #2c3e50;
color: #ecf0f1;
border-radius: 4px;
margin: 15px 0;
}
#insured {
padding: 10px 0;
font-weight: bold;
color: #2c3e50;
border-bottom: 1px solid #eee;
}
.tree-item-header {
padding: 15px 20px;
background: #f0f4fa;
margin: 15px 0;
cursor: pointer;
border-radius: 4px;
border: 1px solid #d6dde6;
font-weight: bold;
color: #2c3e50;
transition: background 0.3s;
/* IE8兼容样式 */
background: #e3e9f2;
}
.tree-item-header:hover {
background: #e3e9f2;
}
.tree-item-header::before {
content: '';
margin-right: 10px;
transition: transform 0.3s;
/* IE8不支持::before伪元素和transform */
}
.tree-item-header.expanded::before {
content: '';
/* IE8不支持 */
}
.result-container-item {
padding: 0 10px;
margin-bottom: 20px;
}
.result-container-item-child-ul {
list-style: none;
}
ul {
list-style: none;
}
li {
list-style: none;
}
.index {
margin: 0 10px;
display: inline-block;
width: 25px;
height: 25px;
line-height: 25px;
text-align: center;
border-radius: 50%;
color: #fff;
background-color: #9fa8da;
border: 1px solid #9fa8da;
}
.result-container-item-child-ul li {
font-size: 14px;
line-height: 1.8;
padding: 10px 15px;
margin: 8px 0;
background: #fff;
border: 1px solid #eee;
border-radius: 4px;
cursor: pointer;
transition: all 0.3s;
/* IE8兼容样式 */
border: 1px solid #ddd;
}
.result-container-item-child-ul li:hover {
background: #f8f9ff;
border-color: #3498db;
}
/* 添加降级样式 */
.no-js-warning {
color: #e74c3c;
text-align: center;
padding: 30px;
font-weight: bold;
font-size: 16px;
background: #fadbd8;
border: 1px solid #f5b7b1;
border-radius: 4px;
margin: 20px;
}
/* 为不支持flex的浏览器提供备选方案 */
.custom-container > * {
display: inline-block;
vertical-align: top;
}
/* 添加加载状态提示 */
.loading {
text-align: center;
padding: 30px;
color: #7f8c8d;
}
.loading-spinner {
display: inline-block;
width: 20px;
height: 20px;
border: 3px solid #f3f3f3;
border-top: 3px solid #3498db;
border-radius: 50%;
animation: spin 1s linear infinite;
/* IE8不支持动画 */
border: 3px solid #3498db;
}
@keyframes spin {
0% {
transform: rotate(0deg);
}
100% {
transform: rotate(360deg);
}
}
.section-title {
font-size: 18px;
font-weight: bold;
margin: 25px 0 15px 0;
padding-bottom: 10px;
border-bottom: 2px solid #3498db;
color: #2c3e50;
}
.empty-message {
text-align: center;
padding: 40px 20px;
color: #95a5a6;
}
.png-icon {
vertical-align: middle;
margin: -2px 10px 0 10px;
outline: none;
border: none;
display: inline-block;
}
</style>