Browse Source

【EQI】前端暂存

web
安虹睿 19 hours ago
parent
commit
e69fbed185
  1. 13
      Web/src/api/system/customlog.js
  2. 3
      Web/src/components/elTable/index.vue
  3. 31
      Web/src/components/tablePage/index.vue
  4. 32
      Web/src/utils/common/apiTableColumns.js
  5. 45
      Web/src/utils/common/index.js
  6. 191
      Web/src/views/task/logisticsPlanLog/index.vue
  7. 191
      Web/src/views/task/productionQualityLog/index.vue
  8. 16
      Web/src/views/task/taskSub/index.vue

13
Web/src/api/system/customlog.js

@ -0,0 +1,13 @@
import request from '@/utils/request'
// 下载JSON
export function getLogJsonList(uid) {
return request({
url: `/api/customlog/getlogrequestjsonlist`,
method: 'get',
// headers:{
// 'accept':'*/*'
// },
params:{uId:uid},
})
}

3
Web/src/components/elTable/index.vue

@ -47,6 +47,7 @@
:fixed="item.fixed"
:width="item.width || props.columnWidth"
:align="item.align || props.columnAlign"
:show-overflow-tooltip="item.tooltip"
:header-align="item.headerAlign || props.columnHeaderAlign">
<template #default="scope">
<!-- 时间格式 -->
@ -143,7 +144,7 @@
<script setup>
defineOptions({ name: 'elTable' })
import { reactive, ref, onMounted } from 'vue'
import { h,reactive, ref, onMounted } from 'vue'
import { ElMessageBox, ElMessage,ElTable, ElTableColumn } from 'element-plus'
import { formatTimeStrToStr } from "@/utils/formatTime";

31
Web/src/components/tablePage/index.vue

