| | |
| | | <th>使用次数</th> |
| | | <th>使用上限</th> |
| | | <th>寿命比%</th> |
| | | <th>寿命预警值</th> |
| | | <th>寿命比预警值</th> |
| | | <th>预警状态</th> |
| | | </tr> |
| | | </thead> |
| | |
| | | }); |
| | | if (res.status === 0) { |
| | | this.$showMessage('上刀提交成功'); |
| | | // 成功后刷新列表 |
| | | await this.fetchFormData(); |
| | | } else { |
| | | this.$showMessage(res.message || '上刀提交失败'); |
| | | } |
| | |
| | | }); |
| | | if (res.status === 0) { |
| | | this.$showMessage('下刀提交成功'); |
| | | // 成功后刷新列表 |
| | | await this.fetchFormData(); |
| | | } else { |
| | | this.$showMessage(res.message || '下刀提交失败'); |
| | | } |
| | |
| | | this.toolModel = ''; |
| | | }, |
| | | async fetchFormData() { |
| | | // 重写:增强兼容性、统一字段映射、格式化时间和百分比,计算预警状态 |
| | | if (!this.workOrderNo || !this.machineNo) { |
| | | console.warn('工单号或机台号为空,跳过获取表单数据'); |
| | | return; |
| | |
| | | }; |
| | | |
| | | try { |
| | | console.log('请求参数:', payload); // 添加调试日志 |
| | | console.log('请求参数:', payload); |
| | | |
| | | const res = await this.$post({ |
| | | url: '/MesCutterLedger/GetFormData', |
| | |
| | | headers: { 'Content-Type': 'application/json' } |
| | | }); |
| | | |
| | | if (res.status === 0) { |
| | | console.log('获取数据成功:', res.data); |
| | | |
| | | // 兼容多种返回结构,取到数组 |
| | | const list = Array.isArray(res.data) ? res.data |
| | | : (res.data && res.data.tbBillList) ? res.data.tbBillList |
| | | : (res.data && res.data.data) ? res.data.data |
| | | : []; |
| | | |
| | | const getField = (obj, ...keys) => { |
| | | for (const k of keys) if (obj?.[k] !== undefined && obj?.[k] !== null) return obj[k]; |
| | | return null; |
| | | }; |
| | | |
| | | // 映射到模板使用的字段 |
| | | this.toolRecords = (list || []).map(t => ({ |
| | | id: getField(t, 'id', 'ID') || `${getField(t, 'cutteR_ID') || getField(t, 'CUTTER_ID') || ''}-${getField(t, 'uP_TIME') || ''}`, |
| | | no: getField(t, 'cutteR_ID', 'CUTTER_ID', 'cutterId', 'no'), |
| | | name: getField(t, 'cutteR_NAME', 'CUTTER_NAME', 'cutterName', 'name'), |
| | | upTime: getField(t, 'uP_TIME', 'UP_TIME', 'uPTime') || '', |
| | | upCount: getField(t, 'uP_COUNT', 'UP_COUNT') ?? '', |
| | | downTime: getField(t, 'dowN_TIME', 'DOWN_TIME', 'downTime') || '', |
| | | downCount: getField(t, 'dowN_COUNT', 'DOWN_COUNT') ?? '', |
| | | useCount: getField(t, 'usE_COUNT', 'USE_COUNT') ?? '', |
| | | useLimit: getField(t, 'usE_LIMIT', 'USE_LIMIT') ?? '', |
| | | lifePercent: getField(t, 'lifE_PERCENT', 'LIFE_PERCENT') ?? '', |
| | | lifeWarn: getField(t, 'lifE_WARN', 'LIFE_WARN') ?? '', |
| | | warnStatus: getField(t, 'status', 'STATUS') || '' |
| | | })); |
| | | |
| | | // 如果后端返回了 totalCount,可以更新 total(用于分页显示) |
| | | const totalFromRes = Number(res.totalCount); |
| | | if (Number.isFinite(totalFromRes) && totalFromRes > 0) { |
| | | this.total = totalFromRes; |
| | | } else { |
| | | this.total = Number(res.data?.total ?? res.data?.totalCount ?? this.toolRecords.length) || 0; |
| | | } |
| | | } else { |
| | | if (res.status !== 0) { |
| | | this.$showMessage(res.message || '获取表单数据失败'); |
| | | return; |
| | | } |
| | | |
| | | // 兼容多种返回结构,取到数组 |
| | | const list = Array.isArray(res.data) ? res.data |
| | | : (res.data && res.data.tbBillList) ? res.data.tbBillList |
| | | : (res.data && res.data.data) ? res.data.data |
| | | : []; |
| | | |
| | | const getField = (obj, ...keys) => { |
| | | for (const k of keys) if (obj?.[k] !== undefined && obj?.[k] !== null) return obj[k]; |
| | | return null; |
| | | }; |
| | | |
| | | const parseNumber = v => { |
| | | if (v === null || v === undefined || v === '') return null; |
| | | const s = String(v).replace(/[,%%]/g, '').trim(); |
| | | const n = parseFloat(s); |
| | | return Number.isFinite(n) ? n : null; |
| | | }; |
| | | |
| | | const formatPercent = n => (n === null || n === undefined || isNaN(n)) ? '' : `${Number(n).toFixed(2)}%`; |
| | | |
| | | const mapped = (list || []).map(t => { |
| | | const upTimeRaw = getField(t, 'uP_TIME', 'UP_TIME', 'uPTime', 'UPTIME', 'UpTime'); |
| | | const downTimeRaw = getField(t, 'dowN_TIME', 'DOWN_TIME', 'downTime', 'DOWNTIME'); |
| | | const lifePercentRaw = getField(t, 'lifE_PERCENT', 'LIFE_PERCENT', 'lifePercent', 'LIFEPERCENT'); |
| | | const lifeWarnRaw = getField(t, 'lifE_WARN', 'LIFE_WARN', 'lifeWarn', 'LIFEWARN'); |
| | | |
| | | const lifePercentNum = parseNumber(lifePercentRaw); |
| | | const lifeWarnNum = parseNumber(lifeWarnRaw); |
| | | |
| | | // 预警规则:当寿命比 >= 预警值时标记 警告(根据图片示例:90.01% vs 90% 为 警告) |
| | | let warnStatus = getField(t, 'status', 'STATUS') || ''; |
| | | if (lifeWarnNum !== null && lifePercentNum !== null) { |
| | | warnStatus = (lifePercentNum >= lifeWarnNum) ? '警告' : '正常'; |
| | | } else { |
| | | // 如果后端直接提供状态字段,则保留,否则默认空 |
| | | warnStatus = warnStatus || ''; |
| | | } |
| | | |
| | | return { |
| | | id: getField(t, 'id', 'ID') || `${getField(t, 'cutteR_ID') || getField(t, 'CUTTER_ID') || ''}-${upTimeRaw || ''}`, |
| | | no: getField(t, 'cutteR_ID', 'CUTTER_ID', 'cutterId', 'no') || '', |
| | | name: getField(t, 'cutteR_NAME', 'CUTTER_NAME', 'cutterName', 'name') || '', |
| | | upTime: this.formatDateTime(upTimeRaw), |
| | | upCount: getField(t, 'uP_COUNT', 'UP_COUNT', 'upCount') ?? '', |
| | | downTime: this.formatDateTime(downTimeRaw), |
| | | downCount: getField(t, 'dowN_COUNT', 'DOWN_COUNT', 'downCount') ?? '', |
| | | useCount: getField(t, 'usE_COUNT', 'USE_COUNT', 'useCount') ?? '', |
| | | useLimit: getField(t, 'usE_LIMIT', 'USE_LIMIT', 'useLimit') ?? '', |
| | | lifePercent: formatPercent(lifePercentNum), |
| | | lifeWarn: lifeWarnNum !== null ? `${Number(lifeWarnNum).toFixed(0)}%` : (lifeWarnRaw ? String(lifeWarnRaw) : ''), |
| | | warnStatus |
| | | }; |
| | | }); |
| | | |
| | | this.toolRecords = mapped; |
| | | |
| | | // 更新 total:优先使用后端 totalCount,否则使用返回数组长度 |
| | | const totalFromRes = Number(res.totalCount); |
| | | if (Number.isFinite(totalFromRes) && totalFromRes > 0) { |
| | | this.total = totalFromRes; |
| | | } else { |
| | | this.total = Number(res.data?.total ?? res.data?.totalCount ?? this.toolRecords.length) || 0; |
| | | } |
| | | } catch (error) { |
| | | console.error('获取表单数据错误:', error); |
| | | this.$showMessage('获取数据失败,请检查网络连接'); |
| | | } |
| | | }, |
| | | formatDateTime(dateTimeStr) { |
| | | if (!dateTimeStr) return ''; |
| | | // 支持多种后端时间格式:ISO / 时间戳 / 自定义字符串 |
| | | // 优先尝试解析为 Date,失败则返回原始字符串的可读片段 |
| | | try { |
| | | // 如果是时间戳(秒或毫秒) |
| | | const s = String(dateTimeStr).trim(); |
| | | if (/^\d{10}$/.test(s)) { |
| | | const d = new Date(Number(s) * 1000); |
| | | return `${d.getMonth() + 1}-${d.getDate()} ${d.getHours()}:${String(d.getMinutes()).padStart(2, '0')}`; |
| | | } |
| | | if (/^\d{13}$/.test(s)) { |
| | | const d = new Date(Number(s)); |
| | | return `${d.getMonth() + 1}-${d.getDate()} ${d.getHours()}:${String(d.getMinutes()).padStart(2, '0')}`; |
| | | } |
| | | const date = new Date(dateTimeStr); |
| | | if (!isNaN(date.getTime())) { |
| | | return `${date.getMonth() + 1}-${date.getDate()} ${date.getHours()}:${String(date.getMinutes()).padStart(2, '0')}`; |
| | | } |
| | | // 回退:截取到日期和时间部分(常见格式) |
| | | const match = String(dateTimeStr).match(/(\d{1,4}[-\/]\d{1,2}[-\/]\d{1,2}).*?(\d{1,2}:\d{2})/); |
| | | if (match) return `${match[1].replace(/-/g, '/').replace(/^\d{4}\//, (m) => m)} ${match[2]}`; |
| | | return String(dateTimeStr); |
| | | } catch { |
| | | return String(dateTimeStr); |
| | | } |
| | | } |
| | | //// 添加辅助方法 |
| | | //formatDateTime(dateTimeStr) { |