Browse Source

1、RF不需要Dry wet分类

2、增加批量同步功能
3、不同的项目物料会对应同一个打样单号,
4、更改打样单预计完成日期同步更改package的日期,更改package的日期也需要同步更改打样单预计完成日期
5、新增baseline字段 获取第一次Delivery日期,可支持修改
7、新增一列时间差字段baseline-最新维护的Delivery&Package
ecss-tx
han\hanst 3 weeks ago
parent
commit
cf17e17064
  1. 4
      src/api/sampleTracking/sampleTracking.js
  2. 9
      src/views/modules/eam/eamProjectInfo.vue
  3. 285
      src/views/modules/sampleTracking/projectProofTracking.vue

4
src/api/sampleTracking/sampleTracking.js

@ -10,8 +10,8 @@ export const searchProjectPartTracking = data => createAPI('/sampleTracking/proj
export const saveProjectPartTracking = data => createAPI('/sampleTracking/projectPart/save', 'POST', data)
export const updateProjectPartTracking = data => createAPI('/sampleTracking/projectPart/update', 'POST', data)
export const deleteProjectPartTracking = data => createAPI('/sampleTracking/projectPart/delete', 'POST', data)
export const syncProjectPartTracking = data => createAPI('/sampleTracking/projectPart/sync', 'POST', data)
export const syncProofTracking = data => createAPI('/sampleTracking/proofTracking/sync', 'POST', data)
export const batchSyncProjectPartTracking = data => createAPI('/sampleTracking/projectPart/batchSync', 'POST', data)
export const batchSyncProofTracking = data => createAPI('/sampleTracking/proofTracking/batchSync', 'POST', data)
export const searchProofTracking = data => createAPI('/sampleTracking/proofTracking/search', 'POST', data)
export const exportProofTracking = data => createAPI('/sampleTracking/proofTracking/export', 'POST', data, 'download')

9
src/views/modules/eam/eamProjectInfo.vue

@ -1243,6 +1243,11 @@ import {updateColumnSize} from "../../../api/table";
}
return this.modalData.buDesc || ''
},
isRfBu () {
let buNoText = this.normalizeBuText(this.currentModalBuNo)
let buDescText = this.normalizeBuText(this.currentModalBuDesc)
return buNoText.indexOf('01-Label') > -1 || buNoText.indexOf('软标') > -1 || buDescText.indexOf('软标') > -1
},
isAlphaBu () {
let buNoText = this.normalizeBuText(this.currentModalBuNo)
let buDescText = this.normalizeBuText(this.currentModalBuDesc)
@ -1261,9 +1266,9 @@ import {updateColumnSize} from "../../../api/table";
isAlphaOrAntennaBu () {
return this.isAlphaBu || this.isAntennaBu
},
// Alpha / 线 /
// RF/Alpha / 线 /
isDryWetTypeOptionalBu () {
return this.isAlphaOrAntennaBu || this.isHardtagBu
return this.isAlphaOrAntennaBu || this.isHardtagBu || this.isRfBu
},
},
components: {

285
src/views/modules/sampleTracking/projectProofTracking.vue

@ -23,7 +23,7 @@
<el-form-item label="料号描述">
<el-input v-model="searchData.partDesc" clearable placeholder="请输入料号描述" style="width: 160px" />
</el-form-item>
<el-form-item label="分类">
<el-form-item v-if="searchData.buNo==='03-RFID'" label="分类">
<el-select v-model="searchData.dryWetType" clearable placeholder="全部" style="width: 100px">
<el-option v-for="item in dryWetTypeList" :key="`searchDryWet_${item}`" :label="item" :value="item" />
</el-select>
@ -62,8 +62,8 @@
<!-- <el-button type="warning" @click="toggleBatchEdit">{{ batchEditMode ? '取消修改' : '批量修改' }}</el-button>
<el-button v-if="batchEditMode" type="success" @click="saveBatchPlan">保存修改</el-button>-->
<el-button type="warning" @click="openCreateProofDialog()">新增打样</el-button>
<el-button type="success" plain :loading="syncNpiLoading" @click="syncToNpi()">同步项目物料到NPI</el-button>
<el-button type="success" plain :loading="syncProofLoading" @click="syncProofToNpi()">同步打样到NPI</el-button>
<el-button type="success" plain :loading="syncBatchNpiLoading" @click="syncBatchProjectPartToNpi()">同步项目物料到NPI</el-button>
<el-button type="success" plain :loading="syncBatchProofLoading" @click="syncBatchProofToNpi()">同步打样到NPI</el-button>
<el-button type="info" v-if="isAuth('833001005:set')" plain @click="openBuProcessConfigDialog">事业部进度设置</el-button>
<el-button type="info" v-if="isAuth('833001005:set2')" plain @click="openDefaultProcessConfigDialog">默认进度设置</el-button>
<el-tooltip style="margin-top: 2px;margin-left: 10px"
@ -86,7 +86,7 @@
@row-click="rowClick"
style="width: 100%; margin-top: 8px"
>
<!-- <el-table-column type="selection" width="45" />-->
<el-table-column type="selection" width="45" />
<el-table-column
v-for="(item, trackingColumnIndex) in visibleTrackingColumns"
:key="`${item.columnProp}_${trackingColumnIndex}`"
@ -226,8 +226,6 @@
</el-table-column>
<el-table-column label="操作" fixed="right" width="150" align="center">
<template slot-scope="scope">
<!-- <a class="action-link" @click="syncToNpi(scope.row)">同步NPI</a>-->
<!-- <a class="action-link" @click="openCreateProofDialog(scope.row)">新增打样</a>-->
<a @click="openOneKeyDialog('edit', scope.row)">修改</a>
<a class="action-link delete-link" @click="deleteProof(scope.row)">删除</a>
<a class="action-link end-link" v-if="scope.row.proofingNo && scope.row.proofingStatus !== '打样完成'" @click="finishProof(scope.row)">打样完成</a>
@ -371,8 +369,13 @@
<el-row :gutter="16">
<el-col :span="6" v-show="isOneKeyCreateFieldVisible('buNo')">
<el-form-item label="BU" required>
<el-select v-model="oneKeyForm.buNo" placeholder="请选择" style="width: 100%">
<el-option v-for="item in userBuList" :key="item.buNo" :label="item.buDesc" :value="item.buNo"></el-option>
<el-select v-model="oneKeyForm.buNo" placeholder="请选择" style="width: 100%" @change="handleOneKeyBuChange">
<el-option
v-for="item in userBuList"
:key="item.buNo"
:label="item.buDesc ? `${normalizeBuNo(item.buNo, searchData.site)}-${item.buDesc}` : normalizeBuNo(item.buNo, searchData.site)"
:value="item.buNo">
</el-option>
</el-select>
</el-form-item>
</el-col>
@ -493,14 +496,14 @@
<el-input v-model="oneKeyForm.partDesc" style="width: 100%"></el-input>
</el-form-item>
</el-col>
<el-col :span="3" v-show="isOneKeyCreateFieldVisible('partType')">
<el-col :span="isOneKeyDryWetTypeVisible()?3:6" v-show="isOneKeyCreateFieldVisible('partType')">
<el-form-item label="料号状态">
<el-select v-model="oneKeyForm.partType" placeholder="请选择" clearable style="width: 100%">
<el-option v-for="item in partTypeList" :key="item" :label="item" :value="item"></el-option>
</el-select>
</el-form-item>
</el-col>
<el-col :span="3" v-show="isOneKeyCreateFieldVisible('dryWetType')">
<el-col :span="3" v-show="isOneKeyCreateFieldVisible('dryWetType') && isOneKeyDryWetTypeVisible()">
<el-form-item label="分类">
<el-select v-model="oneKeyForm.dry_wet_type" placeholder="请选择" clearable style="width: 100%">
<el-option v-for="item in dryWetTypeList" :key="item" :label="item" :value="item"></el-option>
@ -662,7 +665,8 @@
type="date"
value-format="yyyy-MM-dd"
placeholder="选择日期"
style="width: 100%">
style="width: 100%"
@change="handleOneKeyRequiredDeliveryDateChange">
</el-date-picker>
</el-form-item>
</el-col>
@ -688,7 +692,18 @@
</div>
</el-form-item>
</el-col>
<el-col :span="isOneKeyCreateFieldVisible('requiredDeliveryDate') ? 18 : 24" v-show="isOneKeyCreateFieldVisible('remark')">
<el-col :span="6" v-show="isOneKeyCreateFieldVisible('baseline')">
<el-form-item label="Baseline">
<el-date-picker
v-model="oneKeyForm.baseline"
type="date"
value-format="yyyy-MM-dd"
placeholder="选择日期"
style="width: 100%">
</el-date-picker>
</el-form-item>
</el-col>
<el-col :span="(isOneKeyCreateFieldVisible('requiredDeliveryDate') ? 18 : 24) - (isOneKeyCreateFieldVisible('baseline') ? 6 : 0)" v-show="isOneKeyCreateFieldVisible('remark')">
<el-form-item label="备注">
<el-input v-model="oneKeyForm.remark" style="width: 100%"></el-input>
</el-form-item>
@ -991,8 +1006,8 @@ import {
searchProjectInfoTracking,
searchProjectPartTracking,
searchProofTracking,
syncProofTracking,
syncProjectPartTracking,
batchSyncProofTracking,
batchSyncProjectPartTracking,
updateProofTrackingComments,
updateProofTrackingProcess
} from '@/api/sampleTracking/sampleTracking'
@ -1252,6 +1267,34 @@ const DEFAULT_TRACKING_COLUMNS = [
columnWidth: 80,
showOverflowTooltip: false
},
{
serialNumber: 'proofTrackingTable1Baseline',
columnProp: 'baseline',
headerAlign: 'center',
align: 'center',
columnLabel: 'Baseline',
columnHidden: false,
columnImage: false,
columnSortable: false,
status: true,
fixed: '',
columnWidth: 100,
showOverflowTooltip: false
},
{
serialNumber: 'proofTrackingTable1DeliveryVariance',
columnProp: 'deliveryVariance',
headerAlign: 'center',
align: 'center',
columnLabel: 'Delivery Variance',
columnHidden: false,
columnImage: false,
columnSortable: false,
status: true,
fixed: '',
columnWidth: 110,
showOverflowTooltip: false
},
{
serialNumber: 'proofTrackingTable1TrackingStatus',
columnProp: 'trackingStatus',
@ -1386,6 +1429,7 @@ export default {
'proofingNo',
'proofingStatus',
'proofingNumber',
'baseline',
'planStartDate',
'requiredDeliveryDate',
'remark'
@ -1428,8 +1472,8 @@ export default {
dataList: [],
dataListLoading: false,
exportLoading: false,
syncNpiLoading: false,
syncProofLoading: false,
syncBatchNpiLoading: false,
syncBatchProofLoading: false,
pageIndex: 1,
pageSize: 20,
totalPage: 0,
@ -1709,14 +1753,14 @@ export default {
},
getTrackingColumnDisplayValue (row, columnProp) {
if (!row || !columnProp) {
return '-'
return ''
}
const value = row[columnProp]
return this.isBlankValue(value) ? '-' : String(value)
return this.isBlankValue(value) ? '' : String(value)
},
getTrackingRoleDisplayValue (row, nameField, valueField) {
if (!row) {
return '-'
return ''
}
const roleNameValue = row[nameField]
if (!this.isBlankValue(roleNameValue)) {
@ -1724,10 +1768,10 @@ export default {
}
const roleValue = row[valueField]
if (this.isBlankValue(roleValue)) {
return '-'
return ''
}
const displayName = this.getRoleDisplayName(roleValue)
return this.isBlankValue(displayName) ? '-' : displayName
return this.isBlankValue(displayName) ? '' : displayName
},
getSearchBuOptionList () {
return this.userBuList
@ -1904,6 +1948,14 @@ export default {
}))
this.$set(row, processCol.statusField, status)
this.$set(row, processCol.actualField, actualDate)
if (processCol.code === 'deliveryPackage') {
// Delivery&Package 使
this.$set(row, 'requiredDeliveryDate', actualDate || '')
// baseline Delivery&Package
if (!this.formatDate(row.baseline) && actualDate) {
this.$set(row, 'baseline', actualDate)
}
}
},
getAllProcessCodes () {
return this.processColumns.map(item => item.code)
@ -2002,6 +2054,10 @@ export default {
// BUsite 2_01-Label -> 01-Label
return rawBuNo.substring(splitIdx + 1)
},
isRfidBuNo (buNo) {
const normalizedBuNo = this.normalizeBuNo(buNo, this.$store.state.user.site)
return normalizedBuNo.toUpperCase() === '03-RFID'
},
getValidProcessCodes (codes, allowedCodes) {
if (!Array.isArray(codes) || codes.length === 0) {
return []
@ -2923,6 +2979,7 @@ export default {
comments: '',
planStartDate: '',
requiredDeliveryDate: '',
baseline: '',
needDate: '',
remark: ''
}
@ -3373,6 +3430,21 @@ export default {
}
this.oneKeyForm.proofingNo = matched.applyNo
this.oneKeyForm.requiredDeliveryDate = matched.expectedFinishDate || ''
this.syncOneKeyBaselineByRequiredDeliveryDate(this.oneKeyForm.requiredDeliveryDate, false)
},
handleOneKeyRequiredDeliveryDateChange (dateVal) {
this.syncOneKeyBaselineByRequiredDeliveryDate(dateVal, false)
},
syncOneKeyBaselineByRequiredDeliveryDate (requiredDeliveryDate, forceSync) {
const normalizedRequiredDate = this.formatDate(requiredDeliveryDate)
if (!normalizedRequiredDate) {
return
}
const normalizedBaseline = this.formatDate(this.oneKeyForm.baseline)
if (forceSync || !normalizedBaseline) {
// baseline Delivery&Package
this.oneKeyForm.baseline = normalizedRequiredDate
}
},
loadOneKeyProofingApplyOptions (projectNo, options) {
const queryOptions = options || {}
@ -3537,6 +3609,15 @@ export default {
site: this.getSiteByJoinedBuNo(joinedBuNo)
}
},
isOneKeyDryWetTypeVisible () {
return this.isRfidBuNo(this.oneKeyForm && this.oneKeyForm.buNo ? this.oneKeyForm.buNo : '')
},
handleOneKeyBuChange () {
// 湿 RFID BU
if (!this.isOneKeyDryWetTypeVisible()) {
this.oneKeyForm.dry_wet_type = ''
}
},
getRowDateSortTime (row, fieldList) {
if (!row || !Array.isArray(fieldList)) {
return 0
@ -3826,8 +3907,10 @@ export default {
const selectedDryWetType = this.isBlankValue(selectedPart.dry_wet_type)
? selectedPart.dryWetType
: selectedPart.dry_wet_type
if (!this.isBlankValue(selectedDryWetType)) {
if (this.isOneKeyDryWetTypeVisible() && !this.isBlankValue(selectedDryWetType)) {
this.oneKeyForm.dry_wet_type = String(selectedDryWetType).trim()
} else if (!this.isOneKeyDryWetTypeVisible()) {
this.oneKeyForm.dry_wet_type = ''
}
//
this.syncOneKeyPartRoleFields(selectedPart)
@ -3868,6 +3951,14 @@ export default {
if (!inData.priorityLevel) {
inData.priorityLevel = ''
}
if (this.oneKeyDialogMode === 'create' && this.isBlankValue(inData.baseline) && !this.isBlankValue(inData.requiredDeliveryDate)) {
// Delivery&Package baseline
inData.baseline = this.formatDate(inData.requiredDeliveryDate)
}
// 湿 RFID 使 RFID BU
if (!this.isRfidBuNo(inData.buNo)) {
inData.dry_wet_type = ''
}
//
if (!this.isBlankValue(inData.projectCreationDate)) {
inData.buildDate = inData.projectCreationDate
@ -3982,6 +4073,7 @@ export default {
comments: current.comments || '',
planStartDate: current.planStartDate || '',
requiredDeliveryDate: current.requiredDeliveryDate || '',
baseline: current.baseline || '',
needDate: project.needDate || part.needDate || current.needDate || '',
remark: part.remark || project.remark || current.remark || ''
})
@ -3999,6 +4091,9 @@ export default {
form.docEngineer2Name = this.getRoleDisplayName(form.docEngineer2)
form.ipqcHardTagName = this.getRoleDisplayName(form.ipqcHardTag)
form.cQualityEngineer7Name = this.getRoleDisplayName(form.cQualityEngineer7)
if (!this.isRfidBuNo(form.buNo)) {
form.dry_wet_type = ''
}
return form
},
openOneKeyDialog (mode, row) {
@ -4013,9 +4108,14 @@ export default {
this.oneKeyProjectNoSnapshot = ''
this.oneKeyProjectRoleBaseline = {}
this.oneKeyForm = this.getEmptyOneKeyForm()
if (this.userBuList.length > 0) {
const selectedSearchBuNo = this.getSelectedSearchBuNo()
if (selectedSearchBuNo) {
// 沿 BU
this.oneKeyForm.buNo = this.getBuOptionValue(this.searchData.site, selectedSearchBuNo)
} else if (this.userBuList.length > 0) {
this.oneKeyForm.buNo = this.userBuList[0].buNo || ''
}
this.handleOneKeyBuChange()
this.oneKeyDialogVisible = true
return
}
@ -4174,7 +4274,7 @@ export default {
this.proofDialogVisible = true
this.loadProofDialogApplyOptions(this.proofDialogData.projectNo)
},
validateSyncToNpiRow (row) {
collectSyncToNpiMissingLabels (row) {
const projectPartId = this.getTrackingProjectPartId(row)
const missingLabels = []
if (this.isBlankValue(row && row.site)) {
@ -4201,37 +4301,49 @@ export default {
if (this.isBlankValue(row && row.partDesc)) {
missingLabels.push('料号描述')
}
if (missingLabels.length > 0) {
const missingHtml = missingLabels.map(item => `- ${item}`).join('<br/>')
this.$alert(`同步到NPI前,请先完善以下字段:<br/>${missingHtml}`, '提示', {
confirmButtonText: '确定',
dangerouslyUseHTMLString: true
})
return {
passed: false,
projectPartId: projectPartId
}
}
return {
passed: true,
projectPartId: projectPartId
return missingLabels
},
getSelectedRowsForBatchSync (actionLabel) {
const rows = this.selectionRows && this.selectionRows.length > 0 ? this.selectionRows : []
if (rows.length === 0) {
this.$message.warning(`请先勾选需要${actionLabel}的记录`)
}
return rows
},
syncToNpi (row) {
const current = this.getActionRow(row)
if (!current) {
this.$message.warning('请先选择一条记录')
syncBatchProjectPartToNpi () {
const selectedRows = this.getSelectedRowsForBatchSync('同步项目物料到NPI')
if (selectedRows.length === 0) {
return
}
const syncCheck = this.validateSyncToNpiRow(current)
if (!syncCheck.passed) {
const idMap = {}
const projectPartIds = []
const invalidRows = []
selectedRows.forEach(row => {
const projectPartId = this.getTrackingProjectPartId(row)
const missingLabels = this.collectSyncToNpiMissingLabels(row)
if (!projectPartId || missingLabels.length > 0) {
invalidRows.push({
projectNo: row && row.projectNo ? row.projectNo : '-',
testPartNo: row && row.testPartNo ? row.testPartNo : '-',
missingLabels: missingLabels.length > 0 ? missingLabels : ['项目物料ID']
})
return
}
const idKey = String(projectPartId)
if (idMap[idKey]) {
return
}
idMap[idKey] = true
projectPartIds.push(projectPartId)
})
if (projectPartIds.length === 0) {
this.$message.warning('勾选记录未包含可同步的项目物料')
return
}
const projectPartId = syncCheck.projectPartId
this.currentRow = current
const projectNo = current.projectNo || '-'
const testPartNo = current.testPartNo || '-'
const confirmMsg = `确认将项目编码[${projectNo}]物料编码[${testPartNo}]同步到NPI吗?`
const invalidHint = invalidRows.length > 0
? `<br/>其中${invalidRows.length}条记录不满足同步条件,已自动跳过`
: ''
const confirmMsg = `确认批量同步项目物料到NPI吗?<br/>已勾选${selectedRows.length}条,可同步${projectPartIds.length}${invalidHint}`
this.$confirm(confirmMsg, '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
@ -4239,18 +4351,19 @@ export default {
dangerouslyUseHTMLString: true
}).then(() => {
const operator = this.$store.state.user.name
this.syncNpiLoading = true
syncProjectPartTracking({
projectPartId: projectPartId,
this.syncBatchNpiLoading = true
batchSyncProjectPartTracking({
projectPartIds: projectPartIds,
updateBy: operator,
createBy: operator,
userName: operator
}).then(({ data }) => {
if (data && data.code === 0) {
this.$message.success(`同步成功`)
const syncedCount = data.syncedCount || projectPartIds.length
this.$message.success(`批量同步成功,共${syncedCount}条项目物料`)
this.getDataList()
} else {
const failMsg = (data && data.msg) || '同步到NPI失败'
const failMsg = (data && data.msg) || '批量同步项目物料到NPI失败'
if (failMsg.indexOf('缺少以下必填项') > -1) {
this.$alert(failMsg, '同步校验未通过', {
confirmButtonText: '确定'
@ -4260,24 +4373,45 @@ export default {
}
}
}).catch(() => {
this.$message.error('同步到NPI异常')
this.$message.error('批量同步项目物料到NPI异常')
}).finally(() => {
this.syncNpiLoading = false
this.syncBatchNpiLoading = false
})
})
.catch(() => {})
}).catch(() => {})
},
syncProofToNpi (row) {
const current = this.getActionRow(row)
if (!current || !current.trackingId) {
this.$message.warning('请先选择一条打样记录')
syncBatchProofToNpi () {
const selectedRows = this.getSelectedRowsForBatchSync('同步打样到NPI')
if (selectedRows.length === 0) {
return
}
this.currentRow = current
const projectNo = current.projectNo || '-'
const testPartNo = current.testPartNo || '-'
const proofingNo = current.proofingNo || '-'
const confirmMsg = `确认将当前打样记录同步到NPI吗?<br/>项目编码:${projectNo}<br/>物料编码:${testPartNo}<br/>打样单号:${proofingNo}`
const idMap = {}
const trackingIds = []
const invalidRows = []
selectedRows.forEach(row => {
const trackingId = row && row.trackingId
if (!trackingId) {
invalidRows.push({
projectNo: row && row.projectNo ? row.projectNo : '-',
testPartNo: row && row.testPartNo ? row.testPartNo : '-',
proofingNo: row && row.proofingNo ? row.proofingNo : '-'
})
return
}
const idKey = String(trackingId)
if (idMap[idKey]) {
return
}
idMap[idKey] = true
trackingIds.push(trackingId)
})
if (trackingIds.length === 0) {
this.$message.warning('勾选记录未包含可同步的打样单')
return
}
const invalidHint = invalidRows.length > 0
? `<br/>其中${invalidRows.length}条记录缺少打样ID,已自动跳过`
: ''
const confirmMsg = `确认批量同步打样到NPI吗?<br/>已勾选${selectedRows.length}条,可同步${trackingIds.length}${invalidHint}`
this.$confirm(confirmMsg, '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
@ -4285,18 +4419,19 @@ export default {
dangerouslyUseHTMLString: true
}).then(() => {
const operator = this.$store.state.user.name
this.syncProofLoading = true
syncProofTracking({
trackingId: current.trackingId,
this.syncBatchProofLoading = true
batchSyncProofTracking({
trackingIds: trackingIds,
updateBy: operator,
createBy: operator,
userName: operator
}).then(({ data }) => {
if (data && data.code === 0) {
this.$message.success('打样同步成功')
const syncedCount = data.syncedCount || trackingIds.length
this.$message.success(`批量同步成功,共${syncedCount}条打样记录`)
this.getDataList()
} else {
const failMsg = (data && data.msg) || '同步打样到NPI失败'
const failMsg = (data && data.msg) || '批量同步打样到NPI失败'
if (failMsg.indexOf('缺少以下必填项') > -1 || failMsg.indexOf('请先同步项目') > -1 || failMsg.indexOf('请先同步项目物料') > -1) {
this.$alert(failMsg, '同步校验未通过', {
confirmButtonText: '确定'
@ -4306,9 +4441,9 @@ export default {
}
}
}).catch(() => {
this.$message.error('同步打样到NPI异常')
this.$message.error('批量同步打样到NPI异常')
}).finally(() => {
this.syncProofLoading = false
this.syncBatchProofLoading = false
})
}).catch(() => {})
},
@ -4560,6 +4695,8 @@ export default {
if (!silentSuccess) {
this.$message.success(successMsg || '工序更新成功')
}
// /
this.getDataList()
} else {
this.$message.error(data.msg || '工序更新失败')
this.getDataList()

Loading…
Cancel
Save