@ -3,27 +3,27 @@
<el-card class="search-container" v-if="!props.hideSearch">
<el-form :inline="true">
<el-form-item
v-auth="props.apiName + state.searchBtnOptions['search'].auth"
v-auth="(props.authName || props.apiName) + state.searchBtnOptions['search'].auth"
v-for="(item,index) in props.searchOptions"
:key="index"
:label="item.label">
<!-- 文本 -->
<el-input
v-if="item.type == 'input'"
v-if="item.type == 'input' && !item.hide"
v-model="props.searchFilter[item.prop]"
:placeholder="item.label"
:clearable="!item.noClear"
/>
<!-- 数字 -->
<el-input-number
v-if="item.type == 'number'"
v-if="item.type == 'number' && !item.hide"
v-model="props.searchFilter[item.prop]"
:min="item.min"
:max="item.max"
/>
<!-- 时间区域 -->
<el-date-picker
v-if="item.type == 'datetimerange'"
v-if="item.type == 'datetimerange' && !item.hide"
v-model="props.searchFilter[item.prop]"
type="datetimerange"
start-placeholder="起始时间"
@ -33,7 +33,7 @@
/>
<!-- 选择框 -->
<el-select
v-if="item.type == 'select'"
v-if="item.type == 'select' && !item.hide"
v-model="props.searchFilter[item.prop]"
:filterable="!item.noSearch"
placeholder="请选择"
@ -53,7 +53,7 @@
v-for="(btn,btn_key) in props.searchButtons"
:key="btn_key"
:icon="state.searchBtnOptions[btn].icon"
v-auth="state.searchBtnOptions[btn].sAuth || props.apiName + state.searchBtnOptions[btn].auth"
v-auth="(props.authName || props.apiName) + state.searchBtnOptions[btn].auth"
:type="state.searchBtnOptions[btn].type"
@click="searchBtnHandle(btn)"
>{{state.searchBtnOptions[btn].label}}</el-button>
@ -71,6 +71,7 @@
@sortChange="sortChange"
:leftOperation="props.leftOperation"
@leftOperationHadel="leftOperationHadel"
:leftOperationColumnWidth="props.leftOperationColumnWidth"
:rightOperation="getRightOperation()"
@rightOperationHadel="rightOperationHadel"
:multipleTable="props.multipleTable"
@ -160,6 +161,11 @@
type: String,
default: null
},
// 使apiName
authName:{
type: String,
default: null
},
// api detailApigetdetailpageApigetdatapaged
apiType: {
type: String,
@ -180,6 +186,11 @@
type: Object,
default: null
},
//
leftOperationColumnWidth:{
type: Number,
default: 120
},
//
rightOperation:{
type: [Object,String],
@ -288,7 +299,7 @@
name:item,
link:true,
type:_config[item].type,
auth:props.apiName+':'+item,
auth:(props.authName || props.apiName)+':'+item,
hide:(row,scope) => {return row[props.apiRightHideConfig[item].prop] == props.apiRightHideConfig[item].ruleValue}
})
});
@ -358,7 +369,7 @@
if(formData.hasOwnProperty('updateTime')){formData.updateTime = formatDate(new Date(), "YYYY-mm-dd HH:MM:SS")}
}else{
//
let _notChange=['taskconifgure']
let _notChange=['taskconifgure','customlog']
if(_notChange.indexOf(props.apiName) < 0){
formData.remark= `修改信息:${userInfo.realName} ${formatDate(new Date(), "YYYY-mm-dd HH:MM:SS")}`
}
@ -380,12 +391,10 @@
//
function getPageParams(){
let _filters = []
console.log(383,props.searchFilter)
if(props.hideSearch){
_filters = props.searchFilter
}else{
for(let i in props.searchFilter){
console.log(388,i)
let _item = props.searchOptions.filter(item=>item.prop == i)
let _type = (_item && _item.length > 0) ? _item[0].type : null
if(props.searchFilter[i] || props.searchFilter[i] == 0){
@ -470,7 +479,7 @@
console.log(btn)
//
if(btn == 'search'){
getTableData()
getTableData(1)
}
//
else if (btn == 'create'){

32
Web/src/utils/common/apiTableColumns.js

@ -37,6 +37,16 @@ const apiTableColumns = {
{prop:'updateUser',title:'修改人',noEdit:true},
{prop:'updateTime',title:'修改时间',width:180,noEdit:true},
],
// 计划物流日志 + 生产质量日志
customlog:[
{prop:'type',title:'日志类型',width:120},
{prop:'taskName',title:'任务名称',width:160},
{prop:'version',title:'版本号',width:100},
{prop:'path',title:'存储路径',width:360,tooltip:true},
{prop:'info',title:'信息',tooltip:true,width:260},
{prop:'creationTime',title:'创建时间',width:180},
{prop:'remark',title:'备注',tooltip:true,width:200},
],
/*计划物流 */
// 整车月度生产计划2
@ -525,25 +535,25 @@ const apiTableColumns = {
{prop:'subSupplierCode',title:'分供方代码',required:true},
{prop:'subSupplierName',title:'分供方名称',required:true},
{prop:'subSupplierAddress',title:'分供方地址',required:true},
{prop:'componentCode',title:'分供方子件编码'},
{prop:'componentName',title:'分供方子件名称'},
{prop:'componentCode',title:'分供方子件编码',width:150},
{prop:'componentName',title:'分供方子件名称',width:150},
{prop:'subBatchNo',title:'子件批次号',required:true},
{prop:'subBatchNum',title:'子件批次数量',type:'number',required:true},
{prop:'subBatchNum',title:'子件批次数量',type:'number',required:true,width:140},
{prop:'subBatchSn',title:'子件SN码'},
{prop:'empCode',title:'检验人员编号',required:true},
{prop:'empName',title:'检验人员姓名',required:true},
{prop:'deviceCode',title:'检测设备编号',required:true},
{prop:'deviceName',title:'检测设备名称',required:true},
{prop:'featureName',title:'参数/特性名称',required:true},
{prop:'featureUnit',title:'参数/特性单位',required:true},
{prop:'empCode',title:'检验人员编号',required:true,width:140},
{prop:'empName',title:'检验人员姓名',required:true,width:140},
{prop:'deviceCode',title:'检测设备编号',required:true,width:140},
{prop:'deviceName',title:'检测设备名称',required:true,width:140},
{prop:'featureName',title:'参数/特性名称',required:true,width:140},
{prop:'featureUnit',title:'参数/特性单位',required:true,width:140},
{prop:'standardValue',title:'参数/特性标准值',width:180,required:true},
{prop:'featureUpper',title:'参数/特性上限值',width:180,required:true},
{prop:'featureLower',title:'参数/特性下限值',width:180,required:true},
{prop:'featureValue',title:'参数/特性实测值',width:180,required:true},
{prop:'checkNo',title:'来料检验单号',required:true},
{prop:'checkNo',title:'来料检验单号',required:true,width:140},
{prop:'checkResult',title:'批次的最终判定结果',type:'filter',options:EnumList.checkResult,width:180,required:true},
{prop:'checkTime',title:'检验时间',type:'datetime',width:180,required:true},
{prop:'samplingRate',title:'控制项要求频率',type:'number'},
{prop:'samplingRate',title:'控制项要求频率',type:'number',width:150},
{prop:'limitUpdateTime',title:'上下限更新时间',type:'datetime',width:180},
{prop:'vendorFieldDesc',title:'控制项描述'},
{prop:'vendorFieldCode',title:'控制项代码',required:true},

45
Web/src/utils/common/index.js

@ -1,3 +1,6 @@
import apiServeNames from '@/utils/common/apiServeNames'
import apiTableColumns from '@/utils/common/apiTableColumns'
// filter中空字符转义
export function getPageParamsForFilter(pageParams){
if(pageParams.filters && JSON.stringify(pageParams.filters) != "{}"){
@ -8,4 +11,46 @@ export function getPageParamsForFilter(pageParams){
}
}
return pageParams
}
// 下载字符串以json文件格式
/**
* @param {*} stringData 字符串
* @param {*} title 文件名
*/
export async function downLoadJSONByString(stringData,title){
// dada 表示要转换的字符串数据,type 表示要转换的数据格式
const blob = new Blob([stringData], {
type: 'application/json'
})
// 根据 blob生成 url链接
const objectURL = URL.createObjectURL(blob)
// 创建一个 a 标签Tag
const aTag = document.createElement('a')
// 设置文件的下载地址
aTag.href = objectURL
// 设置保存后的文件名称
aTag.download = title
// 给 a 标签添加点击事件
aTag.click()
// 释放一个之前已经存在的、通过调用 URL.createObjectURL() 创建的 URL 对象。
// 当你结束使用某个 URL 对象之后,应该通过调用这个方法来让浏览器知道不用在内存中继续保留对这个文件的引用了。
URL.revokeObjectURL(objectURL)
}
// 法根据tableName获取api
export function getColoumsByServeName(value,prop='tableName',noEdit){
let _api = null
for(let i in apiServeNames){
if(apiServeNames[i][prop] == value){
_api = i
}
}
let __colums = JSON.parse(JSON.stringify(apiTableColumns[_api]))
if(noEdit){
__colums.forEach(item => {
item.type = null
});
}
return __colums
}

191
Web/src/views/task/logisticsPlanLog/index.vue

@ -0,0 +1,191 @@
<template>
<div class="taskSubPage" v-loading="state.loading">
<!-- 主表 -->
<tablePage
:apiName="state.apiName"
:searchOptions="state.searchOptions"
:searchFilter="state.searchFilter"
@leftOperationHadel="leftOperationHadel"
:leftOperation="state.leftOperation"
:leftOperationColumnWidth="180"
:authName="'logisticsPlanLog'"
></tablePage>
<!-- 明细抽屉 -->
<el-drawer
v-if="state.drawerShow"
v-model="state.drawerShow"
:title="`详情 (${state.infoCurrentRow.taskName} - uId:${state.infoCurrentRow.uId})`"
direction="rtl"
destroy-on-close
:size="'80%'"
@close="resetInfo"
>
<div style="height: 100%">
<!-- 前端分页 -->
<elTable
style="height:calc(100% - 50px)"
:tableData="state.infoTableData"
:tableColumns="state.infoTableColumns"
:columnWidth="state.columnWidth"
></elTable>
<elPager
v-if="state.infoType == 2"
style="margin-top: 15px;float:right"
:pager="state.infoPager"
@pageSizeChange="pageSizeChange"
@pageCurrentChange="pageCurrentChange"
:isHideOnlyOne="true"
></elPager>
</div>
</el-drawer>
</div>
</template>
<script setup>
defineOptions({ name: 'logisticsPlanLog' })
import { ElMessageBox, ElMessage,ElTable, ElTableColumn } from 'element-plus'
import { reactive, ref, onMounted,nextTick } from 'vue'
import tablePage from '@/components/tablePage/index.vue'
import elTable from '@/components/elTable/index.vue'
import elPager from '@/components/elPager/index.vue'
import { getLogJsonList } from '@/api/system/customlog'
import { downLoadJSONByString,getColoumsByServeName } from '@/utils/common/index'
import EnumList from '@/utils/common/enumList'
import { useRoute } from 'vue-router'
const route = useRoute()
const state = reactive({
apiName:'customlog',
loading:false,
searchFilter: {
taskName: null,
creationTime:null,
module:'计划物流'
},
searchOptions:[
{type:'input',prop:'taskName',label:'任务名称'},
{type:'datetimerange',prop:'creationTime',label:'创建时间'},
],
leftOperation:[
{label:'查看详情',name:'showInfo',link:true,type:'primary'},
{label:'下载JSON',name:'downloadJSON',link:true,type:'warning'},
],
//
drawerShow:false,
infoTableData:null,
infoTableColumns:[],
columnWidth:null,
infoType:null,
infoAllData:null,
infoCurrentRow:null,
infoPager:{
page: 1,
pageSize: 20,
total: null,
},
})
function leftOperationHadel(btn,scope) {
//
if(btn.name == 'showInfo'){
state.infoCurrentRow = scope.row
// state.infoType = 1
let _arr1 = [
'整车月度生产计划1','整车月度生产计划2','M+6月物料需求计划','日物料需求计划',
'计划协议','采购订单','过焊装未过总装','过涂装未过总装','排序供货','看板配送单',
'退货单','奇瑞RDC共享库存','日MRP状态监控','日MRP预警推移'
]
// list state.infoType = 2
let _arr2 = [
'来料检验数据','排产数据','供应商基础信息','人员资质信息','BOM主数据',
'过程控制项质量数据','生产过程数据','产品一次合格率','工位一次合格率',
'缺陷业务数据','物料主数据','附件类数据','工艺装备','工艺','供应商共享库存',
'M+6月物料需求计划风险确认','日物料需求计划风险确认','采购订单风险确认'
]
state.loading = true
getLogJsonList(scope.row.uId)
.then(res=>{
if(_arr1.indexOf(scope.row.taskName) >= 0){
state.columnWidth = null
state.infoType = 1
state.infoTableData = [JSON.parse(res.message)]
state.infoTableColumns = [
{prop:'date',title:'date'},
{prop:'pageSize',title:'pageSize'},
{prop:'pageNum',title:'pageNum'},
{prop:'isForce',title:'isForce'},
]
}
if(_arr2.indexOf(scope.row.taskName) >= 0){
state.columnWidth = 120
state.infoType = 2
state.infoAllData = JSON.parse(res.message).list
state.infoPager.total = state.infoAllData.length
state.infoTableColumns = getColoumsByServeName(scope.row.taskName,'taskName',true)
initInfoType2Pagedata()
}
nextTick(() => {
state.drawerShow = true
})
})
.finally(() => (state.loading = false))
}
// json
if(btn.name == 'downloadJSON'){
state.loading = true
getLogJsonList(scope.row.uId)
.then(res=>{
downLoadJSONByString(res.message,`${route.meta.title}_uid=${scope.row.uId}.json`)
})
.finally(() => (state.loading = false))
}
}
// InfoType=2
function initInfoType2Pagedata() {
state.infoTableData = state.infoAllData.slice((state.infoPager.page-1) * state.infoPager.pageSize,state.infoPager.page * state.infoPager.pageSize)
}
function pageSizeChange(data) {
state.infoPager.pageSize = data
state.infoPager.page = 1
nextTick(() => {
initInfoType2Pagedata()
})
}
function pageCurrentChange(data) {
state.infoPager.page = data
nextTick(() => {
initInfoType2Pagedata()
})
}
function resetInfo(){
state.drawerShow=false
state.infoTableData=null
state.infoTableColumns=[]
state.columnWidth=null
state.infoType=null
state.infoAllData=null
state.infoPager={
page: 1,
pageSize: 20,
total: null,
}
}
</script>
<style scope lang="scss">
.taskSubPage{
height: 100%;
display: flex;
width:100%;
.el-drawer__header {
margin-bottom:0 !important
}
}
</style>

191
Web/src/views/task/productionQualityLog/index.vue

@ -0,0 +1,191 @@
<template>
<div class="taskSubPage" v-loading="state.loading">
<!-- 主表 -->
<tablePage
:apiName="state.apiName"
:searchOptions="state.searchOptions"
:searchFilter="state.searchFilter"
@leftOperationHadel="leftOperationHadel"
:leftOperation="state.leftOperation"
:leftOperationColumnWidth="180"
:authName="'productionQualityLog'"
></tablePage>
<!-- 明细抽屉 -->
<el-drawer
v-if="state.drawerShow"
v-model="state.drawerShow"
:title="`详情 (${state.infoCurrentRow.taskName} - uId:${state.infoCurrentRow.uId})`"
direction="rtl"
destroy-on-close
:size="'80%'"
@close="resetInfo"
>
<div style="height: 100%">
<!-- 前端分页 -->
<elTable
style="height:calc(100% - 50px)"
:tableData="state.infoTableData"
:tableColumns="state.infoTableColumns"
:columnWidth="state.columnWidth"
></elTable>
<elPager
v-if="state.infoType == 2"
style="margin-top: 15px;float:right"
:pager="state.infoPager"
@pageSizeChange="pageSizeChange"
@pageCurrentChange="pageCurrentChange"
:isHideOnlyOne="true"
></elPager>
</div>
</el-drawer>
</div>
</template>
<script setup>
defineOptions({ name: 'productionQualityLog' })
import { ElMessageBox, ElMessage,ElTable, ElTableColumn } from 'element-plus'
import { reactive, ref, onMounted,nextTick } from 'vue'
import tablePage from '@/components/tablePage/index.vue'
import elTable from '@/components/elTable/index.vue'
import elPager from '@/components/elPager/index.vue'
import { getLogJsonList } from '@/api/system/customlog'
import { downLoadJSONByString,getColoumsByServeName } from '@/utils/common/index'
import EnumList from '@/utils/common/enumList'
import { useRoute } from 'vue-router'
const route = useRoute()
const state = reactive({
apiName:'customlog',
loading:false,
searchFilter: {
taskName: null,
creationTime:null,
module:'生产质量'
},
searchOptions:[
{type:'input',prop:'taskName',label:'任务名称'},
{type:'datetimerange',prop:'creationTime',label:'创建时间'},
],
leftOperation:[
{label:'查看详情',name:'showInfo',link:true,type:'primary'},
{label:'下载JSON',name:'downloadJSON',link:true,type:'warning'},
],
//
drawerShow:false,
infoTableData:null,
infoTableColumns:[],
columnWidth:null,
infoType:null,
infoAllData:null,
infoCurrentRow:null,
infoPager:{
page: 1,
pageSize: 20,
total: null,
},
})
function leftOperationHadel(btn,scope) {
//
if(btn.name == 'showInfo'){
state.infoCurrentRow = scope.row
// state.infoType = 1
let _arr1 = [
'整车月度生产计划1','整车月度生产计划2','M+6月物料需求计划','日物料需求计划',
'计划协议','采购订单','过焊装未过总装','过涂装未过总装','排序供货','看板配送单',
'退货单','奇瑞RDC共享库存','日MRP状态监控','日MRP预警推移'
]
// list state.infoType = 2
let _arr2 = [
'来料检验数据','排产数据','供应商基础信息','人员资质信息','BOM主数据',
'过程控制项质量数据','生产过程数据','产品一次合格率','工位一次合格率',
'缺陷业务数据','物料主数据','附件类数据','工艺装备','工艺','供应商共享库存',
'M+6月物料需求计划风险确认','日物料需求计划风险确认','采购订单风险确认'
]
state.loading = true
getLogJsonList(scope.row.uId)
.then(res=>{
if(_arr1.indexOf(scope.row.taskName) >= 0){
state.columnWidth = null
state.infoType = 1
state.infoTableData = [JSON.parse(res.message)]
state.infoTableColumns = [
{prop:'date',title:'date'},
{prop:'pageSize',title:'pageSize'},
{prop:'pageNum',title:'pageNum'},
{prop:'isForce',title:'isForce'},
]
}
if(_arr2.indexOf(scope.row.taskName) >= 0){
state.columnWidth = 120
state.infoType = 2
state.infoAllData = JSON.parse(res.message).list
state.infoPager.total = state.infoAllData.length
state.infoTableColumns = getColoumsByServeName(scope.row.taskName,'taskName',true)
initInfoType2Pagedata()
}
nextTick(() => {
state.drawerShow = true
})
})
.finally(() => (state.loading = false))
}
// json
if(btn.name == 'downloadJSON'){
state.loading = true
getLogJsonList(scope.row.uId)
.then(res=>{
downLoadJSONByString(res.message,`${route.meta.title}_uid=${scope.row.uId}.json`)
})
.finally(() => (state.loading = false))
}
}
// InfoType=2
function initInfoType2Pagedata() {
state.infoTableData = state.infoAllData.slice((state.infoPager.page-1) * state.infoPager.pageSize,state.infoPager.page * state.infoPager.pageSize)
}
function pageSizeChange(data) {
state.infoPager.pageSize = data
state.infoPager.page = 1
nextTick(() => {
initInfoType2Pagedata()
})
}
function pageCurrentChange(data) {
state.infoPager.page = data
nextTick(() => {
initInfoType2Pagedata()
})
}
function resetInfo(){
state.drawerShow=false
state.infoTableData=null
state.infoTableColumns=[]
state.columnWidth=null
state.infoType=null
state.infoAllData=null
state.infoPager={
page: 1,
pageSize: 20,
total: null,
}
}
</script>
<style scope lang="scss">
.taskSubPage{
height: 100%;
display: flex;
width:100%;
.el-drawer__header {
margin-bottom:0 !important
}
}
</style>

16
Web/src/views/task/taskSub/index.vue

@ -33,11 +33,10 @@
<script setup>
defineOptions({ name: 'taskSub' })
import apiTableColumns from '@/utils/common/apiTableColumns'
import { ElMessageBox, ElMessage,ElTable, ElTableColumn } from 'element-plus'
import { reactive, ref, onMounted,nextTick } from 'vue'
import tablePage from '@/components/tablePage/index.vue'
import apiServeNames from '@/utils/common/apiServeNames'
import { getColoumsByServeName } from '@/utils/common/index'
const state = reactive({
apiName:'tasksub',
@ -60,21 +59,10 @@
rightOperation:'apiUpdate',
})
function getApiByTableName(tableName){
let _api = null
for(let i in apiServeNames){
if(apiServeNames[i].tableName == tableName){
console.log(apiServeNames[i].tableName,tableName)
_api = i
}
}
return _api
}
function leftOperationHadel(btn,scope) {
//
if(btn.name == 'showInfo'){
state.infoTableColumns = apiTableColumns[getApiByTableName(scope.row.tableName)]
state.infoTableColumns = getColoumsByServeName(scope.row.tableName,'tableName',true)
if(!state.infoTableColumns){
ElMessage.error(`不支持的表名: ${scope.row.tableName}`)
return

Loading…
Cancel
Save