feat(inventory): 实现出库单生成功能

- 新增出库对话框组件,支持产品与仓库信息展示
- 实现仓库库存选择与出库数量输入功能
- 添加发货信息填写与验证逻辑
- 集成出库单创建接口并处理响应结果
- 提供出库单详情查看与撤销功能- 支持订单执行状态更新与签收文件上传下载
dev_1.0.0
chenhao 2025-11-17 16:55:18 +08:00
parent bb35f25900
commit a3e2a95fc6
5 changed files with 925 additions and 0 deletions

View File

@ -0,0 +1,265 @@
<template>
<el-dialog :title="title" :visible.sync="open" width="80%" append-to-body @close="cancel" class="checkout-dialog">
<el-form ref="form" :model="form" :rules="rules" label-width="120px">
<el-card class="box-card">
<div slot="header" class="clearfix">
<span>产品与出库信息</span>
</div>
<el-row>
<el-col :span="8">
<el-form-item label="产品编码:">{{ product.productCode }}</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="产品型号:">{{ product.model }}</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="制造商:">{{ product.vendorName }}</el-form-item>
</el-col>
</el-row>
</el-card>
<el-card class="box-card" style="margin-top: 20px;">
<div slot="header" class="clearfix">
<span>仓库信息</span>
</div>
<el-table :data="warehouseList" v-loading="loading">
<el-table-column label="仓库" prop="warehouseName" />
<el-table-column label="实时库存" prop="availableCount" />
<el-table-column label="本次提交出库">
<template slot-scope="scope">
<el-input-number
v-model="scope.row.confirmQuantity"
:min="0"
@change="handleQuantityChange"
controls-position="right"
size="small"
></el-input-number>
</template>
</el-table-column>
</el-table>
</el-card>
<el-card class="box-card" style="margin-top: 20px;">
<div slot="header" class="clearfix">
<span>发货信息</span>
</div>
<el-row>
<div style="display: flex; align-items: center; gap: 24px; margin-bottom: 18px;">
<el-form-item label="应出库(台):" style="margin-bottom: 0;">
<span>{{ outQuantityInfo.should }}</span>
</el-form-item>
<el-form-item label="已提交出库(台):" style="margin-bottom: 0;">
<span>{{ outQuantityInfo.submitted }}</span>
</el-form-item>
<el-form-item label="本次提交出库(台):" label-width="200px" style="margin-bottom: 0;">
<span style="font-weight: bold;">{{ totalConfirmQuantity }}</span>
</el-form-item>
</div>
</el-row>
<el-row>
<el-col :span="24">
<el-form-item label="收货地址" prop="contactAddress">
<el-input v-model="form.contactAddress" placeholder="请输入收货地址" />
</el-form-item>
</el-col>
</el-row>
<el-row>
<el-col :span="12">
<el-form-item label="联系人" prop="contactPerson">
<el-input v-model="form.contactPerson" placeholder="请输入联系人" />
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="联系电话" prop="contactPhone">
<el-input v-model="form.contactPhone" placeholder="请输入联系电话" />
</el-form-item>
</el-col>
</el-row>
<el-row>
<el-col :span="24">
<el-form-item label="要求发货时间" prop="deliveryTime">
<el-radio-group v-model="form.deliveryTimeType" @change="handleDeliveryTimeTypeChange">
<el-radio label="0">立即发货</el-radio>
<el-radio label="1">自定义</el-radio>
</el-radio-group>
<el-date-picker
v-if="form.deliveryTimeType === '1'"
v-model="form.deliveryTime"
type="date"
placeholder="选择日期"
value-format="yyyy-MM-dd"
style="margin-left: 20px;"
></el-date-picker>
</el-form-item>
</el-col>
</el-row>
</el-card>
</el-form>
<div slot="footer" class="dialog-footer">
<el-button type="primary" @click="submitForm"> </el-button>
<el-button @click="cancel"> </el-button>
</div>
</el-dialog>
</template>
<script>
import { getCheckOutPreview, addOuter } from "@/api/inventory/execution";
export default {
name: "CheckoutDialog",
props: {
orderInfo: {
type: Object,
default: () => ({})
}
},
data() {
return {
title: "生成出库单",
open: false,
loading: false,
product: {},
warehouseList: [],
totalConfirmQuantity: 0,
outQuantityInfo: {
should: 0,
submitted: 0
},
form: {
orderCode: null,
productCode: null,
quantity: 0,
contactAddress: null,
contactPerson: null,
contactPhone: null,
deliveryTimeType: '0',
deliveryTime: null,
detailList: []
},
rules: {
contactAddress: [{ required: true, message: "收货地址不能为空", trigger: "blur" }],
contactPerson: [{ required: true, message: "联系人不能为空", trigger: "blur" }],
contactPhone: [{ required: true, message: "联系电话不能为空", trigger: "blur" }],
}
};
},
methods: {
//
show(product) {
this.reset();
this.product = product;
this.form.orderCode = this.orderInfo.orderCode;
this.form.productCode = product.productCode;
this.form.contactAddress = this.orderInfo.notifierAddress;
this.form.contactPerson = this.orderInfo.notifier;
this.form.contactPhone = this.orderInfo.notifierPhone;
this.handleDeliveryTimeTypeChange('0'); //
this.outQuantityInfo.should = product.quantity;
this.outQuantityInfo.submitted = Number(product.generatedQuantity) + Number(product.confirmQuantity);
const params = {
productCode: product.productCode,
quantity: Number(product.quantity) - this.outQuantityInfo.submitted
};
this.loading = true;
this.open = true;
getCheckOutPreview(params).then(response => {
this.warehouseList = response.data.map(item => {
item.confirmQuantity = item.confirmQuantity || 0;
return item;
});
this.handleQuantityChange();
this.loading = false;
}).catch(() => {
this.loading = false;
});
},
//
reset() {
this.product = {};
this.warehouseList = [];
this.totalConfirmQuantity = 0;
this.outQuantityInfo = { should: 0, submitted: 0 };
this.form = {
orderCode: null,
productCode: null,
quantity: 0,
contactAddress: null,
contactPerson: null,
contactPhone: null,
deliveryTimeType: '0',
deliveryTime: null,
detailList: []
};
this.resetForm("form");
},
//
cancel() {
this.open = false;
this.reset();
},
//
handleQuantityChange() {
this.totalConfirmQuantity = this.warehouseList.reduce((sum, item) => {
return sum + (Number(item.confirmQuantity) || 0);
}, 0);
},
//
handleDeliveryTimeTypeChange(val) {
if (val === '0') {
this.form.deliveryTime = this.parseTime(new Date(), '{y}-{m}-{d}');
} else {
this.form.deliveryTime = null;
}
},
//
submitForm() {
this.$refs["form"].validate(valid => {
if (valid) {
if (this.totalConfirmQuantity <= 0) {
this.$modal.msgError("本次提交出库数量应大于0");
return;
}
const remainingQuantity = this.outQuantityInfo.should - this.outQuantityInfo.submitted;
if (this.totalConfirmQuantity > remainingQuantity) {
this.$modal.msgError("本次提交出库数量不能大于应出库数量");
return;
}
this.form.quantity = this.totalConfirmQuantity;
this.form.detailList = this.warehouseList
.filter(item => item.confirmQuantity > 0)
.map(item => ({
warehouseId: item.warehouseId,
quantity: item.confirmQuantity
}));
const detailQuantitySum = this.form.detailList.reduce((sum, item) => {
return sum + (Number(item.quantity) || 0);
}, 0);
if (this.form.quantity !== detailQuantitySum) {
this.$modal.msgError("本次出库数量与仓库明细出库数量不一致,请检查。");
return;
}
addOuter(this.form).then(response => {
this.$modal.msgSuccess("生成出库单成功");
this.open = false;
this.$emit("success");
});
}
});
}
}
};
</script>
<style scoped>
.checkout-dialog >>> .el-dialog__body {
max-height: calc(100vh - 200px); /* 视口高度减去头部和底部的高度 */
overflow-y: auto; /* 当内容超出时显示垂直滚动条 */
}
</style>

