Commit 7b7b3751 by qinjianhui

feat: 入库申请单提交入库功能开发

parent dda34c8e
......@@ -6,6 +6,7 @@ import { LogisticBill } from '@/types/api/podMakeOrder'
import { userData } from '@/types/api/user'
import { VersionImageList } from '@/types/api/typesetting'
import { SupplierItem, WarehouseListData } from '@/types'
import { loactionData } from './warehouse'
// 获取物流公司
export function getLogisticsCompanyList() {
......@@ -75,3 +76,13 @@ export function getBaseCurrencyInfoApi() {
'factory/supplier/getBaseCurrencyInfo',
)
}
// 获取库位List
export function LocationInfoGetAll(wareHouseId?: string | number) {
return axios.get<never, BaseRespData<loactionData[]>>(
'/factoryWarehouseLocation/getByWareHouse',
{
params: { wareHouseId },
},
)
}
......@@ -100,6 +100,7 @@ export function supplierDispatchApi(data: {
warehouseId: number | string
warehouseName: string
expectDeliveryTime: string
currencyCode: string
detailsList: StockingOrderProduct[]
}) {
return axios.post<never, BaseRespData<void>>(
......
......@@ -284,14 +284,6 @@ export function warehouseInfoGetAll() {
'/factoryWarehouseInfo/getAll',
)
}
export function LocationInfoGetAll(wareHouseId?: string | number) {
return axios.get<never, BaseRespData<loactionData[]>>(
'/factoryWarehouseLocation/getByWareHouse',
{
params: { wareHouseId },
},
)
}
export function createWarehouseInventoryApi(data: WarehouseWarningData) {
return axios.post<never, BaseRespData<never>>(
......
import axios from '@/api/axios'
import { BasePaginationData, BaseRespData } from '@/types/api'
import {
LogListData,
SubmitWarehousingData,
} from '@/types/api/supply/stockingOrder'
import { LogListData } from '@/types/api/supply/stockingOrder'
import {
SearchForm,
TableData,
......@@ -11,6 +8,7 @@ import {
StockingApplyOrderDetailList,
RelatedDocumentList,
StockingApplyOrderDetailData,
LocationDataBySkuData,
} from '@/types/api/warehouse/stockingApplyOrder'
export function getStockingApplyOrderListApi(
......@@ -56,9 +54,9 @@ export function warehouseReceiptApi(id: number) {
)
}
export function submitWarehousingApi(data: SubmitWarehousingData) {
export function submitWarehousingApi(data: StockingApplyOrderDetailData) {
return axios.post<never, BaseRespData<void>>(
'factory/supply/stockingUpWarehouseApply/submitWarehousing',
'factory/supply/stockingUpWarehouseApply/submitInventory',
data,
)
}
......@@ -68,3 +66,13 @@ export function getStockingApplyOrderDetailById(id: number) {
`factory/supply/stockingUpWarehouseApply/get?id=${id}`,
)
}
export function getLocationListApi(sku: string, warehouseId: string | number) {
return axios.post<never, BaseRespData<LocationDataBySkuData[]>>(
'factoryWarehouseInventory/getBySkuAndWarehouseId',
{
sku,
warehouseId,
},
)
}
......@@ -89,7 +89,6 @@ export interface AddStockingOrderForm {
rejectReason?: string // 驳回原因
}
// 备货单商品
export interface StockingOrderProduct {
productNo?: string
warehouseSkuId?: number
......@@ -118,18 +117,3 @@ export interface LogListData {
description?: string
updateTime?: string
}
// 提交入库
export interface SubmitWarehousingItem {
id: number
buyStored: number
rejectsAmount: number
locationId?: number
}
export interface SubmitWarehousingData {
warehouseApplyId?: number
inspectorId?: number
remark?: string
itemList: SubmitWarehousingItem[]
}
......@@ -48,11 +48,14 @@ export interface StockingApplyOrderDetailList {
warehouseSkuName?: string
warehouseSkuImage?: string
shipmentQuantity?: number
buyStored?: number
rejectsAmount?: number
buyStored?: number | string
rejectsAmount?: number | string
price?: number
createTime?: string
updateTime?: string
locationId?: number
locationCode?: string | undefined
finallyShipmentQuantity?: number
}
export interface RelatedDocumentList {}
......@@ -61,7 +64,29 @@ export interface StockingApplyOrderDetailData {
warehouseApplyNo?: string
warehouseName?: string
warehouseId?: number
inspectorId?: number
checkerUserId?: number
remark?: string
checkerName?: string
detailsList: StockingApplyOrderDetailList[]
}
export interface LocationDataBySkuData {
id: number
factoryId?: number
warehouseId?: number
warehouseName?: string
locationId?: number
locationCode?: string
warehouseSku?: string
customSku?: string
skuName?: string
createTime?: string
updateTime?: string
productItem?: unknown
usableInventory?: number
image?: string
price?: number
currencyCode?: string
currencyName?: string
sumOccupyInventory?: number
}
......@@ -293,15 +293,24 @@ const handleDispatch = async () => {
text: '正在提交...',
background: 'rgba(0, 0, 0, 0.7)',
})
const {
stockingUpManageNo,
warehouseId,
warehouseName,
expectDeliveryTime,
currencyCode,
detailsList,
} = formData.value
try {
const res = await supplierDispatchApi({
manageId: currentRow.value?.id as number,
manageNo: formData.value.stockingUpManageNo as string,
warehouseId: formData.value.warehouseId as number,
warehouseName: formData.value.warehouseName as string,
expectDeliveryTime: formData.value.expectDeliveryTime as string,
manageNo: stockingUpManageNo as string,
warehouseId: warehouseId as number,
warehouseName: warehouseName as string,
expectDeliveryTime: expectDeliveryTime as string,
currencyCode: currencyCode as string,
detailsList:
formData.value.detailsList?.map((e) => ({
detailsList?.map((e) => ({
...e,
shipmentQuantity: Number(e.currentShipQuantity ?? 0),
currentShipQuantity: undefined,
......@@ -334,12 +343,18 @@ const open = async (row: TableData) => {
ElMessage.warning(res.message)
return
}
const { stockingUpManageNo, warehouseId, detailsList, warehouseName } =
res.data
const {
stockingUpManageNo,
warehouseId,
detailsList,
warehouseName,
currencyCode,
} = res.data
formData.value = {
stockingUpManageNo,
warehouseId,
warehouseName,
currencyCode,
detailsList: detailsList?.map((item) => ({
...item,
remainingQuantity: new BigNumber(item.buyAmount || 0)
......
......@@ -130,13 +130,13 @@ const stockProductsColumns = computed(() => {
},
{
label: '实际质检数',
prop: '',
prop: 'finallyShipmentQuantity',
width: 120,
align: 'right',
},
{
label: '入库待审核数',
prop: '',
prop: 'storedPending',
width: 120,
align: 'right',
},
......
......@@ -2,7 +2,7 @@
<ElDialog
v-model="visible"
title="提交入库"
width="1200px"
width="1400px"
top="10vh"
:close-on-click-modal="false"
destroy-on-close
......@@ -30,9 +30,9 @@
placeholder="自动带出"
/>
</ElFormItem>
<ElFormItem label="质检员" prop="inspectorId" class="form-item">
<ElFormItem label="质检员" prop="checkerUserId" class="form-item">
<ElSelect
v-model="formData.inspectorId"
v-model="formData.checkerUserId"
placeholder="请选择"
filterable
clearable
......@@ -52,10 +52,11 @@
</ElForm>
<div class="table-section">
<TableView
:selection-able="true"
:selectionable="true"
:serial-numberable="true"
:data="formData.detailsList"
:columns="tableColumns"
@selection-change="handleSelectionChange"
>
<template #buyStored="{ row }">
<ElInput
......@@ -81,7 +82,7 @@
style="width: 100px"
>
<ElOption
v-for="item in locationList"
v-for="item in allLocationList"
:key="item.id"
:label="item.locationCode"
:value="item.id"
......@@ -90,6 +91,11 @@
</template>
</TableView>
</div>
<div class="batch-action">
<ElButton type="primary" @click="batchSetBuyStored">
申请数量>>本次入库数量
</ElButton>
</div>
</div>
<template #footer>
<div class="dialog-footer">
......@@ -107,18 +113,20 @@ import { ref } from 'vue'
import type { FormInstance, FormRules } from 'element-plus'
import { ElMessage } from 'element-plus'
import ImageView from '@/components/ImageView.vue'
import { getUserListApi } from '@/api/common'
import { LocationInfoGetAll, loactionData } from '@/api/warehouse'
import { getUserListApi, LocationInfoGetAll } from '@/api/common'
import { loactionData } from '@/api/warehouse'
import {
getLocationListApi,
getStockingApplyOrderDetailById,
submitWarehousingApi,
} from '@/api/warehouse/stockingApplyOrder'
import {
TableData,
StockingApplyOrderDetailData,
StockingApplyOrderDetailList,
LocationDataBySkuData,
} from '@/types/api/warehouse/stockingApplyOrder'
import { userData } from '@/types/api/user'
import { BigNumber } from 'bignumber.js'
const emit = defineEmits<{
(e: 'refresh'): void
......@@ -127,9 +135,9 @@ const emit = defineEmits<{
const visible = ref(false)
const submitLoading = ref(false)
const formRef = ref<FormInstance>()
const currentRow = ref<TableData | null>(null)
const userList = ref<userData[]>([])
const locationList = ref<loactionData[]>([])
const locationList = ref<LocationDataBySkuData[]>([])
const selectedRows = ref<StockingApplyOrderDetailList[]>([])
const formData = ref<StockingApplyOrderDetailData>({
detailsList: [],
......@@ -137,7 +145,7 @@ const formData = ref<StockingApplyOrderDetailData>({
warehouseApplyNo: '',
warehouseName: '',
warehouseId: undefined,
inspectorId: undefined,
checkerUserId: undefined,
remark: '',
})
const tableColumns = ref([
......@@ -158,6 +166,7 @@ const tableColumns = ref([
{
label: '款号',
width: 140,
prop: 'productNo',
align: 'center',
},
{
......@@ -169,6 +178,7 @@ const tableColumns = ref([
{
label: '申请数量',
width: 120,
prop: 'shipmentQuantity',
align: 'right',
},
{
......@@ -187,20 +197,27 @@ const tableColumns = ref([
},
{
label: '实际质检数',
prop: '',
prop: 'finallyShipmentQuantity',
width: 100,
align: 'right',
render: (row: StockingApplyOrderDetailList) => {
const buyStored = new BigNumber(row.buyStored || 0).toNumber()
const rejectsAmount = new BigNumber(row.rejectsAmount || 0).toNumber()
return new BigNumber(buyStored).plus(rejectsAmount).toNumber()
},
},
{
label: '库位',
prop: 'locationName',
prop: 'locationId',
width: 140,
align: 'right',
slot: 'locationName',
},
])
const formRules: FormRules = {
inspectorId: [{ required: true, message: '请选择质检员', trigger: 'change' }],
checkerUserId: [
{ required: true, message: '请选择质检员', trigger: 'change' },
],
}
const loadUserList = async () => {
......@@ -214,18 +231,6 @@ const loadUserList = async () => {
}
}
const loadLocationList = async (warehouseId: number | undefined) => {
if (!warehouseId) return
try {
const res = await LocationInfoGetAll(warehouseId)
if (res.code === 200) {
locationList.value = res.data || []
}
} catch (e) {
console.error(e)
}
}
const loadDetailList = async (id: number) => {
const loading = ElLoading.service({
lock: true,
......@@ -235,6 +240,32 @@ const loadDetailList = async (id: number) => {
try {
const res = await getStockingApplyOrderDetailById(id)
if (res.code !== 200) return
if (!res.data.checkerUserId) {
res.data.checkerUserId = JSON.parse(
localStorage.getItem('user') || '{}',
).id
}
const skuList = res.data.detailsList.map((item) => item.warehouseSku)
try {
const locationRes = await getLocationListApi(
skuList.join(','),
res.data.warehouseId as string | number,
)
if (locationRes.code !== 200) return
locationList.value = locationRes.data || []
if (locationList.value.length > 0) {
res.data.detailsList.forEach((item) => {
const location = locationList.value.find(
(location) => location.warehouseSku === item.warehouseSku,
)
if (location) {
item.locationId = location.locationId
}
})
}
} catch (e) {
console.error(e)
}
formData.value = res.data
visible.value = true
} catch (e) {
......@@ -243,10 +274,26 @@ const loadDetailList = async (id: number) => {
loading.close()
}
}
const allLocationList = ref<loactionData[]>([])
const loadAllLocationList = async (
warehouseId: string | number | undefined,
) => {
if (!warehouseId) return
try {
const res = await LocationInfoGetAll(warehouseId)
if (res.code !== 200) return
allLocationList.value = res.data || []
} catch (e) {
console.error(e)
}
}
const open = async (row: TableData) => {
const open = async (row: {
id: number
warehouseId: string | number | undefined
}) => {
loadUserList()
await loadLocationList(row.warehouseId)
await loadAllLocationList(row.warehouseId)
loadDetailList(row.id)
}
......@@ -254,7 +301,20 @@ const handleCancel = () => {
visible.value = false
}
// 提交入库
const handleSelectionChange = (rows: StockingApplyOrderDetailList[]) => {
selectedRows.value = rows
}
const batchSetBuyStored = () => {
if (selectedRows.value.length === 0) {
ElMessage.warning('请先选择数据')
return
}
selectedRows.value.forEach((row) => {
row.buyStored = row.shipmentQuantity
})
}
const handleSubmit = async () => {
if (!formRef.value) return
try {
......@@ -262,27 +322,31 @@ const handleSubmit = async () => {
} catch {
return
}
const invalidItem = formData.value.detailsList.find(
(item) => (item.buyStored || 0) > (item.shipmentQuantity || 0),
)
if (invalidItem) {
ElMessage.error('入库数量不能大于申请数量')
return
for (const item of formData.value.detailsList) {
if (!item.buyStored) {
ElMessage.error(`库存SKU:${item.warehouseSku}入库数量不能为空`)
return
}
if (Number(item.buyStored) > Number(item.shipmentQuantity)) {
ElMessage.error(`库存SKU:${item.warehouseSku}入库数量不能大于申请数量`)
return
}
const locationCode = allLocationList.value.find(
(location: loactionData) => location.id === Number(item.locationId),
)?.locationCode
item.locationCode = locationCode as string | undefined
const buyStored = new BigNumber(item.buyStored || 0).toNumber()
const rejectsAmount = new BigNumber(item.rejectsAmount || 0).toNumber()
item.finallyShipmentQuantity = new BigNumber(buyStored)
.plus(rejectsAmount)
.toNumber()
}
const checkerName = userList.value.find(
(item) => item.id === formData.value.checkerUserId,
)?.account
submitLoading.value = true
try {
const submitData = {
warehouseApplyId: currentRow.value?.id,
inspectorId: formData.value.inspectorId,
remark: formData.value.remark,
itemList: formData.value.detailsList.map((item) => ({
id: item.id,
buyStored: item.buyStored || 0,
rejectsAmount: item.rejectsAmount || 0,
locationId: item.locationId,
})),
}
const res = await submitWarehousingApi(submitData)
const res = await submitWarehousingApi({ ...formData.value, checkerName })
if (res.code === 200) {
ElMessage.success('入库成功')
visible.value = false
......@@ -313,6 +377,9 @@ defineExpose({ open })
flex: 1;
overflow: hidden;
}
.batch-action {
margin-top: 10px;
}
.form-item {
flex: 0 0 auto;
margin-right: 20px;
......
......@@ -236,7 +236,7 @@ const tableColumns = computed(() => [
},
{
label: '实际到货日期',
prop: '',
prop: 'deliveryTime',
width: 160,
align: 'center',
},
......@@ -359,7 +359,10 @@ const warehouseReceipt = async (row: TableData) => {
}
const submitWarehousing = (row: TableData) => {
submitWarehousingDialogRef.value?.open(row)
submitWarehousingDialogRef.value?.open({
id: row.id,
warehouseId: row.warehouseId,
})
}
const onRefresh = () => {
......
......@@ -6,7 +6,6 @@ import {
updateLocationApi,
updateProductNoApi,
updateCustomSkuApi,
LocationInfoGetAll,
getWarehouseInventoryInfo,
factoryLogWarehouseLog,
LogListData,
......@@ -21,6 +20,7 @@ import SplitDiv from '@/components/splitDiv/splitDiv.vue'
import { filePath } from '@/api/axios.ts'
import { useEnterKeyTrigger } from '@/utils/hooks/useEnterKeyTrigger.ts'
import { getInventoryLowerLimitApi } from '@/api/externalAuth'
import { LocationInfoGetAll } from '@/api/common'
const searchForm = ref({
warehouseId: '',
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment