| | |
| | | } |
| | | } |
| | | |
| | | this.columns.push({ |
| | | field: 'æä½', |
| | | title: 'æä½', |
| | | width: 90, |
| | | fixed: 'right', |
| | | align: 'center', |
| | | formatter: (row) => { |
| | | return ( |
| | | '<i style="cursor: pointer;color: #2d8cf0;"class="el-icon-view">æ¥çæç»</i>' |
| | | ); |
| | | }, |
| | | click: (row) => { |
| | | this.$refs.gridBody.open(row); |
| | | } |
| | | }); |
| | | |
| | | }, |
| | | onInited() { |
| | | //æ¡æ¶åå§åé
ç½®å |
| | |
| | | > |
| | | <div> |
| | | <!-- åæ®è¾å
¥åºåï¼æ¯ææ«ç ï¼ --> |
| | | <el-form :inline="true" :model="orderForm" style="margin-bottom: 20px; align-items: flex-end;"> |
| | | <el-form |
| | | :inline="true" |
| | | :model="orderForm" |
| | | style="margin-bottom: 20px; align-items: flex-end;" |
| | | @submit.prevent |
| | | > |
| | | <el-form-item label="åºåºåæ®:" name="outboundOrderNo"> |
| | | <el-input |
| | | v-model="orderForm.outboundOrderNo" |
| | |
| | | clearable |
| | | style="width: 220px; margin-right: 10px;" |
| | | @input="handleOutboundInput" |
| | | @keyup.enter="focusPurchaseInput" |
| | | @keyup.enter="(e) => { |
| | | e.stopPropagation(); // 黿¢äºä»¶å泡 |
| | | e.preventDefault(); // 黿¢é»è®¤è¡ä¸º |
| | | focusBarcodeInputDirectly(); |
| | | }" |
| | | ref="outboundInputRef" |
| | | ></el-input> |
| | | </el-form-item> |
| | | <el-form-item label="éè´åæ®:" name="purchaseOrderNo"> |
| | | <el-input |
| | | v-model="orderForm.purchaseOrderNo" |
| | | placeholder="请è¾å
¥ææ«æéè´åæ®å·" |
| | | placeholder="æ«ç æ¡ç åèªå¨å¡«å
" |
| | | clearable |
| | | style="width: 220px; margin-right: 10px;" |
| | | @input="handlePurchaseInput" |
| | | @keyup.enter="focusBarcodeInput" |
| | | readonly |
| | | ref="purchaseInputRef" |
| | | ></el-input> |
| | | </el-form-item> |
| | | </el-form> |
| | | |
| | | <!-- 䏿¹è¾å
¥æ¡ --> |
| | | <el-form :inline="true" :model="formData" ref="formRef" style="margin-bottom: 20px; align-items: flex-end;"> |
| | | <el-form |
| | | :inline="true" |
| | | :model="formData" |
| | | ref="formRef" |
| | | style="margin-bottom: 20px; align-items: flex-end;" |
| | | @submit.prevent |
| | | > |
| | | <el-form-item |
| | | label="æ«ææ¡ç :" |
| | | style="width: 80%" |
| | |
| | | ref="barcodeInputRef" |
| | | v-model="formData.barcode" |
| | | placeholder="è¯·ä½¿ç¨æ«ç æªæ«ææ¡ç ï¼ææå¨è¾å
¥" |
| | | @keyup.enter="handleScan" |
| | | @keydown.enter="debouncedHandleScan" |
| | | autofocus |
| | | class="custom-input" |
| | | :disabled="!orderForm.outboundOrderNo || !orderForm.purchaseOrderNo" |
| | | :disabled="!orderForm.outboundOrderNo || loading" |
| | | ></el-input> |
| | | </el-form-item> |
| | | <el-form-item> |
| | |
| | | size="small" |
| | | @click="handleScan" |
| | | class="custom-button" |
| | | :disabled="!orderForm.outboundOrderNo || !orderForm.purchaseOrderNo || loading" |
| | | :disabled="!orderForm.outboundOrderNo || loading" |
| | | > |
| | | <Search /> ç¡®è®¤æ«æ |
| | | </el-button> |
| | |
| | | </div> |
| | | </transition-group> |
| | | <div class="empty-tip" v-if="scannedBarcodes.length === 0"> |
| | | <span>ææ æ«æè®°å½ï¼è¯·å
è¾å
¥åæ®åæ«ææ¡ç </span> |
| | | <span>ææ æ«æè®°å½ï¼è¯·å
è¾å
¥åºåºåæ®åæ«ææ¡ç </span> |
| | | </div> |
| | | </el-scrollbar> |
| | | </div> |
| | |
| | | > |
| | | <Check /> æäº¤åºåº |
| | | </el-button> |
| | | <el-button type="text" size="small" @click="showDetailBox = false" class="cancel-btn" :disabled="loading"> |
| | | <el-button |
| | | type="text" |
| | | size="small" |
| | | @click="(e) => { |
| | | e.stopPropagation(); |
| | | e.preventDefault(); |
| | | showDetailBox = false; |
| | | }" |
| | | class="cancel-btn" |
| | | :disabled="loading" |
| | | > |
| | | åæ¶ |
| | | </el-button> |
| | | </div> |
| | |
| | | </template> |
| | | |
| | | <script setup> |
| | | import { ref, reactive, onMounted, nextTick } from 'vue'; |
| | | import { ref, reactive, onMounted, nextTick, watch } from 'vue'; |
| | | import { ElMessage } from 'element-plus'; |
| | | import { Search } from '@element-plus/icons-vue'; |
| | | import { Search, Check } from '@element-plus/icons-vue'; |
| | | |
| | | import VolBox from "@/components/basic/VolBox.vue"; |
| | | import http from '@/api/http'; |
| | |
| | | }); |
| | | const scannedBarcodes = ref([]); |
| | | const loading = ref(false); |
| | | // æ°å¢ï¼åå¨é¦æ¬¡æ«æçéè´åå·ï¼ç¨äºä¸è´æ§æ ¡éªï¼ |
| | | const firstPurchaseOrderNo = ref(null); |
| | | |
| | | // 模æ¿å¼ç¨ |
| | | const formRef = ref(null); |
| | |
| | | }); |
| | | }); |
| | | |
| | | // ç嬿«æå表ï¼è¥ä¸ºç©ºåéç½®é¦æ¬¡éè´åå· |
| | | watch(scannedBarcodes, (newVal) => { |
| | | if (newVal.length === 0) { |
| | | firstPurchaseOrderNo.value = null; |
| | | orderForm.purchaseOrderNo = ""; // 忥æ¸
空éè´åè¾å
¥æ¡ |
| | | } |
| | | }, { deep: true }); |
| | | |
| | | // ç®å鲿彿°ï¼æ éä¾èµlodashï¼ |
| | | const debounce = (fn, delay = 100) => { |
| | | let timer = null; |
| | | return (...args) => { |
| | | if (timer) clearTimeout(timer); |
| | | timer = setTimeout(() => { |
| | | fn.apply(this, args); |
| | | }, delay); |
| | | }; |
| | | }; |
| | | |
| | | // æå¼å¼¹çª |
| | | const open = () => { |
| | | showDetailBox.value = true; |
| | |
| | | formData.barcode = ""; |
| | | orderForm.outboundOrderNo = ""; |
| | | orderForm.purchaseOrderNo = ""; |
| | | // éç½®é¦æ¬¡éè´åå· |
| | | firstPurchaseOrderNo.value = null; |
| | | nextTick(() => { |
| | | outboundInputRef.value?.focus(); |
| | | }); |
| | |
| | | |
| | | // åºåºåè¾å
¥å¤çï¼æ«ç ææå¨è¾å
¥ï¼ |
| | | const handleOutboundInput = (value) => { |
| | | // æ«ç æªè¾å
¥é常ä¼èªå¨è§¦åenteräºä»¶ï¼è¿é主è¦å¤çæå¨è¾å
¥çæ
åµ |
| | | if (value && value.trim()) { |
| | | // å¯ä»¥å¨è¿éæ·»å åºåºåå·çæ ¼å¼éªè¯é»è¾ |
| | | // åºåºåå·æ ¼å¼éªè¯é»è¾ï¼æéä¿çï¼ |
| | | } |
| | | }; |
| | | |
| | | // éè´åè¾å
¥å¤çï¼æ«ç ææå¨è¾å
¥ï¼ |
| | | const handlePurchaseInput = (value) => { |
| | | if (value && value.trim()) { |
| | | // å¯ä»¥å¨è¿éæ·»å éè´åå·çæ ¼å¼éªè¯é»è¾ |
| | | // éè´åå·æ ¼å¼éªè¯é»è¾ï¼æéä¿çï¼ |
| | | } |
| | | }; |
| | | |
| | | // ç¦ç¹è·³è½¬å½æ° |
| | | const focusPurchaseInput = () => { |
| | | // ç´æ¥è·³è½¬å°æ¡ç è¾å
¥æ¡ï¼æ éå
å¡«éè´åï¼ |
| | | const focusBarcodeInputDirectly = () => { |
| | | if (orderForm.outboundOrderNo.trim()) { |
| | | purchaseInputRef.value?.focus(); |
| | | barcodeInputRef.value?.focus(); |
| | | } else { |
| | | ElMessage.warning("请å
è¾å
¥ææçåºåºåæ®å·"); |
| | | } |
| | | }; |
| | | |
| | | const focusBarcodeInput = () => { |
| | | if (orderForm.purchaseOrderNo.trim()) { |
| | | barcodeInputRef.value?.focus(); |
| | | } else { |
| | | ElMessage.warning("请å
è¾å
¥ææçéè´åæ®å·"); |
| | | /** |
| | | * æ ¹æ®æ¡ç æ¥è¯¢éè´åæ¥å£ï¼å®å
¨å¯¹é½ç¤ºä¾è¯·æ±æ ¼å¼ï¼ |
| | | * @param {string} barcode æ¡ç |
| | | * @returns {Promise<string>} éè´åå· |
| | | */ |
| | | const getPurchaseOrderByBarcode = async (barcode) => { |
| | | // å®å
¨æç
§ç¤ºä¾æ ¼å¼ï¼urlæ¼æ¥åæ° + 第äºä¸ªåæ°ä¼ æç¤ºææ¬ |
| | | const res = await http.post(`/api/OutboundPicking/GetPurchaseOrderByBarcode?barCode=${encodeURIComponent(barcode)}`, "æ¥è¯¢éè´åä¸..."); |
| | | |
| | | if (res.status !== true) { |
| | | throw new Error(res.message || "æ¥è¯¢éè´å失败"); |
| | | } |
| | | if (!res.data?.purchaseOrderNo) { |
| | | throw new Error("æªæ¥è¯¢å°è¯¥æ¡ç 对åºçéè´å"); |
| | | } |
| | | return res.data.purchaseOrderNo; |
| | | }; |
| | | |
| | | // æ«ææ¡ç å¤ç |
| | | // æ«ææ¡ç æ ¸å¿é»è¾ |
| | | const handleScan = async () => { |
| | | if (!formRef.value) return; |
| | | // éªè¯æ¡ç å¿
å¡« |
| | | await formRef.value.validateField('barcode'); |
| | | |
| | | const barcode = formData.barcode.trim(); |
| | | |
| | | const outboundOrderNo = orderForm.outboundOrderNo.trim(); |
| | | |
| | | // æ£æ¥æ¡ç æ¯å¦å·²æ«æ |
| | | if (scannedBarcodes.value.some(item => item.barcode === barcode)) { |
| | | ElMessage.warning(`æ¡ç ${barcode} å·²æ«æè¿ï¼è¯·å¿é夿«æ`); |
| | | formData.barcode = ""; |
| | |
| | | |
| | | try { |
| | | loading.value = true; |
| | | // è¿éä¿çäºåæçæ¡ç éªè¯æ¥å£ï¼ä½ å¯ä»¥æ ¹æ®å®é
éæ±ä¿®æ¹æä¿ç |
| | | const res = await http.post("/api/OutboundPicking/BarcodeValidate", { |
| | | outOder: orderForm.outboundOrderNo, // 注æï¼è¿éç°å¨ä¼ éçæ¯åæ®å·å符串ï¼è䏿¯ID |
| | | inOder: orderForm.purchaseOrderNo, // 注æï¼è¿éç°å¨ä¼ éçæ¯åæ®å·å符串ï¼è䏿¯ID |
| | | |
| | | // æ¥éª¤1ï¼ä»
ä¼ æ¡ç æ¥è¯¢éè´åï¼ä½¿ç¨ç¤ºä¾æ ¼å¼ç请æ±ï¼ |
| | | const purchaseOrderNo = await getPurchaseOrderByBarcode(barcode); |
| | | |
| | | // æ ¸å¿æ ¡éªï¼éè´åä¸è´æ§æ£æ¥ |
| | | if (firstPurchaseOrderNo.value) { |
| | | // é馿¬¡æ«æï¼æ ¡éªéè´åå·æ¯å¦ä¸è´ |
| | | if (purchaseOrderNo !== firstPurchaseOrderNo.value) { |
| | | throw new Error(`å½åæ¡ç 对åºçéè´åã${purchaseOrderNo}ãä¸é¦æ¬¡æ«æçéè´åã${firstPurchaseOrderNo.value}ãä¸ä¸è´ï¼ç¦æ¢æ«æï¼`); |
| | | } |
| | | } else { |
| | | // 馿¬¡æ«æï¼è®°å½éè´åå· |
| | | firstPurchaseOrderNo.value = purchaseOrderNo; |
| | | } |
| | | |
| | | // èµå¼éè´åå°è¾å
¥æ¡ |
| | | orderForm.purchaseOrderNo = purchaseOrderNo; |
| | | ElMessage.success(`æåæ¥è¯¢å°éè´åï¼${purchaseOrderNo}`); |
| | | |
| | | // æ¥éª¤2ï¼è°ç¨åææ¡ç éªè¯æ¥å£ï¼å¦é坹齿 ¼å¼å¯åæ¥ä¿®æ¹ï¼æ¤å¤ä¿çåææ ¼å¼ï¼ |
| | | const validateRes = await http.post("/api/OutboundPicking/BarcodeValidate", { |
| | | outOder: outboundOrderNo, |
| | | inOder: purchaseOrderNo, |
| | | barCode: barcode |
| | | }); |
| | | |
| | | if (res.status === true) { |
| | | if (validateRes.status === true) { |
| | | scannedBarcodes.value.push({ barcode }); |
| | | ElMessage.success("æ«ææå"); |
| | | formData.barcode = ""; |
| | | } else { |
| | | ElMessage.error("æ«æå¤±è´¥ï¼" + (res.message || 'éªè¯å¤±è´¥')); |
| | | ElMessage.error("æ«æå¤±è´¥ï¼" + (validateRes.message || 'æ¡ç éªè¯å¤±è´¥')); |
| | | } |
| | | } catch (error) { |
| | | ElMessage.error("æ«æéªè¯å¼å¸¸ï¼" + error.message); |
| | | // æè·éè´åä¸ä¸è´çé误并æç¤º |
| | | ElMessage.error(error.message); |
| | | // æ¸
空å½åè¾å
¥æ¡ï¼èç¦æ¡ç è¾å
¥æ¡ |
| | | formData.barcode = ""; |
| | | nextTick(() => barcodeInputRef.value?.focus()); |
| | | } finally { |
| | | loading.value = false; |
| | | nextTick(() => barcodeInputRef.value?.focus()); |
| | | // 强å¶èç¦æ¡ç è¾å
¥æ¡ï¼é¿å
ç¦ç¹è·³å°å¼¹çªå¤ |
| | | nextTick(() => { |
| | | if (barcodeInputRef.value) { |
| | | barcodeInputRef.value.focus(); |
| | | // æ¸
空è¾å
¥æ¡éä¸ç¶æï¼æ«ç æªå¯è½æ®çéä¸ï¼ |
| | | if (barcodeInputRef.value.input) { |
| | | barcodeInputRef.value.input.select = () => {}; |
| | | } |
| | | } |
| | | }); |
| | | } |
| | | }; |
| | | |
| | | // 另鲿åäºä»¶æ¦æªçæ«æå¤çï¼éé
æ«ç æªï¼ |
| | | const debouncedHandleScan = debounce(async (e) => { |
| | | // 黿¢äºä»¶å泡åé»è®¤è¡ä¸º |
| | | e.stopPropagation(); |
| | | e.preventDefault(); |
| | | await handleScan(); |
| | | }, 100); |
| | | |
| | | // ç§»é¤åæ¡æ«æè®°å½ |
| | | const removeItem = async (index, barcode) => { |
| | | try { |
| | | loading.value = true; |
| | | // è¿éä¿çäºåæçå 餿¡ç æ¥å£ï¼ä½ å¯ä»¥æ ¹æ®å®é
éæ±ä¿®æ¹æä¿ç |
| | | const res = await http.post("/api/OutboundPicking/DeleteBarcode", { |
| | | outOder: orderForm.outboundOrderNo, |
| | | inOder: orderForm.purchaseOrderNo, |
| | |
| | | if (res.status === true) { |
| | | scannedBarcodes.value.splice(index, 1); |
| | | ElMessage.success("å 餿å"); |
| | | // è¥å é¤åæ æ¡ç ï¼èªå¨éç½®é¦æ¬¡éè´åå·åéè´åè¾å
¥æ¡ |
| | | if (scannedBarcodes.value.length === 0) { |
| | | firstPurchaseOrderNo.value = null; |
| | | orderForm.purchaseOrderNo = ""; |
| | | } |
| | | } else { |
| | | ElMessage.error("å é¤å¤±è´¥ï¼" + (res.message || 'å é¤å¤±è´¥')); |
| | | } |
| | |
| | | |
| | | try { |
| | | loading.value = true; |
| | | // è¿éä¿çäºåæçæäº¤æ¥å£ï¼æ³¨æåæ°ç°å¨ä¼ éçæ¯åæ®å·å符串 |
| | | const res = await http.post("/api/OutboundPicking/NoStockOutSubmit", { |
| | | OutOderSubmit: orderForm.outboundOrderNo, |
| | | InOderSubmit: orderForm.purchaseOrderNo, |
| | |
| | | if (res.status === true) { |
| | | ElMessage.success("åºåºæäº¤æå"); |
| | | showDetailBox.value = false; |
| | | // æäº¤æååéç½®ç¶æ |
| | | firstPurchaseOrderNo.value = null; |
| | | scannedBarcodes.value = []; |
| | | } else { |
| | | ElMessage.error("åºåºæäº¤å¤±è´¥ï¼" + (res.message || 'æäº¤å¤±è´¥')); |
| | | } |
| | |
| | | // }); |
| | | // } |
| | | // } |
| | | // this.columns.forEach(column => { |
| | | // if (column.field == 'materielCode') { |
| | | // column.formatter = (row) => { |
| | | // var str = ''; |
| | | // var list = row.materielCode.split(','); |
| | | // for (let index = 0; index < list.length; index++) { |
| | | // str += list[index] + '<br>'; |
| | | // } |
| | | // return str = list[0] == "" ? "空箱" : str; |
| | | // } |
| | | // } |
| | | // if (column.field == 'batchNo') { |
| | | // column.formatter = (row) => { |
| | | // var str = ''; |
| | | // var list = row.batchNo.split(','); |
| | | // for (let index = 0; index < list.length; index++) { |
| | | // str += list[index] + '<br>'; |
| | | // } |
| | | // return str = list[0] == "" ? "æ " : str; |
| | | // } |
| | | // } |
| | | // if (column.field == 'materielInfo') { |
| | | // const today = new Date() |
| | | // column.formatter = (row) => { |
| | | // if (row.details.length > 0) { |
| | | // const today = new Date(); |
| | | // const closestDate = row.details |
| | | // .map(x => { |
| | | // const date = new Date(x.effectiveDate); |
| | | // const diffInDays = Math.ceil(Math.abs((today - date) / (1000 * 60 * 60 * 24))); |
| | | // return { date, diffInDays }; |
| | | // }) |
| | | // .reduce((closest, current) => (current.diffInDays < closest.diffInDays ? current : closest)) |
| | | // .date; |
| | | this.columns.forEach(column => { |
| | | // if (column.field == 'materielCode') { |
| | | // column.formatter = (row) => { |
| | | // var str = ''; |
| | | // var list = row.materielCode.split(','); |
| | | // for (let index = 0; index < list.length; index++) { |
| | | // str += list[index] + '<br>'; |
| | | // } |
| | | // return str = list[0] == "" ? "空箱" : str; |
| | | // } |
| | | // } |
| | | // if (column.field == 'batchNo') { |
| | | // column.formatter = (row) => { |
| | | // var str = ''; |
| | | // var list = row.batchNo.split(','); |
| | | // for (let index = 0; index < list.length; index++) { |
| | | // str += list[index] + '<br>'; |
| | | // } |
| | | // return str = list[0] == "" ? "æ " : str; |
| | | // } |
| | | // } |
| | | // if (column.field == 'materielInfo') { |
| | | // const today = new Date() |
| | | // column.formatter = (row) => { |
| | | // if (row.details.length > 0) { |
| | | // const today = new Date(); |
| | | // const closestDate = row.details |
| | | // .map(x => { |
| | | // const date = new Date(x.effectiveDate); |
| | | // const diffInDays = Math.ceil(Math.abs((today - date) / (1000 * 60 * 60 * 24))); |
| | | // return { date, diffInDays }; |
| | | // }) |
| | | // .reduce((closest, current) => (current.diffInDays < closest.diffInDays ? current : closest)) |
| | | // .date; |
| | | |
| | | // const daysSinceClosest = Math.ceil(Math.abs((today - closestDate) / (1000 * 60 * 60 * 24))); |
| | | // return '<span style="color: #F56C6C">' + daysSinceClosest + "天" + '</span>'; |
| | | // } else { |
| | | // return '<span style="color: #F56C6C">' + "æ ä¿è´¨æ" + '</span>'; |
| | | // } |
| | | // const daysSinceClosest = Math.ceil(Math.abs((today - closestDate) / (1000 * 60 * 60 * 24))); |
| | | // return '<span style="color: #F56C6C">' + daysSinceClosest + "天" + '</span>'; |
| | | // } else { |
| | | // return '<span style="color: #F56C6C">' + "æ ä¿è´¨æ" + '</span>'; |
| | | // } |
| | | |
| | | // } |
| | | // } |
| | | // if (column.field == 'sumStock') { |
| | | // column.formatter = (row) => { |
| | | // if (row.details.length > 0) { |
| | | // var sum = 0; |
| | | // const closestDate = row.details |
| | | // .map(x => { |
| | | // sum += (x.stockQuantity) |
| | | // }) |
| | | // return '<span style="color: #F56C6C">' + sum + row.details[0].unit + '</span>'; |
| | | // } else { |
| | | // return '<span style="color: #F56C6C">' + "1个" + '</span>'; |
| | | // } |
| | | // } |
| | | // } |
| | | if (column.field == 'sumStock') { |
| | | column.formatter = (row) => { |
| | | if (row.details.length > 0) { |
| | | var sum = 0; |
| | | const closestDate = row.details |
| | | .map(x => { |
| | | sum += (x.stockQuantity) |
| | | }) |
| | | return '<span style="color: #F56C6C">' + sum + row.details[0].unit + '</span>'; |
| | | } else { |
| | | return '<span style="color: #F56C6C">' + "1个" + '</span>'; |
| | | } |
| | | |
| | | // } |
| | | // } |
| | | // }) |
| | | } |
| | | } |
| | | if (column.field === 'orderStatistics') { |
| | | column.formatter = (row) => { |
| | | // æ ¡éªdetailsæ¯å¦åå¨ä¸ææ°æ® |
| | | if (row.details && row.details.length > 0) { |
| | | // æmaterielCodeåç»ç»è®¡stockQuantityæ»åï¼å¹¶è®°å½åä½ï¼å第ä¸ä¸ªé空åä½ï¼ |
| | | const materielSumMap = row.details.reduce((acc, item) => { |
| | | const materielCode = item.materielCode || 'æªç¥ç©æ'; |
| | | const quantity = Number(item.stockQuantity) || 0; |
| | | const unit = item.unit || ''; // è·ååä½ï¼æ å为空 |
| | | |
| | | // ç´¯å æ°é |
| | | acc[materielCode] = { |
| | | total: (acc[materielCode]?.total || 0) + quantity, |
| | | unit: acc[materielCode]?.unit || unit // ä¿ç第ä¸ä¸ªé空åä½ |
| | | }; |
| | | return acc; |
| | | }, {}); |
| | | |
| | | // æ¯ä¸ªç©æé¡¹çæç¬ç«divï¼è·¨è¡æ¾ç¤ºï¼å
å«åä½ï¼ |
| | | const displayItems = Object.entries(materielSumMap).map(([code, data]) => { |
| | | // å¤çå使¾ç¤ºï¼æåä½åå ç©ºæ ¼æ¾ç¤ºï¼æ å䏿¾ç¤º |
| | | const unitText = data.unit ? ` ${data.unit}` : ''; |
| | | return `<div style="line-height: 1.5; white-space: normal;">${code}ï¼${data.total}${unitText}</div>`; |
| | | }); |
| | | const displayContent = displayItems.join(''); |
| | | return `<div style="color: #F56C6C; white-space: normal; word-break: break-all;">${displayContent}</div>`; |
| | | } else { |
| | | return '<span style="color: #F56C6C">空箱</span>'; |
| | | } |
| | | }; |
| | | } |
| | | if (column.field == 'stockOrderNo') { |
| | | column.formatter = (row) => { |
| | | // ææç»æ°æ®æ¶å¤ç |
| | | if (row.details && row.details.length > 0) { |
| | | // æåææé空çorderNOå¹¶å»é |
| | | const uniqueOrderNOs = [...new Set( |
| | | row.details.map(item => item.orderNo).filter(no => no) // è¿æ»¤ç©ºåæ®å· |
| | | )]; |
| | | |
| | | // æææåæ®å·åæ¢è¡æ¾ç¤ºï¼å¦åæ¾ç¤ºé»è®¤ææ¬ |
| | | if (uniqueOrderNOs.length > 0) { |
| | | return `<span style="color: #F56C6C">${uniqueOrderNOs.join('<br>')}</span>`; |
| | | } else { |
| | | return '<span style="color: #F56C6C">ææ åæ®</span>'; |
| | | } |
| | | } else { |
| | | // æ æç»æ°æ®æ¶æ¾ç¤ºé»è®¤ææ¬ |
| | | return '<span style="color: #F56C6C">ææ åæ®</span>'; |
| | | } |
| | | } |
| | | } |
| | | }) |
| | | }, |
| | | onInited() { |
| | | //æ¡æ¶åå§åé
ç½®å |
| | |
| | | const searchFormOptions = ref([ |
| | | [ |
| | | { title: "æçç¼å·", field: "palletCode",type: "like" }, |
| | | // { title: "è´§ä½ç¼å·", field: "locationCode",type: "like" }, |
| | | { title: "è´§ä½ç¼å·", field: "locationCode",type: "like" }, |
| | | { title: "è´§ä½ç¶æ", field: "locationStatus" ,type: "selectList",dataKey: "locationStatusEnum",data: [],}, |
| | | { title: "åºåç¶æ", field: "stockStatus",type: "selectList",dataKey: "stockStatusEmun",data: [],}, |
| | | ], |
| | |
| | | field: "locationName", |
| | | title: "è´§ä½åç§°", |
| | | type: "string", |
| | | width: 270, |
| | | width: 150, |
| | | align: "left", |
| | | }, |
| | | { |
| | | field: "warehouseId", |
| | | title: "æå±ä»åº", |
| | | type: "string", |
| | | width: 80, |
| | | align: "left", |
| | | }, |
| | | |
| | | { |
| | | field: "roadwayNo", |
| | | title: "å··éç¼å·", |
| | |
| | | hidden:true |
| | | }, |
| | | { |
| | | field: "materielCode", |
| | | title: "æå«ç©æç¼å·", |
| | | field: "orderStatistics", |
| | | title: "æå«ç©ææç»", |
| | | type: "string", |
| | | width: 120, |
| | | width: 240, |
| | | align: "left", |
| | | }, |
| | | { |
| | | field: "sumStock", |
| | | title: "æ»åºå", |
| | | type: "string", |
| | | width: 140, |
| | | align: "left", |
| | | }, |
| | | { |
| | | field: "stockOrderNo", |
| | | title: "æå«åæ®", |
| | | type: "string", |
| | | width: 140, |
| | | align: "left", |
| | |
| | | align: "left", |
| | | }, |
| | | { |
| | | field: "enalbeStatus", |
| | | title: "è´§ä½ç¦ç¨ç¶æ", |
| | | type: "string", |
| | | width: 140, |
| | | align: "left", |
| | | bind: { key: "enableStatusEnum", data: [] }, |
| | | }, |
| | | { |
| | | field: "locationStatus", |
| | | title: "è´§ä½ç¶æ", |
| | | type: "string", |
| | | width: 140, |
| | | align: "left", |
| | | bind: { key: "locationStatusEnum", data: [] }, |
| | | }, |
| | | { |
| | | field: "locationType", |
| | | title: "è´§ä½ç±»å", |
| | | type: "string", |
| | | width: 140, |
| | | align: "left", |
| | | bind:{key: "locationTypeEnum", data: []} |
| | | }, |
| | | { |
| | | field: "stockStatus", |
| | | title: "åºåç¶æ", |
| | | type: "string", |
| | | width: 140, |
| | | align: "left", |
| | | bind:{key: "stockStatusEmun", data: []} |
| | | }, |
| | | { |
| | | field: "warehouseId", |
| | | title: "æå±ä»åº", |
| | | type: "string", |
| | | width: 80, |
| | | align: "left", |
| | | }, |
| | | { |
| | | field: "modifier", |
| | | title: "ä¿®æ¹äºº", |
| | | type: "string", |
| | |
| | | |
| | | WebResponseContent UnPalletQuantity(string orderNo); |
| | | WebResponseContent BarcodeMaterielGroup(BarcodeMaterielGroupDTO materielGroupDTO); |
| | | |
| | | /// <summary> |
| | | /// æ¡ç æ¥è¯¢å
¥åºå |
| | | /// </summary> |
| | | /// <param name="barcode"></param> |
| | | /// <returns></returns> |
| | | public WebResponseContent GetPurchaseOrderByBarcode(string barcode); |
| | | } |
| | | } |
| | |
| | | return WebResponseContent.Instance.Error(ex.Message); |
| | | } |
| | | } |
| | | |
| | | public WebResponseContent GetPurchaseOrderByBarcode(string barcode) |
| | | { |
| | | try |
| | | { |
| | | Dt_InboundOrderDetail inboundOrderDetail = _stockInfoDetailService.Db.Queryable<Dt_InboundOrderDetail>().Where(x=>x.Barcode == barcode&& x.OrderDetailStatus !=OrderDetailStatusEnum.Over.ObjToInt()).First(); |
| | | if(inboundOrderDetail == null) |
| | | { |
| | | return WebResponseContent.Instance.Error($"æªæ¾å°è¯¥æ¡ç {barcode}çå
¥åºæç»æè
æç»ç¶æå·²å
¥æºä»å®æ"); |
| | | } |
| | | Dt_InboundOrder inboundOrder = _inboundOrderRepository.QueryFirst(x => x.Id == inboundOrderDetail.OrderId && x.OrderStatus != InOrderStatusEnum.å
¥åºå®æ.ObjToInt()); |
| | | if (inboundOrder == null) |
| | | { |
| | | return WebResponseContent.Instance.Error($"该å
¥åºå{inboundOrder}ç¶æå·²å
¥æºä»å®æ"); |
| | | } |
| | | var resultData = new { purchaseOrderNo = inboundOrder.UpperOrderNo }; |
| | | |
| | | return WebResponseContent.Instance.OK("æ¥è¯¢éè´åæå", data: resultData); |
| | | } |
| | | catch(Exception ex) |
| | | { |
| | | return WebResponseContent.Instance.Error(ex.Message); |
| | | } |
| | | } |
| | | #endregion |
| | | |
| | | public WebResponseContent UnPalletQuantity(string orderNo) |
| | |
| | | using WIDESEA_Core; |
| | | using WIDESEA_Core.BaseRepository; |
| | | using WIDESEA_Core.BaseServices; |
| | | using WIDESEA_Core.Enums; |
| | | using WIDESEA_Core.Helper; |
| | | using WIDESEA_Core.HttpContextUser; |
| | | using WIDESEA_DTO.Stock; |
| | | using WIDESEA_IStockService; |
| | |
| | | |
| | | public PageGridData<StockInfoDetailWithPalletDto> GetPageData2(PageDataOptions options) |
| | | { |
| | | PageGridData<Dt_StockInfoDetail> lists = base.GetPageData (options); |
| | | // 1. è·ååºç¡åé¡µæ°æ® |
| | | PageGridData<Dt_StockInfoDetail> pageData = base.GetPageData(options); |
| | | List<Dt_StockInfoDetail> filteredDetails = pageData.Rows.ToList(); // å
æ·è´åå§æ°æ® |
| | | |
| | | List<int> stockIds = lists.Rows.Select(detail => detail.StockId).Distinct().ToList(); |
| | | var stocks= _stockinfoRepository.QueryData(x => stockIds.Contains(x.Id)).ToList(); |
| | | |
| | | if (!string.IsNullOrEmpty(options.Wheres)) |
| | | { |
| | | try |
| | | { |
| | | List<SearchParameters> searchParametersList = options.Wheres.DeserializeObject<List<SearchParameters>>(); |
| | | if (searchParametersList?.Any() == true) |
| | | { |
| | | foreach (var param in searchParametersList) |
| | | { |
| | | // å¹é
æçç¼å·æ¥è¯¢æ¡ä»¶ï¼å°ååæ®µåï¼ |
| | | if (param.Name.Equals(nameof(Dt_StockInfo.PalletCode).FirstLetterToLower(), StringComparison.OrdinalIgnoreCase) |
| | | && !string.IsNullOrEmpty(param.Value?.ToString())) |
| | | { |
| | | // ä¼åï¼æ¹éæ¥è¯¢ï¼å¦ææå¤ä¸ªæçç ï¼è¿éä¹å¯ä»¥æ©å±ï¼ |
| | | string palletCode = param.Value.ToString().Trim(); |
| | | var targetStock = _stockinfoRepository.QueryFirst(x => x.PalletCode == palletCode); |
| | | |
| | | List<StockInfoDetailWithPalletDto> dtoList = lists.Rows |
| | | // ç©ºå¼æ ¡éªï¼æªæ¾å°å¯¹åºæççåºåï¼ç´æ¥è¿æ»¤ä¸ºç©º |
| | | if (targetStock != null) |
| | | { |
| | | filteredDetails = filteredDetails.Where(x => x.StockId == targetStock.Id).ToList(); |
| | | } |
| | | else |
| | | { |
| | | filteredDetails = new List<Dt_StockInfoDetail>(); |
| | | } |
| | | break; // å个æçç æ¥è¯¢ï¼å¹é
åéåºå¾ªç¯ |
| | | } |
| | | } |
| | | } |
| | | } |
| | | catch (Exception ex) |
| | | { |
| | | } |
| | | } |
| | | |
| | | List<int> stockIds = filteredDetails.Select(detail => detail.StockId).Distinct().ToList(); |
| | | var stockDict = _stockinfoRepository.QueryData(x => stockIds.Contains(x.Id)) |
| | | .ToDictionary(x => x.Id, x => x.PalletCode ?? "æ æçç¼å·"); |
| | | |
| | | List<StockInfoDetailWithPalletDto> dtoList = filteredDetails |
| | | .Select(detail => new StockInfoDetailWithPalletDto |
| | | { |
| | | |
| | | Id = detail.Id, |
| | | StockId = detail.StockId, |
| | | MaterielCode = detail.MaterielCode, |
| | |
| | | CreateDate = detail.CreateDate, |
| | | Modifier = detail.Modifier, |
| | | ModifyDate = detail.ModifyDate, |
| | | PalletCode= stocks |
| | | .FirstOrDefault(stock => stock.Id == detail.StockId)? |
| | | .PalletCode ?? "æ æçç¼å·" |
| | | PalletCode = stockDict.TryGetValue(detail.StockId, out var palletCode) ? palletCode : "æ æçç¼å·" |
| | | }) |
| | | .ToList(); |
| | | |
| | | return new PageGridData<StockInfoDetailWithPalletDto> { Rows = dtoList, Total = lists.Total, Summary = lists.Summary }; |
| | | return new PageGridData<StockInfoDetailWithPalletDto> |
| | | { |
| | | Rows = dtoList, |
| | | Total = pageData.Total, |
| | | Summary = pageData.Summary |
| | | }; |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | |
| | | using WIDESEA_Core; |
| | | using WIDESEA_Core.BaseRepository; |
| | | using WIDESEA_Core.DB.Models; |
| | | using WIDESEA_Core.Enums; |
| | | using WIDESEA_Core.Helper; |
| | | //using WIDESEA_Core.HostedService; |
| | | using WIDESEA_Core.Utilities; |
| | |
| | | |
| | | public virtual PageGridData<StockViewDTO> GetPageData(PageDataOptions options) |
| | | { |
| | | string where = options.ValidatePageOptions(typeof(StockViewDTO).GetProperties()); |
| | | //è·åæåºå段 |
| | | //Dictionary<string, OrderByType> orderbyDic = options.GetPageDataSort(typeof(StockViewDTO).GetProperties()); |
| | | //List<OrderByModel> orderByModels = new List<OrderByModel>(); |
| | | //foreach (var item in orderbyDic) |
| | | //{ |
| | | // OrderByModel orderByModel = new OrderByModel() |
| | | // { |
| | | // FieldName = item.Key, |
| | | // OrderByType = item.Value |
| | | // }; |
| | | // orderByModels.Add(orderByModel); |
| | | //} |
| | | int totalCount = 0; |
| | | |
| | | ISugarQueryable<Dt_StockInfo> sugarQueryable1 = _dbBase.Queryable<Dt_StockInfo>().Includes(x=>x.Details); |
| | | ISugarQueryable<Dt_LocationInfo> sugarQueryable = _dbBase.Queryable<Dt_LocationInfo>(); |
| | | ISugarQueryable<Dt_StockInfoDetail> sugarQueryable2 = _dbBase.Queryable<Dt_StockInfoDetail>(); |
| | | |
| | | |
| | | List<StockViewDTO> list = sugarQueryable1.InnerJoin(sugarQueryable, (b, a) => a.LocationCode == b.LocationCode).WhereIF(!string.IsNullOrEmpty(where), where).Select((b, a) => new StockViewDTO |
| | | try |
| | | { |
| | | LocationCode = b.LocationCode, |
| | | Column = a.Column, |
| | | CreateDate = b.CreateDate, |
| | | Creater = b.Creater, |
| | | Depth = a.Depth, |
| | | EnalbeStatus = a.EnableStatus, |
| | | Layer = a.Layer, |
| | | LocationName = a.LocationName, |
| | | LocationStatus = a.LocationStatus, |
| | | LocationType = a.LocationType, |
| | | Modifier = b.Modifier, |
| | | ModifyDate = b.ModifyDate, |
| | | PalletCode = b.PalletCode, |
| | | StockRemark = b.Remark, |
| | | RoadwayNo = a.RoadwayNo, |
| | | Row = a.Row, |
| | | StockId = b.Id, |
| | | StockStatus = b.StockStatus, |
| | | Details = b.Details, |
| | | }).ToPageList(options.Page, options.Rows, ref totalCount); |
| | | ISugarQueryable<Dt_StockInfo> sugarQueryable1 = _dbBase.Queryable<Dt_StockInfo>().Includes(x => x.Details); |
| | | if (!string.IsNullOrEmpty(options.Wheres)) |
| | | { |
| | | try |
| | | { |
| | | List<SearchParameters> searchParametersList = options.Wheres.DeserializeObject<List<SearchParameters>>(); |
| | | if (searchParametersList?.Any() == true) |
| | | { |
| | | foreach (var param in searchParametersList) |
| | | { |
| | | switch (param.Name) |
| | | { |
| | | case var name when name == nameof(Dt_StockInfoDetail.MaterielCode).FirstLetterToLower(): |
| | | if (!string.IsNullOrEmpty(param.Value?.ToString())) |
| | | { |
| | | sugarQueryable1 = sugarQueryable1 |
| | | .Where(x => x.Details.Any(v => v.MaterielCode.Contains(param.Value.ToString()))); |
| | | } |
| | | break; |
| | | case var name when name == nameof(Dt_StockInfoDetail.BatchNo).FirstLetterToLower(): |
| | | if (!string.IsNullOrEmpty(param.Value?.ToString())) |
| | | { |
| | | sugarQueryable1 = sugarQueryable1 |
| | | .Where(x => x.Details.Any(v => v.BatchNo.Contains(param.Value.ToString()))); |
| | | } |
| | | break; |
| | | |
| | | case var name when name == nameof(Dt_StockInfo.LocationCode).FirstLetterToLower(): |
| | | if (!string.IsNullOrEmpty(param.Value?.ToString())) |
| | | { |
| | | sugarQueryable1 = sugarQueryable1 |
| | | .Where(x => x.LocationCode == param.Value.ToString()); |
| | | } |
| | | break; |
| | | case var name when name == nameof(Dt_StockInfo.CreateDate).FirstLetterToLower(): |
| | | if (DateTime.TryParse(param.Value?.ToString(), out DateTime minDate)) |
| | | { |
| | | LinqExpressionType expressionType = param.DisplayType.GetLinqCondition(); |
| | | if (expressionType == LinqExpressionType.ThanOrEqual) |
| | | { |
| | | sugarQueryable1 = sugarQueryable1.Where(x => x.CreateDate >= minDate); |
| | | } |
| | | else if (expressionType == LinqExpressionType.LessThanOrEqual) |
| | | { |
| | | sugarQueryable1 = sugarQueryable1.Where(x => x.CreateDate <= minDate); |
| | | } |
| | | } |
| | | break; |
| | | } |
| | | } |
| | | } |
| | | } |
| | | catch (Exception ex) |
| | | { |
| | | } |
| | | } |
| | | EntityProperties.ValidatePageOptions(options, ref sugarQueryable1); |
| | | ISugarQueryable<Dt_LocationInfo> sugarQueryable = _dbBase.Queryable<Dt_LocationInfo>(); |
| | | ISugarQueryable<StockViewDTO> list = sugarQueryable1.InnerJoin(sugarQueryable, (b, a) => a.LocationCode == b.LocationCode).Select((b, a) => new StockViewDTO |
| | | { |
| | | LocationCode = b.LocationCode, |
| | | Column = a.Column, |
| | | WarehouseId = b.WarehouseId, |
| | | CreateDate = b.CreateDate, |
| | | Creater = b.Creater, |
| | | Depth = a.Depth, |
| | | EnalbeStatus = a.EnableStatus, |
| | | Layer = a.Layer, |
| | | LocationName = a.LocationName, |
| | | LocationStatus = a.LocationStatus, |
| | | LocationType = a.LocationType, |
| | | Modifier = b.Modifier, |
| | | ModifyDate = b.ModifyDate, |
| | | PalletCode = b.PalletCode, |
| | | StockRemark = b.Remark, |
| | | RoadwayNo = a.RoadwayNo, |
| | | Row = a.Row, |
| | | StockId = b.Id, |
| | | StockStatus = b.StockStatus, |
| | | Details = b.Details, |
| | | }); |
| | | int totalCount = 0; |
| | | var stockViewDTOs = list.ToPageList(options.Page, options.Rows, ref totalCount); |
| | | return new PageGridData<StockViewDTO>(totalCount, stockViewDTOs); |
| | | |
| | | return new PageGridData<StockViewDTO>(totalCount, list); |
| | | |
| | | } |
| | | catch (Exception ex) |
| | | { |
| | | } |
| | | return new PageGridData<StockViewDTO>(); |
| | | } |
| | | |
| | | public virtual object GetDetailPage(PageDataOptions pageData) |
| | |
| | | using WIDESEA_DTO.System; |
| | | using WIDESEA_ISystemService; |
| | | using WIDESEA_Model.Models; |
| | | using WIDESEA_Model.Models.Basic; |
| | | |
| | | namespace WIDESEA_SystemService |
| | | { |
| | |
| | | { |
| | | switch (key) |
| | | { |
| | | default: |
| | | return result; |
| | | case "warehouses": |
| | | { |
| | | List<object> data = new List<object>(); |
| | | |
| | | { |
| | | List<Dt_WarehouseArea> warehouses = BaseDal.Db.Queryable<Dt_WarehouseArea>().ToList(); |
| | | int index = 0; |
| | | foreach (var item in warehouses) |
| | | { |
| | | data.Add(new { key = item.Code, value = item.Name }); |
| | | index++; |
| | | } |
| | | } |
| | | |
| | | result = new VueDictionaryDTO { DicNo = key, Config = "", Data = data }; |
| | | } |
| | | break; |
| | | case "locationTypes": |
| | | { |
| | | List<object> data = new List<object>(); |
| | | |
| | | { |
| | | List<Dt_LocationType> warehouses = BaseDal.Db.Queryable<Dt_LocationType>().ToList(); |
| | | int index = 0; |
| | | foreach (var item in warehouses) |
| | | { |
| | | data.Add(new { key = item.LocationType, value = item.LocationTypeDesc }); |
| | | index++; |
| | | } |
| | | } |
| | | |
| | | result = new VueDictionaryDTO { DicNo = key, Config = "", Data = data }; |
| | | } |
| | | break; |
| | | case "stockStatusEmun": |
| | | { |
| | | List<object> data = new List<object>(); |
| | | Type type = typeof(StockStatusEmun); |
| | | List<int> enums = Enum.GetValues(typeof(StockStatusEmun)).Cast<int>().ToList(); |
| | | int index = 0; |
| | | foreach (var item in enums) |
| | | { |
| | | FieldInfo? fieldInfo = typeof(StockStatusEmun).GetField(((StockStatusEmun)item).ToString()); |
| | | DescriptionAttribute? description = fieldInfo.GetCustomAttribute<DescriptionAttribute>(); |
| | | if (description != null) |
| | | { |
| | | data.Add(new { key = item.ToString(), value = description.Description }); |
| | | } |
| | | else |
| | | { |
| | | data.Add(new { key = item.ToString(), value = item.ToString() }); |
| | | } |
| | | index++; |
| | | } |
| | | |
| | | result = new VueDictionaryDTO { DicNo = key, Config = "", Data = data }; |
| | | } |
| | | break; |
| | | } |
| | | return result; |
| | | } |
| | | catch (Exception ex) |
| | | { |
| | |
| | | //å½åç¨æ·çæé |
| | | List<Permissions> permissions = _MenuService.GetPermissions(App.User.RoleId); |
| | | |
| | | List<int> menuIds = _MenuService.Repository.QueryData(x => x.MenuId, x => x.MenuType == 1); |
| | | |
| | | List<int> originalMeunIds = new List<int>(); |
| | | //被åé
è§è²çæé |
| | | List<Sys_RoleAuth> roleAuths = _RoleAuthService.Repository.QueryData(x => x.RoleId == roleId && menuIds.Contains(x.MenuId)); |
| | | List<Sys_RoleAuth> roleAuths = _RoleAuthService.Repository.QueryData(x => x.RoleId == roleId); |
| | | List<Sys_RoleAuth> updateAuths = new List<Sys_RoleAuth>(); |
| | | List<Sys_RoleAuth> addAuths = new List<Sys_RoleAuth>(); |
| | | foreach (UserPermissionDTO x in userPermissions) |
| | | { |
| | | Permissions per = permissions.FirstOrDefault(p => p.MenuId == x.Id); |
| | |
| | | var auth = roleAuths.Where(r => r.MenuId == x.Id).Select(s => new { s.AuthId, s.AuthValue, s.MenuId }).FirstOrDefault(); |
| | | string newAuthValue = string.Join(",", arr); |
| | | //æé没æåçåååä¸å¤ç |
| | | if (auth == null || auth.AuthValue != newAuthValue) |
| | | if (auth == null) |
| | | { |
| | | addAuths.Add(new Sys_RoleAuth() |
| | | { |
| | | RoleId = roleId, |
| | | MenuId = x.Id, |
| | | AuthValue = string.Join(",", arr), |
| | | AuthId = auth == null ? 0 : auth.AuthId, |
| | | ModifyDate = DateTime.Now, |
| | | Modifier = App.User.UserName, |
| | | CreateDate = DateTime.Now, |
| | | Creater = App.User.UserName |
| | | }); |
| | | } |
| | | else if (auth.AuthValue != newAuthValue) |
| | | { |
| | | updateAuths.Add(new Sys_RoleAuth() |
| | | { |
| | |
| | | //æ´æ°æé |
| | | _RoleAuthService.Repository.UpdateData(updateAuths); |
| | | //æ°å¢çæé |
| | | _RoleAuthService.Repository.AddData(updateAuths); |
| | | _RoleAuthService.Repository.AddData(addAuths); |
| | | |
| | | //è·åæéåæ¶çæé |
| | | int[] authIds = roleAuths.Where(x => userPermissions.Select(u => u.Id) |
| | |
| | | { |
| | | return await Service.NoStockOutSubmit(noStockOutSubmit); |
| | | } |
| | | |
| | | [HttpPost, HttpGet, Route("GetPurchaseOrderByBarcode"), AllowAnonymous] |
| | | public WebResponseContent GetPurchaseOrderByBarcode(string barcode) |
| | | { |
| | | return Service.GetPurchaseOrderByBarcode(barcode); |
| | | } |
| | | } |
| | | } |