View File

@ -0,0 +1,119 @@
<template>
<el-drawer :title="title" :visible.sync="open" size="1000px" append-to-body @close="cancel">
<el-form ref="form" :model="form" label-width="120px">
<el-card class="box-card">
<div slot="header" class="clearfix">
<span>出库单信息</span>
</div>
<el-row>
<el-col :span="12">
<el-form-item label="出库单号:">{{ form.outerCode }}</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="出库时间:">{{ parseTime(form.createTime, '{y}-{m}-{d} {h}:{i}:{s}') }}</el-form-item>
</el-col>
</el-row>
<el-row>
<el-col :span="8">
<el-form-item label="产品编码:">{{ form.productCode }}</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="产品型号:">{{ form.model }}</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="制造商:">{{ form.vendorName }}</el-form-item>
</el-col>
</el-row>
</el-card>
<el-card class="box-card" style="margin-top: 20px;">
<div slot="header" class="clearfix">
<span>仓库信息</span>
</div>
<el-table :data="warehouseList" v-loading="loading">
<el-table-column label="仓库" prop="warehouseName" />
<el-table-column label="本次提交出库" prop="quantity" />
</el-table>
</el-card>
<el-card class="box-card" style="margin-top: 20px;">
<div slot="header" class="clearfix">
<span>发货信息</span>
</div>
<el-row>
<el-col :span="24">
<el-form-item label="本次提交出库(台):">
<span style="font-weight: bold;">{{ form.quantity }}</span>
</el-form-item>
</el-col>
</el-row>
<el-row>
<el-col :span="24">
<el-form-item label="收货地址:">{{ form.contactAddress }}</el-form-item>
</el-col>
</el-row>
<el-row>
<el-col :span="12">
<el-form-item label="联系人:">{{ form.contactPerson }}</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="联系电话:">{{ form.contactPhone }}</el-form-item>
</el-col>
</el-row>
<el-row>
<el-col :span="24">
<el-form-item label="要求发货时间:">
<span>{{ form.deliveryTimeType === '0' ? '立即发货' : parseTime(form.deliveryTime, '{y}-{m}-{d}') }}</span>
</el-form-item>
</el-col>
</el-row>
</el-card>
</el-form>
<div slot="footer" class="dialog-footer">
<el-button @click="cancel"> </el-button>
</div>
</el-drawer>
</template>
<script>
import { getOuter } from "@/api/inventory/execution"; // Assuming getOuter is in the same API file
export default {
name: "OuterDetailDialog",
data() {
return {
title: "出库单详情",
open: false,
loading: false,
form: {},
warehouseList: []
};
},
methods: {
//
show(id) {
this.reset();
this.open = true;
this.loading = true;
getOuter(id).then(response => {
this.form = response.data;
this.warehouseList = response.data.warehouseInfoList;
this.loading = false;
}).catch(() => {
this.loading = false;
});
},
//
reset() {
this.form = {};
this.warehouseList = [];
this.resetForm("form");
},
//
cancel() {
this.open = false;
this.reset();
}
}
};
</script>

