You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
haoliang-net/frontend/src/views/collect-address/CollectAddressDetailPage.vue

93 lines
5.3 KiB
Vue

<template>
<div>
<!-- 使用 PageHeader 统一头部 -->
<PageHeader :title="`采集地址详情:${detail.name}`" :showBack="true">
<template #breadcrumb>
<el-breadcrumb separator="/" style="margin: 0 0 12px 0;">
<el-breadcrumb-item><router-link :to="homePath">首页</router-link></el-breadcrumb-item>
<el-breadcrumb-item><router-link :to="collectAddressPath">采集地址</router-link></el-breadcrumb-item>
<el-breadcrumb-item>{{ detail.name || '采集地址详情' }}</el-breadcrumb-item>
</el-breadcrumb>
</template>
</PageHeader>
<el-card shadow="hover" style="margin-bottom:20px"><template #header><span>基本信息</span></template>
<el-descriptions :column="2" border size="small">
<el-descriptions-item label="名称">{{detail.name}}</el-descriptions-item>
<el-descriptions-item label="URL">{{detail.url}}</el-descriptions-item>
<el-descriptions-item label="品牌">{{detail.brandName}}</el-descriptions-item>
<el-descriptions-item label="采集间隔">{{detail.collectInterval ?? detail.interval}}</el-descriptions-item>
<el-descriptions-item label="状态"><el-tag :type="detail.isEnabled?'success':'danger'" size="small">{{detail.isEnabled?'启用':'停用'}}</el-tag></el-descriptions-item>
<el-descriptions-item label="最后采集">{{detail.lastCollectTime||'-'}}</el-descriptions-item>
</el-descriptions>
</el-card>
<el-card shadow="hover" style="margin-bottom:20px"><template #header><span>关联机床</span></template>
<el-table :data="machines" border stripe size="small">
<el-table-column prop="machineName" label="机床名称"/><el-table-column prop="deviceCode" label="device_code"/><el-table-column prop="workshopName" label="车间"/>
<el-table-column label="在线" align="center"><template #default="{row}"><el-tag :type="row.isOnline?'success':'danger'" size="small">{{row.isOnline?'在线':'离线'}}</el-tag></template></el-table-column>
<el-table-column prop="programName" label="当前程序"/>
</el-table>
</el-card>
<el-card shadow="hover"><template #header><span>最近采集记录</span></template>
<el-table :data="records" border stripe size="small">
<el-table-column prop="requestTime" label="请求时间"/>
<el-table-column prop="duration" label="耗时(ms)" align="center"/>
<el-table-column label="状态" align="center"><template #default="{row}"><el-tag :type="row.isSuccess?'success':'danger'" size="small">{{row.isSuccess?'成功':'失败'}}</el-tag></template></el-table-column>
<el-table-column prop="machineCount" label="机床数" align="center"/>
<el-table-column label="操作" width="120" align="center"><template #default="{row}"><el-button size="small" link type="primary" @click="viewRawJson(row)">JSON</el-button></template></el-table-column>
</el-table>
</el-card>
<el-dialog v-model:visible="rawJsonDialogVisible" :title="rawJsonTitle" width="700px">
<el-input type="textarea" v-model="rawJsonContent" rows="15" :readonly="true"></el-input>
<template #footer><el-button @click="rawJsonDialogVisible=false"></el-button></template>
</el-dialog>
</div>
</template>
<script setup lang="ts">
import {ref,onMounted} from 'vue'
import {useRoute} from 'vue-router'
import request from '@/utils/request'
import type { ApiResponse, CollectAddress } from '@/types'
import PageHeader from '@/components/PageHeader.vue'
import { useMockPath } from '@/composables/useMockPath'
type CollectMachineRow = { machineName: string; deviceCode?: string; workshopName?: string; isOnline?: boolean; programName?: string }
type CollectRecordRow = { requestTime: string; duration: number; isSuccess: boolean; machineCount: number; machineName?: string }
const { isMock } = useMockPath()
const homePath = isMock ? '/mock/dashboard' : '/dashboard'
const collectAddressPath = isMock ? '/mock/collect-address' : '/collect-address'
const route=useRoute()
const detail=ref<CollectAddress>({} as CollectAddress)
const machines=ref<CollectMachineRow[]>([])
const records=ref<CollectRecordRow[]>([])
// 原始JSON弹窗相关
const rawJsonDialogVisible = ref(false)
const rawJsonContent = ref('')
const rawJsonTitle = ref('原始采集数据')
async function viewRawJson(record: CollectRecordRow){
// 请求原始JSON
const id = route.params.id
const resp = await request.get<{ rawJson: string }>(`/admin/collect-address/${id}/raw-json`, { params: { recordId: record.requestTime } })
const raw = resp.data?.rawJson ?? '[]'
let parsed: unknown
try { parsed = JSON.parse(raw) } catch { parsed = raw }
rawJsonContent.value = JSON.stringify(parsed, null, 2)
rawJsonTitle.value = `原始采集数据 - ${record.machineName ?? ''}`
rawJsonDialogVisible.value = true
}
async function loadData(){
const id=route.params.id
const [d,m,r] = await Promise.all([
request.get<CollectAddress>(`/admin/collect-address/${id}`),
request.get<{ items: CollectMachineRow[] }>(`/admin/collect-address/${id}/machines`),
request.get<{ items: CollectRecordRow[] }>(`/admin/collect-address/${id}/collect-records`),
])
detail.value = d.data ?? ({} as CollectAddress)
machines.value = m.data?.items ?? []
records.value = r.data?.items ?? []
}
onMounted(loadData)
</script>