505 lines
15 KiB
Vue
505 lines
15 KiB
Vue
<template>
|
|
<div class="pedigree-detail">
|
|
<div v-if="currentNode === 'inputModel'" class="detail-content">
|
|
<BaseTable
|
|
ref="inputModelTableRef"
|
|
tableName="DATA_SEARCH"
|
|
:api="getFileListApiFun"
|
|
:params="modelParams"
|
|
showIndex
|
|
:fullHeight="true"
|
|
hideSearch
|
|
:actionList="modelActionList"
|
|
/>
|
|
</div>
|
|
|
|
<div v-else-if="currentNode === 'simParams'" class="detail-content">
|
|
<div class="sim-params-tabs">
|
|
<el-radio-group v-model="currentFlowNodeId" @change="flowNodeRadioChangeFun">
|
|
<el-radio-button v-for="item in flowNodeList" :key="item.uuid" :value="item.uuid">
|
|
{{ item.nodeName }}
|
|
</el-radio-button>
|
|
</el-radio-group>
|
|
</div>
|
|
<div class="sim-params-content">
|
|
<FlowNodeParamTable
|
|
ref="paramTableRef"
|
|
:nodeParams="currentNodeParams"
|
|
:pageInfo="currentPageInfo"
|
|
:currentNode="currentFlowNode"
|
|
:runInfo="runInfo"
|
|
:hideButtons="true"
|
|
:readonly="true"
|
|
/>
|
|
</div>
|
|
</div>
|
|
|
|
<div v-else-if="currentNode === 'calcModel'" class="detail-content">
|
|
<BaseTable
|
|
ref="calcModelTableRef"
|
|
tableName="DATA_SEARCH"
|
|
:api="getFileListApiFun"
|
|
:params="calcFileParams"
|
|
showIndex
|
|
:fullHeight="true"
|
|
hideSearch
|
|
:actionList="calcFileActionList"
|
|
/>
|
|
</div>
|
|
|
|
<div v-else-if="currentNode === 'calcResult'" class="detail-content">
|
|
<BaseTable
|
|
ref="calcResultTableRef"
|
|
tableName="DATA_SEARCH"
|
|
:api="getFileListApiFun"
|
|
:params="calcResultParams"
|
|
showIndex
|
|
:fullHeight="true"
|
|
hideSearch
|
|
:actionList="calcFileActionList"
|
|
/>
|
|
</div>
|
|
|
|
<div v-else-if="currentNode === 'keyResult'" class="detail-content">
|
|
<div class="key-result-tabs">
|
|
<el-radio-group v-model="keyResultType" @change="refreshKeyResultTableFun">
|
|
<el-radio-button value="1">{{ $t('数据谱系.云图结果') }}</el-radio-button>
|
|
<el-radio-button value="2">{{ $t('数据谱系.曲线结果') }}</el-radio-button>
|
|
<el-radio-button value="3">{{ $t('数据谱系.数值指标') }}</el-radio-button>
|
|
<el-radio-button value="4">{{ $t('数据谱系.视频文件') }}</el-radio-button>
|
|
</el-radio-group>
|
|
</div>
|
|
<div class="key-result-content">
|
|
<BaseTable
|
|
v-if="keyResultType === '1'"
|
|
ref="cloudImageTableRef"
|
|
tableName="DATA_SEARCH"
|
|
:api="getFileListApiFun"
|
|
:params="cloudImageParams"
|
|
showIndex
|
|
:fullHeight="true"
|
|
hideSearch
|
|
:actionList="cloudImageActionList"
|
|
/>
|
|
<BaseTable
|
|
v-else-if="keyResultType === '2'"
|
|
ref="curveTableRef"
|
|
tableName="DATA_SEARCH"
|
|
:api="getFileListApiFun"
|
|
:params="curveParams"
|
|
showIndex
|
|
:fullHeight="true"
|
|
hideSearch
|
|
:actionList="curveActionList"
|
|
/>
|
|
<TaskPerformance
|
|
v-else-if="keyResultType === '3'"
|
|
:paramType="pedigreeType === 'task' ? 'task' : 'run'"
|
|
:taskInfo="pedigreeType === 'task' ? { uuid: taskId } : undefined"
|
|
:runInfo="pedigreeType === 'run' ? { uuid: runId } : undefined"
|
|
:fullHeight="true"
|
|
:showLeftOptions="false"
|
|
:showSaveButton="false"
|
|
:showSetting="false"
|
|
:canUpdate="false"
|
|
:showCheckbox="false"
|
|
/>
|
|
<BaseTable
|
|
v-else-if="keyResultType === '4'"
|
|
ref="videoTableRef"
|
|
tableName="DATA_SEARCH"
|
|
:api="getFileListApiFun"
|
|
:params="videoParams"
|
|
showIndex
|
|
:fullHeight="true"
|
|
hideSearch
|
|
:actionList="videoActionList"
|
|
/>
|
|
</div>
|
|
</div>
|
|
|
|
<div v-else-if="currentNode === 'simReport'" class="detail-content">
|
|
<BaseTable
|
|
ref="reportTableRef"
|
|
tableName="DATA_SEARCH"
|
|
:api="getFileListApiFun"
|
|
:params="reportParams"
|
|
showIndex
|
|
:fullHeight="true"
|
|
hideSearch
|
|
:actionList="reportActionList"
|
|
/>
|
|
</div>
|
|
|
|
<div v-else-if="currentNode === 'testData'" class="detail-content">
|
|
<BaseTable
|
|
ref="testDataTableRef"
|
|
tableName="DATA_SEARCH"
|
|
:api="getFileListApiFun"
|
|
:params="testDataParams"
|
|
showIndex
|
|
:fullHeight="true"
|
|
hideSearch
|
|
:actionList="testDataActionList"
|
|
/>
|
|
</div>
|
|
|
|
<div
|
|
v-else-if="currentNode === 'reviewReport' && enableConfigByTenant([TENANT_ENUM.LYRIC])"
|
|
class="detail-content"
|
|
>
|
|
<BaseTable
|
|
ref="reviewReportTableRef"
|
|
tableName="DATA_SEARCH"
|
|
:api="getFileListApiFun"
|
|
:params="reviewFileParams"
|
|
showIndex
|
|
:fullHeight="true"
|
|
hideSearch
|
|
:actionList="reviewReportActionList"
|
|
/>
|
|
</div>
|
|
|
|
<FilePreview v-model="previewVisible" :fileId="currentRow?.id" />
|
|
</div>
|
|
</template>
|
|
|
|
<script setup lang="ts">
|
|
import { ref, watch, computed } from 'vue';
|
|
import BaseTable from '@/components/common/table/baseTable.vue';
|
|
import { getSimulationTaskFileApi } from '@/api/data/dataAnalysis';
|
|
import { FILE_TYPE } from '@/utils/enum/file';
|
|
import FlowNodeParamTable from '@/components/flow/flowNodeParamTable.vue';
|
|
import { listSimulationFlowNodeApi } from '@/api/project/run';
|
|
import { getRunListByRunIdListApi } from '@/api/project/node';
|
|
import { queryFlowTemplateDetailApi } from '@/api/capability/flow';
|
|
import FilePreview from '@/components/common/filePreview/index.vue';
|
|
import TaskPerformance from '@/components/taskDetail/taskPerformance.vue';
|
|
import { downloadFileById } from '@/utils/file';
|
|
import { cloneDeep } from 'lodash-es';
|
|
import { enableConfigByTenant, TENANT_ENUM } from '@/tenants/tenant';
|
|
|
|
const FILE_DICT_CLASS = 'ALL_FILE_TYPE';
|
|
const DICT_TAGS = ['fileTypeDictClass', 'fileTypeDictValue'];
|
|
|
|
interface Props {
|
|
currentNode?: string;
|
|
runId?: string;
|
|
taskId?: string;
|
|
rowData?: Record<string, any>;
|
|
pedigreeType?: 'task' | 'run';
|
|
defaultKeyResultType?: '1' | '2' | '3' | string;
|
|
}
|
|
|
|
const props = withDefaults(defineProps<Props>(), {
|
|
currentNode: 'inputModel',
|
|
runId: '',
|
|
taskId: '',
|
|
rowData: () => ({}),
|
|
pedigreeType: 'run',
|
|
defaultKeyResultType: '1',
|
|
});
|
|
|
|
const previewVisible = ref(false);
|
|
const currentRow = ref<any>(null);
|
|
|
|
const previewFileFun = (row: any) => {
|
|
currentRow.value = row;
|
|
previewVisible.value = true;
|
|
};
|
|
|
|
const downloadFileFun = (row: any) => {
|
|
downloadFileById(row.id);
|
|
};
|
|
|
|
const modelActionList = [
|
|
{ title: '预览', type: 'primary', click: previewFileFun },
|
|
{ title: '下载', type: 'primary', click: downloadFileFun },
|
|
];
|
|
const calcFileActionList = [{ title: '下载', type: 'primary', click: downloadFileFun }];
|
|
const cloudImageActionList = [
|
|
{ title: '预览', type: 'primary', click: previewFileFun },
|
|
{ title: '下载', type: 'primary', click: downloadFileFun },
|
|
];
|
|
const curveActionList = [
|
|
{ title: '预览', type: 'primary', click: previewFileFun },
|
|
{ title: '下载', type: 'primary', click: downloadFileFun },
|
|
];
|
|
const reportActionList = [
|
|
{ title: '预览', type: 'primary', click: previewFileFun },
|
|
{ title: '下载', type: 'primary', click: downloadFileFun },
|
|
];
|
|
const testDataActionList = [
|
|
{ title: '预览', type: 'primary', click: previewFileFun },
|
|
{ title: '下载', type: 'primary', click: downloadFileFun },
|
|
];
|
|
const reviewReportActionList = [
|
|
{ title: '预览', type: 'primary', click: previewFileFun },
|
|
{ title: '下载', type: 'primary', click: downloadFileFun },
|
|
];
|
|
const videoActionList = [
|
|
{ title: '预览', type: 'primary', click: previewFileFun },
|
|
{ title: '下载', type: 'primary', click: downloadFileFun },
|
|
];
|
|
|
|
const keyResultType = ref('1');
|
|
|
|
const flowNodeList = ref<any[]>([]);
|
|
const currentFlowNodeId = ref<string>('');
|
|
const runInfo = ref<any>({});
|
|
const currentFlowNode = ref<any>(null);
|
|
const currentPageInfo = ref<any>({});
|
|
const nodeConfigList = ref<any>({});
|
|
|
|
const currentCalcResultNodeId = ref<string>('');
|
|
const currentCalcResultNode = ref<any>(null);
|
|
|
|
const fetchFlowNodesFun = async () => {
|
|
if (!props.runId) {
|
|
flowNodeList.value = [];
|
|
runInfo.value = {};
|
|
nodeConfigList.value = {};
|
|
return;
|
|
}
|
|
const [nodesRes, runInfoRes]: any = await Promise.all([
|
|
listSimulationFlowNodeApi({ runId: props.runId }),
|
|
getRunListByRunIdListApi({ runIdList: [props.runId] }),
|
|
]);
|
|
if (runInfoRes?.code === 200 && runInfoRes.data?.length > 0) {
|
|
runInfo.value = runInfoRes.data[0];
|
|
if (runInfo.value.flowTemplate) {
|
|
const templateRes: any = await queryFlowTemplateDetailApi({
|
|
uuid: runInfo.value.flowTemplate,
|
|
status: 1,
|
|
});
|
|
if (templateRes?.code === 200 && templateRes.data?.viewContent) {
|
|
try {
|
|
const viewData = JSON.parse(templateRes.data.viewContent);
|
|
const nodes = viewData.cells?.filter((item: any) => item.type) || [];
|
|
const configMap: any = {};
|
|
nodes.forEach((node: any) => {
|
|
if (node.data?.label && node.data?.pageConfigList) {
|
|
configMap[node.data.label] = node.data.pageConfigList;
|
|
}
|
|
});
|
|
nodeConfigList.value = configMap;
|
|
} catch {
|
|
nodeConfigList.value = {};
|
|
}
|
|
}
|
|
}
|
|
}
|
|
if (nodesRes?.code === 200 && nodesRes.data?.flowNodeDtoList) {
|
|
const allNodes = nodesRes.data.flowNodeDtoList || [];
|
|
flowNodeList.value = allNodes.filter((node: any) => {
|
|
const nodeType = node.nodeDetailInfo?.type;
|
|
return nodeType !== 'StartEvent' && nodeType !== 'EndEvent';
|
|
});
|
|
if (flowNodeList.value.length > 0 && !currentFlowNodeId.value) {
|
|
currentFlowNodeId.value = flowNodeList.value[0].uuid;
|
|
flowNodeRadioChangeFun(flowNodeList.value[0].uuid);
|
|
}
|
|
if (flowNodeList.value.length > 0 && !currentCalcResultNodeId.value) {
|
|
currentCalcResultNodeId.value = flowNodeList.value[0].uuid;
|
|
flowNodeRadioChangeFun(flowNodeList.value[0].uuid);
|
|
}
|
|
} else {
|
|
flowNodeList.value = [];
|
|
}
|
|
};
|
|
|
|
const currentNodeParams = ref<any>([]);
|
|
|
|
const mergeUserParamsFun = (list: any[], userParams: any): any[] => {
|
|
const result = cloneDeep(list);
|
|
for (const item of result) {
|
|
if (item.englishLabel && userParams?.[item.englishLabel] !== undefined) {
|
|
item.defaultValue = userParams[item.englishLabel];
|
|
}
|
|
if (item.children?.length) {
|
|
const childParams =
|
|
item.tagType === 'view' && item.tagIcon === 'row'
|
|
? userParams?.[item.vModel] || {}
|
|
: userParams;
|
|
item.children = mergeUserParamsFun(item.children, childParams);
|
|
}
|
|
}
|
|
return result;
|
|
};
|
|
|
|
const getFileListApiFun = async (params: any) => {
|
|
if (props.pedigreeType === 'task') {
|
|
const res: any = await getSimulationTaskFileApi({
|
|
...params,
|
|
runId: props.runId,
|
|
});
|
|
return res;
|
|
} else {
|
|
const res: any = await getSimulationTaskFileApi({
|
|
...params,
|
|
runId: props.runId,
|
|
});
|
|
return res;
|
|
}
|
|
};
|
|
|
|
const buildParamsFun = (fileType: number) => {
|
|
if (props.pedigreeType === 'task') {
|
|
return {
|
|
uuid: props.taskId,
|
|
fileTypeDictValue: String(fileType),
|
|
fileTypeDictClass: FILE_DICT_CLASS,
|
|
dictTags: DICT_TAGS,
|
|
level: 'task',
|
|
tagReq: {
|
|
...props?.rowData?.tagReq,
|
|
},
|
|
};
|
|
} else {
|
|
return {
|
|
uuid: props.runId,
|
|
fileTypeDictValue: String(fileType),
|
|
fileTypeDictClass: FILE_DICT_CLASS,
|
|
dictTags: DICT_TAGS,
|
|
tagReq: {
|
|
...props?.rowData?.tagReq,
|
|
},
|
|
};
|
|
}
|
|
};
|
|
|
|
const modelParams = computed(() => buildParamsFun(FILE_TYPE.MODEL_3D_FILE));
|
|
const calcFileParams = computed(() => buildParamsFun(FILE_TYPE.CALCULATION_FILE));
|
|
const calcResultParams = computed(() => buildParamsFun(FILE_TYPE.CALCULATION_RESULT));
|
|
const reportParams = computed(() => buildParamsFun(FILE_TYPE.REPORT_FILE));
|
|
const testDataParams = computed(() => buildParamsFun(FILE_TYPE.TEST_DOCUMENT_FILE));
|
|
const reviewFileParams = computed(() => buildParamsFun(FILE_TYPE.REVIEW_FILE));
|
|
const cloudImageParams = computed(() => buildParamsFun(FILE_TYPE.PNG_FILE));
|
|
const curveParams = computed(() => buildParamsFun(FILE_TYPE.CANVAS_FILE));
|
|
const videoParams = computed(() => buildParamsFun(FILE_TYPE.VIDEO_FILE));
|
|
|
|
const cloudImageTableRef = ref();
|
|
const curveTableRef = ref();
|
|
const videoTableRef = ref();
|
|
|
|
const refreshKeyResultTableFun = () => {
|
|
const tableRefMap: Record<string, any> = {
|
|
'1': cloudImageTableRef,
|
|
'2': curveTableRef,
|
|
'4': videoTableRef,
|
|
};
|
|
tableRefMap[keyResultType.value]?.value?.resetFun(true);
|
|
};
|
|
|
|
const flowNodeRadioChangeFun = (uuid: string) => {
|
|
const selectedNode = flowNodeList.value.find((node: any) => node.uuid === uuid);
|
|
if (selectedNode) {
|
|
currentFlowNode.value = selectedNode;
|
|
const userParams = selectedNode.userParams || {};
|
|
currentPageInfo.value = {
|
|
userParams,
|
|
inputDirId: selectedNode.inputDirId || '',
|
|
};
|
|
const nodeName = selectedNode.nodeName || '';
|
|
const templateConfig = nodeConfigList.value[nodeName] || [];
|
|
currentNodeParams.value = mergeUserParamsFun(templateConfig, userParams);
|
|
|
|
currentCalcResultNode.value = selectedNode;
|
|
}
|
|
};
|
|
|
|
watch(
|
|
() => props.currentNode,
|
|
(newVal) => {
|
|
if (newVal === 'simParams') {
|
|
currentFlowNodeId.value = '';
|
|
fetchFlowNodesFun();
|
|
} else if (newVal === 'calcResult') {
|
|
currentCalcResultNodeId.value = '';
|
|
fetchFlowNodesFun();
|
|
} else if (newVal === 'keyResult' && props.defaultKeyResultType) {
|
|
keyResultType.value = props.defaultKeyResultType;
|
|
refreshKeyResultTableFun();
|
|
}
|
|
}
|
|
);
|
|
|
|
watch(
|
|
() => props.defaultKeyResultType,
|
|
(newVal) => {
|
|
if (props.currentNode === 'keyResult' && newVal) {
|
|
keyResultType.value = newVal;
|
|
refreshKeyResultTableFun();
|
|
}
|
|
},
|
|
{ immediate: true }
|
|
);
|
|
|
|
watch(
|
|
() => props.runId,
|
|
(newVal, oldVal) => {
|
|
if (newVal && newVal !== oldVal && props.currentNode === 'keyResult') {
|
|
keyResultType.value = props.defaultKeyResultType || '1';
|
|
refreshKeyResultTableFun();
|
|
}
|
|
}
|
|
);
|
|
|
|
watch(
|
|
() => props.runId,
|
|
(newVal) => {
|
|
if (newVal && props.currentNode === 'simParams') {
|
|
currentFlowNodeId.value = '';
|
|
fetchFlowNodesFun();
|
|
}
|
|
},
|
|
{ immediate: true }
|
|
);
|
|
</script>
|
|
|
|
<style lang="scss" scoped>
|
|
.pedigree-detail {
|
|
width: 100%;
|
|
height: 100%;
|
|
|
|
.detail-content {
|
|
width: 100%;
|
|
height: 100%;
|
|
}
|
|
|
|
.sim-params-tabs {
|
|
width: 100%;
|
|
height: 50px;
|
|
display: flex;
|
|
align-items: center;
|
|
padding: 0 10px;
|
|
}
|
|
|
|
.sim-params-content {
|
|
width: 100%;
|
|
height: calc(100% - 50px);
|
|
}
|
|
|
|
.empty-tip {
|
|
width: 100%;
|
|
height: 100%;
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
}
|
|
|
|
.key-result-tabs {
|
|
width: 100%;
|
|
height: 50px;
|
|
display: flex;
|
|
align-items: center;
|
|
padding: 0 10px;
|
|
}
|
|
|
|
.key-result-content {
|
|
width: 100%;
|
|
height: calc(100% - 50px);
|
|
}
|
|
}
|
|
</style>
|