View File

@ -0,0 +1,205 @@
<template xmlns="http://www.w3.org/1999/html">
<div class="app-container">
<el-form ref="form" :model="form" :rules="rules" label-width="120px">
<el-card class="box-card">
<div slot="header" class="clearfix">
<el-button icon="el-icon-back" type="text" @click="cancel"></el-button>
<br/>
<span>订单信息</span>
</div>
<el-row>
<order-info
:order-data.sync="form"
layout="dialog"
:is-readonly="true"
/>
</el-row>
</el-card>
</el-form>
<el-card class="box-card" style="margin-top: 20px;">
<div slot="header" class="clearfix">
<span>产品信息</span>
</div>
<el-table :data="productDetailList">
<el-table-column label="序号" type="index" width="55" align="center" />
<el-table-column label="产品编码" prop="productCode" />
<el-table-column label="产品型号" prop="model" />
<el-table-column label="应出库" prop="quantity" />
<el-table-column label="已确认出库" prop="confirmQuantity" />
<el-table-column label="已生成出库" prop="generatedQuantity" />
<el-table-column label="实时库存" prop="availableCount" />
<el-table-column label="操作" align="center">
<template slot-scope="scope">
<el-button
size="mini"
type="success"
:disabled="isCheckoutDisabled(scope.row)"
@click="handleCheckout(scope.row)"
>出库</el-button>
</template>
</el-table-column>
</el-table>
</el-card>
<el-card class="box-card" style="margin-top: 20px;">
<div slot="header" class="clearfix">
<span>已生成出库单</span>
</div>
<el-table :data="inventoryOuterList">
<el-table-column label="序号" type="index" width="55" align="center" />
<el-table-column label="出库单号" prop="outerCode" />
<el-table-column label="产品编码" prop="productCode" />
<el-table-column label="产品型号" prop="model" />
<el-table-column label="数量" prop="quantity" />
<el-table-column label="出库状态" prop="outerStatus">
<template slot-scope="scope">
<dict-tag :options="dict.type.outer_outer_status" :value="scope.row.outerStatus"/>
</template>
</el-table-column>
<el-table-column label="联系人" prop="contactPerson" />
<el-table-column label="收货地址" prop="contactAddress" :show-overflow-tooltip="true" />
<el-table-column label="生成时间" prop="createTime" />
<el-table-column label="操作" align="center">
<template slot-scope="scope">
<div v-if="scope.row.outerStatus === '1' || scope.row.outerStatus === '4'">
<el-button size="mini" type="danger" @click="handleDeleteOuter(scope.row)"></el-button>
<el-button size="mini" type="default" @click="handleConfirmOuter(scope.row)"></el-button>
</div>
<div v-else>
<el-button size="mini" type="success" @click="handleViewOuter(scope.row)"></el-button>
</div>
</template>
</el-table-column>
</el-table>
</el-card>
<div style="text-align: center; margin-top: 30px;">
<el-button type="primary" @click="submitForm" v-if="canUpdate"> </el-button>
<el-button @click="cancel"> </el-button>
</div>
<!-- 出库对话框 -->
<checkout-dialog ref="checkoutDialog" :order-info="form" @success="handleCheckoutSuccess"></checkout-dialog>
<!-- 出库单详情对话框 -->
<outer-detail-dialog ref="outerDetailDialog"></outer-detail-dialog>
</div>
</template>
<script>
import { getExecution, updateExecution, removeOuter, confirmOuterStatus } from "@/api/inventory/execution";
import { getDicts } from "@/api/system/dict/data";
import CheckoutDialog from './CheckoutDialog.vue';
import OuterDetailDialog from './OuterDetailDialog.vue';
import OrderDetailDrawer from "@/views/project/order/OrderDetailDrawer.vue";
import OrderInfo from "@/components/order/OrderInfo.vue";
export default {
name: "ExecutionEdit",
components: {OrderInfo, OrderDetailDrawer, CheckoutDialog, OuterDetailDialog },
dicts: ['bg_type', 'currency_type', 'company_delivery', 'identify_level', 'outer_outer_status'],
data() {
return {
form: {},
currentOrderId:null,
rules: {
// Add validation rules based on the red asterisks in edit.html
businessPerson: [{ required: true, message: "进货商接口人不能为空", trigger: "blur" }],
businessPhone: [{ required: true, message: "联系方式不能为空", trigger: "blur" }],
deliveryTime: [{ required: true, message: "要求到货时间不能为空", trigger: "blur" }],
orderChannel: [{ required: true, message: "下单通路不能为空", trigger: "change" }],
supplier: [{ required: true, message: "供货商不能为空", trigger: "blur" }],
dutyPhone: [{ required: true, message: "联系方式不能为空", trigger: "blur" }],
partnerName: [{ required: true, message: "进货商不能为空", trigger: "blur" }],
partnerPhone: [{ required: true, message: "联系方式不能为空", trigger: "blur" }],
currencyType: [{ required: true, message: "币种不能为空", trigger: "change" }],
},
canUpdate: false,
productDetailList: [],
inventoryOuterList: [],
industryOptions: []
};
},
created() {
const id = this.$route.params && this.$route.params.id;
if (id) {
this.getExecutionDetails(id);
}
},
methods: {
getExecutionDetails(id) {
getExecution(id).then(response => {
this.form = response.data.projectOrderInfo;
this.productDetailList = response.data.productDetailList;
this.inventoryOuterList = response.data.inventoryOuterList;
this.canUpdate = response.data.canUpdate;
this.fetchIndustryOptions(this.form.bgProperty);
this.currentOrderId=this.form.id
});
},
fetchIndustryOptions(bgType) {
const dictType = bgType === 'YYS' ? 'bg_yys' : 'bg_hysy';
getDicts(dictType).then(response => {
this.industryOptions = response.data.map(item => ({
value: item.dictValue,
label: item.dictLabel
}));
});
},
isCheckoutDisabled(row) {
return Number(row.quantity) <= (Number(row.generatedQuantity) + Number(row.confirmQuantity));
},
handleCheckout(row) {
this.$refs.checkoutDialog.show(row);
},
handleCheckoutSuccess() {
this.getExecutionDetails(this.form.id);
},
handleDeleteOuter(row) {
this.$modal.confirm('确定要撤销该出库单吗?').then(() => {
return removeOuter(row.id);
}).then(() => {
this.getExecutionDetails(this.form.id);
this.$modal.msgSuccess("撤销成功");
}).catch(() => {});
},
handleConfirmOuter(row) {
this.$modal.confirm('确定要将此单据状态更新为“已确认出库”吗?').then(() => {
return confirmOuterStatus(row.id, row.orderCode);
}).then(() => {
this.getExecutionDetails(this.form.id);
this.$modal.msgSuccess("操作成功");
}).catch(() => {});
},
handleViewOuter(row) {
this.$refs.outerDetailDialog.show(row.id);
},
submitForm() {
this.$refs["form"].validate(valid => {
if (valid) {
updateExecution(this.form).then(response => {
this.$modal.msgSuccess("修改成功");
this.cancel();
});
}
});
},
cancel() {
this.$router.go(-1);
}
},
watch: {
'form.bgProperty'(newVal) {
if(newVal) {
this.fetchIndustryOptions(newVal);
}
}
}
};
</script>
<style scoped>
.box-card {
margin-bottom: 20px;
}
</style>

View File

@ -0,0 +1,313 @@
<template>
<div class="app-container">
<el-form :model="queryParams" ref="queryForm" size="small" :inline="true" v-show="showSearch" label-width="100px">
<el-form-item label="项目编号" prop="projectCode">
<el-input
v-model="queryParams.projectCode"
placeholder="请输入项目编号"
clearable
@keyup.enter.native="handleQuery"
/>
</el-form-item>
<el-form-item label="合同编号" prop="orderCode">
<el-input
v-model="queryParams.orderCode"
placeholder="请输入合同编号"
clearable
@keyup.enter.native="handleQuery"
/>
</el-form-item>
<el-form-item label="项目名称" prop="projectName">
<el-input
v-model="queryParams.projectName"
placeholder="请输入项目名称"
clearable
@keyup.enter.native="handleQuery"
/>
</el-form-item>
<el-form-item label="出库状态" prop="outerStatus">
<el-select v-model="queryParams.outerStatus" placeholder="请选择出库状态" clearable>
<el-option
v-for="dict in dict.type.execution_outer_status"
:key="dict.value"
:label="dict.label"
:value="dict.value"
/>
</el-select>
</el-form-item>
<el-form-item label="发货状态" prop="deliveryStatus">
<el-select v-model="queryParams.deliveryStatus" placeholder="请选择发货状态" clearable>
<el-option
v-for="dict in dict.type.execution_delivery_status"
:key="dict.value"
:label="dict.label"
:value="dict.value"
/>
</el-select>
</el-form-item>
<el-form-item label="签收状态" prop="signStatus">
<el-select v-model="queryParams.signStatus" placeholder="请选择签收状态" clearable>
<el-option
v-for="dict in dict.type.execution_sign_status"
:key="dict.value"
:label="dict.label"
:value="dict.value"
/>
</el-select>
</el-form-item>
<el-form-item label="时间选择">
<el-select v-model="queryParams.timeType" placeholder="请选择时间类型" clearable style="width: 150px">
<el-option label="要求到货时间" value="0" />
<el-option label="订单生效时间" value="1" />
</el-select>
<el-date-picker
v-model="dateRange"
style="width: 240px; margin-left: 10px;"
value-format="yyyy-MM-dd"
type="daterange"
range-separator="-"
start-placeholder="开始日期"
end-placeholder="结束日期"
></el-date-picker>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="el-icon-search" size="mini" @click="handleQuery"></el-button>
<el-button icon="el-icon-refresh" size="mini" @click="resetQuery"></el-button>
</el-form-item>
</el-form>
<el-table v-loading="loading" :data="executionList" @sort-change="handleSortChange">
<el-table-column label="序号" type="index" width="55" align="center" />
<el-table-column label="项目编号" align="center" prop="projectCode" />
<el-table-column label="合同编号" align="center" prop="orderCode" width="200">
<template slot-scope="scope">
<router-link :to="'/project/order-view/' + scope.row.id" class="link-type">
<span>{{ scope.row.orderCode }}</span>
</router-link>
</template>
</el-table-column>
<el-table-column label="项目名称" align="center" prop="projectName" width="300" :show-overflow-tooltip="true">
<template slot-scope="scope">
<router-link :to="'/sip/project-view/' + scope.row.projectId" class="link-type">
<span>{{ scope.row.projectName }}</span>
</router-link>
</template>
</el-table-column>
<el-table-column label="出库状态" align="center" prop="outerStatus">
<template slot-scope="scope">
<dict-tag :options="dict.type.execution_outer_status" :value="scope.row.outerStatus"/>
</template>
</el-table-column>
<el-table-column label="签收状态" align="center" prop="signStatus">
<template slot-scope="scope">
<dict-tag :options="dict.type.execution_sign_status" :value="scope.row.signStatus"/>
</template>
</el-table-column>
<el-table-column label="发货状态" align="center" prop="deliveryStatus">
<template slot-scope="scope">
<dict-tag :options="dict.type.execution_delivery_status" :value="scope.row.deliveryStatus"/>
</template>
</el-table-column>
<el-table-column label="订单生效时间" align="center" prop="approveTime" sortable="custom" width="180">
<template slot-scope="scope">
<span>{{ parseTime(scope.row.approveTime, '{y}-{m}-{d}') }}</span>
</template>
</el-table-column>
<el-table-column label="要求到货时间" align="center" prop="deliveryTime" sortable="custom" width="180">
<template slot-scope="scope">
<span>{{ parseTime(scope.row.deliveryTime, '{y}-{m}-{d}') }}</span>
</template>
</el-table-column>
<el-table-column label="操作" align="center" class-name="small-padding fixed-width" fixed="right" width="200">
<template slot-scope="scope">
<el-button
size="mini"
type="text"
icon="el-icon-edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['inventory:execution:edit']"
>编辑</el-button>
<el-button
v-if="scope.row.signStatus == '0' && scope.row.deliveryStatus=='2'"
size="mini"
type="text"
icon="el-icon-upload2"
@click="handleSign(scope.row)"
v-hasPermi="['inventory:execution:sign']"
>签收</el-button>
<el-button
v-if="scope.row.signStatus == '1'"
size="mini"
type="text"
icon="el-icon-download"
@click="handleDownloadSign(scope.row)"
v-hasPermi="['inventory:execution:signdown']"
>签收文件</el-button>
<el-button
size="mini"
type="text"
icon="el-icon-delete"
@click="handleRecall(scope.row)"
v-hasPermi="['inventory:execution:recall']"
>撤单</el-button>
</template>
</el-table-column>
</el-table>
<pagination
v-show="total>0"
:total="total"
:page.sync="queryParams.pageNum"
:limit.sync="queryParams.pageSize"
@pagination="getList"
/>
<!-- 签收文件上传对话框 -->
<el-dialog title="上传签收文件" :visible.sync="upload.open" width="400px" append-to-body>
<el-upload
ref="upload"
:limit="1"
accept=".zip,.rar,image/*,.pdf,.doc,.docx"
:headers="upload.headers"
:action="upload.url"
:data="upload.data"
:disabled="upload.isUploading"
:on-progress="handleFileUploadProgress"
:on-success="handleFileSuccess"
:auto-upload="false"
drag
>
<i class="el-icon-upload"></i>
<div class="el-upload__text">将文件拖到此处<em>点击上传</em></div>
</el-upload>
<div slot="footer" class="dialog-footer">
<el-button type="primary" @click="submitFileForm"> </el-button>
<el-button @click="upload.open = false"> </el-button>
</div>
</el-dialog>
</div>
</template>
<script>
import { listExecution, recallExecution, downloadSignFile } from "@/api/inventory/execution";
import { getToken } from "@/utils/auth";
export default {
name: "Execution",
dicts: ['execution_outer_status', 'execution_delivery_status', 'execution_sign_status'],
data() {
return {
//
loading: true,
//
showSearch: true,
//
total: 0,
//
executionList: [],
//
dateRange: [],
//
queryParams: {
pageNum: 1,
pageSize: 10,
projectCode: null,
orderCode: null,
projectName: null,
outerStatus: null,
deliveryStatus: null,
signStatus: null,
timeType: '0', //
orderByColumn: 'approveTime',
isAsc: 'desc'
},
//
upload: {
//
open: false,
//
isUploading: false,
//
headers: { Authorization: "Bearer " + getToken() },
//
url: process.env.VUE_APP_BASE_API + "/project/order/sign",
}
};
},
created() {
this.getList();
},
methods: {
/** 查询订单执行列表 */
getList() {
this.loading = true;
this.addDateRange(this.queryParams, this.dateRange, this.queryParams.timeType === '0' ? 'deliveryTime' : 'approveTime');
listExecution(this.queryParams).then(response => {
this.executionList = response.rows;
this.total = response.total;
this.loading = false;
});
},
/** 搜索按钮操作 */
handleQuery() {
this.queryParams.pageNum = 1;
this.getList();
},
/** 重置按钮操作 */
resetQuery() {
this.dateRange = [];
this.resetForm("queryForm");
this.handleQuery();
},
/** 排序触发事件 */
handleSortChange(column, prop, order) {
this.queryParams.orderByColumn = column.prop;
this.queryParams.isAsc = column.order === 'ascending' ? 'asc' : 'desc';
this.getList();
},
/** 编辑按钮操作 */
handleUpdate(row) {
//
this.$router.push("/inventory/execution/edit/" + row.id);
},
/** 签收按钮操作 */
handleSign(row) {
this.upload.data = {
orderId: row.id,
versionCode: row.versionCode
};
this.upload.open = true;
},
//
handleFileUploadProgress(event, file, fileList) {
this.upload.isUploading = true;
},
//
handleFileSuccess(response, file, fileList) {
this.upload.open = false;
this.upload.isUploading = false;
this.$refs.upload.clearFiles();
this.$alert(response.msg, "操作成功", { dangerouslyUseHTMLString: true });
this.getList();
},
//
submitFileForm() {
this.$refs.upload.submit();
},
/** 下载签收文件按钮操作 */
handleDownloadSign(row) {
window.location.href = process.env.VUE_APP_BASE_API + `/project/order/sign/download?orderId=` + encodeURI(row.id) + '&versionCode=' + encodeURI(row.versionCode);
},
/** 撤单按钮操作 */
handleRecall(row) {
this.$modal.confirm('撤回此单后,该合同下所有出库单以及关联的发货纪录将同步删除,操作不可恢复,请确认后执行!').then(function() {
return recallExecution(row.id);
}).then(() => {
this.getList();
this.$modal.msgSuccess("撤单成功");
}).catch(() => {});
}
}
};
</script>

View File

@ -0,0 +1,23 @@
package com.ruoyi.sip.dto.inventory;
import lombok.Data;
/**
* @author : ch
* @version : 1.0
* @ClassName : CheckOutDto
* @Description :
* @DATE : Created in 15:42 2025/11/17
* <pre> Copyright: Copyright(c) 2025 </pre>
* <pre> Company : </pre>
* Modification History:
* Date Author Version Discription
* --------------------------------------------------------------------------
* 2025/11/17 ch 1.0 Why & What is modified: <> *
*/
@Data
public class CheckOutDto {
private String productCode;
private Integer quantity;
}