Merge remote-tracking branch 'origin/master'

This commit is contained in:
z 2026-04-17 10:02:57 +08:00
commit f174371f0e
13 changed files with 565 additions and 7 deletions

View File

@ -0,0 +1,64 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="jnpf.mapper.OrderDetailMapper">
<select id="getOrderItemWithOrder" resultType="jnpf.model.order.OrderItemWithOrderVO">
SELECT
od.id AS itemId,
od.sale_ord_id AS saleOrdId,
od.ord_item_status AS ordItemStatus,
od.ord_qty AS ordQty,
od.produce_qty AS produceQty,
(od.ord_qty - IFNULL(od.produce_qty, 0)) AS remainingQty,
od.material_name AS materialName,
od.unit AS unit,
od.spec AS spec,
od.deliveried_qty AS deliveriedQty,
od.material_code AS materialCode,
od.price_tax AS priceTax,
od.material_use AS materialUse,
od.remark AS remark,
od.f_creator_user_id AS creatorUserId,
eo.is_urgent AS isUrgent,
eo.contract_no AS contractNo,
eo.sale_ord_no AS saleOrdNo,
eo.cust_name AS custName,
eo.ord_type AS ordType,
eo.ord_status AS ordStatus,
eo.pro_status AS proStatus,
eo.ord_date AS ordDate,
eo.req_delivery_date AS reqDeliveryDate,
eo.payment_terms AS paymentTerms,
eo.tax_rate AS taxRate,
eo.ord_status AS ordStatus
FROM tso_order_item od
LEFT JOIN tso_order eo ON od.sale_ord_id = eo.id
<where>
AND (od.f_delete_mark IS NULL OR od.f_delete_mark = 0)
AND (eo.f_delete_mark IS NULL OR eo.f_delete_mark = 0)
AND eo.pro_status &lt;&gt; '2'
AND od.ord_item_status NOT IN ('2','9')
AND eo.ord_status = '3'
<if test="pagination.ordDateStart != null">
AND eo.ord_date &gt;= #{pagination.ordDateStart}
</if>
<if test="pagination.ordDateEnd != null">
AND eo.ord_date &lt;= #{pagination.ordDateEnd}
</if>
<if test="pagination.saleOrdNo != null and pagination.saleOrdNo != ''">
AND eo.sale_ord_no LIKE CONCAT('%', #{pagination.saleOrdNo}, '%')
</if>
<if test="pagination.custName != null and pagination.custName != ''">
AND eo.cust_name LIKE CONCAT('%', #{pagination.custName}, '%')
</if>
<if test="pagination.ordItemStatus == null or pagination.ordItemStatus == ''">
AND od.ord_item_status IN ('1', '0')
</if>
<if test="pagination.ordItemStatus != null and pagination.ordItemStatus != ''">
AND od.ord_item_status = #{pagination.ordItemStatus}
</if>
</where>
ORDER BY eo.ord_date DESC, od.id DESC
</select>
</mapper>

View File

@ -1,7 +1,13 @@
package jnpf.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import jnpf.entity.OrderDetailEntity;
import jnpf.model.order.OrderItemWithOrderPagination;
import jnpf.model.order.OrderItemWithOrderVO;
import org.apache.ibatis.annotations.Param;
import java.util.List;
/**
* 业务订单明细 Mapper
@ -13,4 +19,7 @@ import jnpf.entity.OrderDetailEntity;
*/
public interface OrderDetailMapper extends BaseMapper<OrderDetailEntity> {
List<OrderItemWithOrderVO> getOrderItemWithOrder(Page<OrderItemWithOrderVO> page, @Param("pagination") OrderItemWithOrderPagination pagination);
}

View File

@ -2,6 +2,8 @@ package jnpf.service;
import com.baomidou.mybatisplus.extension.service.IService;
import jnpf.entity.OrderDetailEntity;
import jnpf.model.order.OrderItemWithOrderPagination;
import jnpf.model.order.OrderItemWithOrderVO;
import jnpf.model.orderdetail.OrderDetailPagination;
import java.util.List;
@ -32,4 +34,7 @@ public interface OrderDetailService extends IService<OrderDetailEntity> {
*/
List<OrderDetailEntity> getListByOrderId(Long saleOrdId);
List<OrderItemWithOrderVO> getOrderItemWithOrder(OrderItemWithOrderPagination pagination);
}

View File

@ -1,9 +1,12 @@
package jnpf.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import jnpf.entity.OrderDetailEntity;
import jnpf.mapper.OrderDetailMapper;
import jnpf.model.order.OrderItemWithOrderPagination;
import jnpf.model.order.OrderItemWithOrderVO;
import jnpf.model.orderdetail.OrderDetailPagination;
import jnpf.service.OrderDetailService;
import org.springframework.stereotype.Service;
@ -34,6 +37,11 @@ public class OrderDetailServiceImpl extends ServiceImpl<OrderDetailMapper, Order
return this.list(query);
}
@Override
public List<OrderItemWithOrderVO> getOrderItemWithOrder(OrderItemWithOrderPagination pagination) {
Page<OrderItemWithOrderVO> page = new Page<>(pagination.getCurrentPage(), pagination.getPageSize());
List<OrderItemWithOrderVO> voList = this.baseMapper.getOrderItemWithOrder(page, pagination);
pagination.setTotal((int) page.getTotal());
return voList;
}
}

View File

@ -12,6 +12,8 @@ import jnpf.base.vo.PageListVO;
import jnpf.base.vo.PaginationVO;
import jnpf.constant.MsgCode;
import jnpf.entity.OrderDetailEntity;
import jnpf.model.order.OrderItemWithOrderPagination;
import jnpf.model.order.OrderItemWithOrderVO;
import jnpf.model.orderdetail.OrderDetailForm;
import jnpf.model.orderdetail.OrderDetailPagination;
import jnpf.model.orderdetail.OrderDetailVO;
@ -52,6 +54,13 @@ public class OrderDetailController {
return ActionResult.page(voList, JsonUtil.getJsonToBean(orderDetailPagination, PaginationVO.class));
}
@Operation(summary = "订单明细分页查询(关联订单主表)")
@PostMapping("/getOrderItemWithOrder")
public ActionResult<PageListVO<OrderItemWithOrderVO>> getOrderItemWithOrder(@RequestBody OrderItemWithOrderPagination pagination) {
List<OrderItemWithOrderVO> voList = orderDetailService.getOrderItemWithOrder(pagination);
return ActionResult.page(voList, JsonUtil.getJsonToBean(pagination, PaginationVO.class));
}
/**
* 根据订单ID获取明细列表
*

View File

@ -0,0 +1,27 @@
package jnpf.model.order;
import io.swagger.v3.oas.annotations.media.Schema;
import jnpf.base.Pagination;
import lombok.Data;
import java.util.Date;
@Data
public class OrderItemWithOrderPagination extends Pagination {
@Schema(description = "下单时间开始")
private Date ordDateStart;
@Schema(description = "下单时间结束")
private Date ordDateEnd;
@Schema(description = "订单编码")
private String saleOrdNo;
@Schema(description = "客户名称")
private String custName;
@Schema(description = "行状态")
private String ordItemStatus;
}

View File

@ -0,0 +1,93 @@
package jnpf.model.order;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.io.Serializable;
import java.math.BigDecimal;
import java.util.Date;
@Data
@Schema(description = "订单子表与主表联表查询VO", name = "订单明细与订单联表查询")
public class OrderItemWithOrderVO implements Serializable {
@Schema(description = "子表主键")
private Integer itemId;
@Schema(description = "销售订单主表ID")
private Integer saleOrdId;
@Schema(description = "订单编码")
private String saleOrdNo;
@Schema(description = "订单状态")
private String ordStatus;
@Schema(description = "生产状态")
private String proStatus;
@Schema(description = "下单日期")
private Date ordDate;
@Schema(description = "客户名称")
private String custName;
@Schema(description = "产品名称")
private String materialName;
@Schema(description = "规格型号")
private String spec;
@Schema(description = "订单数量")
private BigDecimal ordQty;
@Schema(description = "已转生产数量")
private BigDecimal produceQty;
@Schema(description = "剩余数量")
private BigDecimal remainingQty;
@Schema(description = "订单类型")
private String ordType;
@Schema(description = "要求交货日期")
private Date reqDeliveryDate;
@Schema(description = "是否急单")
private String isUrgent;
@Schema(description = "单位")
private String unit;
@Schema(description = "生产状态")
private String produceStatus;
@Schema(description = "物料编码")
private String materialCode;
@Schema(description = "含税单价")
private BigDecimal priceTax;
@Schema(description = "用途")
private String materialUse;
@Schema(description = "已发货数量")
private BigDecimal deliveriedQty;
@Schema(description = "行状态")
private String ordItemStatus;
@Schema(description = "备注")
private String remark;
@Schema(description = "合同编号")
private String contractNo;
@Schema(description = "创建时间")
private Date creatorTime;
@Schema(description = "创建用户ID")
private String creatorUserId;
}

View File

@ -0,0 +1,22 @@
// 维护后期的字典信息
// 字典映射配置id -> 名称)
export const dictMaps = {
// 生产状态
proStatus: { '0': '正常', '1': '部分转生产', '2': '全部转生产' },
// 行状态
orderItemStatus: { '0': '正常', '1': '部分转产', '2': '全部转产', '9': '关闭' },
};
// 根据映射自动生成下拉选项
export const dictOptions = {};
for (const key in dictMaps) {
const map = dictMaps[key];
dictOptions[key] = Object.entries(map).map(([enCode, fullName]) => ({ enCode, fullName }));
}
// 获取显示名称
export function getLabel(type, value) {
const map = dictMaps[type];
return map ? (map[value] || value) : value;
}

View File

@ -231,7 +231,31 @@ export default {
},
handleClose() {
this.visible = false;
this.$emit('refresh', true)
this.$emit('refresh', true);
this.resetDataForm();
},
resetDataForm() {
this.dataForm = {
id: "",
supplierNo: undefined,
supplierName: undefined,
supplierSimName: undefined,
supplierType: undefined,
supplierReg: undefined,
contact1: undefined,
conPhone1: undefined,
conAddress1: undefined,
contact2: undefined,
conPhone2: undefined,
conAddress2: undefined,
bankName: undefined,
bankAccount: undefined,
taxNo: undefined,
remark: undefined,
enabledStatus: "1",
status: "1",
isBlacklist: "0",
};
},
},
};

View File

@ -50,8 +50,7 @@
</div>
<div class="JNPF-common-head-right"></div>
</div>
<JNPF-table v-loading="listLoading" :data="list" @selection-change="handleSelectionChange">
<el-table-column type="selection" width="50" align="center"/>
<JNPF-table v-loading="listLoading" :data="list">
<el-table-column prop="supplierNo" label="供应商编码" align="center"/>
<el-table-column prop="supplierName" label="供应商名称" align="center"/>
<el-table-column prop="supplierSimName" label="简称" align="center"/>

View File

@ -0,0 +1,274 @@
<template>
<div class="JNPF-common-layout supplier_data">
<div class="JNPF-common-layout-center">
<el-row class="JNPF-common-search-box" :gutter="16">
<el-form @submit.native.prevent>
<el-col :span="6">
<el-form-item label="下单时间">
<JnpfDateRangePicker v-model="query.ordDate" format="yyyy-MM-dd"
startPlaceholder="开始日期" endPlaceholder="结束日期" />
</el-form-item>
</el-col>
<el-col :span="6">
<el-form-item label="订单编号">
<el-input
v-model="query.saleOrdNo"
placeholder="请输入订单编号"
clearable
>
</el-input>
</el-form-item>
</el-col>
<el-col :span="6">
<el-form-item label="生产状态">
<JnpfSelect
v-model="query.ordItemStatus"
placeholder="请选择生产状态"
clearable
:options="ordItemStatusOptions"
:props="ordItemStatusProps"
>
</JnpfSelect>
</el-form-item>
</el-col>
<el-col :span="6">
<el-form-item label="客户名称">
<el-input
v-model="query.custName"
placeholder="请输入客户名称"
clearable
>
</el-input>
</el-form-item>
</el-col>
<el-col :span="6">
<el-form-item>
<el-button
type="primary"
icon="el-icon-search"
@click="search()"
>
查询
</el-button>
<el-button
icon="el-icon-refresh-right"
@click="reset()"
>
重置
</el-button>
</el-form-item>
</el-col>
</el-form>
</el-row>
<div class="JNPF-common-layout-main JNPF-flex-main">
<div class="JNPF-common-head">
<div></div>
<div class="JNPF-common-head-right"></div>
</div>
<JNPF-table v-loading="listLoading" :data="list" border ref="table" height="400">
<el-table-column prop="saleOrdNo" label="订单编码" align="center" min-width="120" />
<el-table-column prop="ordStatus" label="订单状态" align="center" min-width="100">
<template slot-scope="scope">
{{ getDictText(scope.row.ordStatus, ordStatusOptions) }}
</template>
</el-table-column>
<el-table-column prop="ordDate" label="下单日期" align="center" min-width="120" :formatter="jnpf.tableDateFormat1"/>
<el-table-column prop="custName" label="客户名称" align="center" min-width="150" />
<el-table-column prop="materialName" label="产品名称" align="center" min-width="150" />
<el-table-column prop="spec" label="规格型号" align="center" min-width="120" />
<el-table-column prop="ordQty" label="订单数量" align="center" min-width="100" />
<el-table-column label="已转生产数量" align="center" min-width="120">
<template slot-scope="scope">
{{ Number(scope.row.produceQty) || 0 }}
</template>
</el-table-column>
<el-table-column label="剩余数量" align="center" min-width="100">
<template slot-scope="scope">
{{ (Number(scope.row.ordQty) || 0) - (Number(scope.row.produceQty) || 0) }}
</template>
</el-table-column>
<el-table-column prop="ordType" label="订单类型" align="center" min-width="100">
<template slot-scope="scope">
{{ scope.row.ordType == '1' ? '常规' : scope.row.ordType == '2' ? '定制' : scope.row.ordType }}
</template>
</el-table-column>
<el-table-column prop="reqDeliveryDate" label="要求交货日期" align="center" min-width="120" :formatter="jnpf.tableDateFormat1"/>
<el-table-column prop="isUrgent" label="是否急单" align="center" min-width="100">
<template slot-scope="scope">
{{ scope.row.isUrgent == '0' ? '是' : scope.row.isUrgent == '1' ? '否' : '' }}
</template>
</el-table-column>
<el-table-column label="单位" align="center" min-width="80">
<template slot-scope="scope">
{{ scope.row.unit == '1' ? 'kg' : scope.row.unit == '2' ? 'T' : scope.row.unit }}
</template>
</el-table-column>
<!-- <el-table-column prop="proStatus" label="生产状态" align="center" min-width="100">
<template slot-scope="scope">
{{ getLabel('proStatus', scope.row.proStatus) }}
</template>
</el-table-column> -->
<el-table-column prop="ordItemStatus" label="生产状态" align="center" min-width="100">
<template slot-scope="scope">
{{ getLabel('orderItemStatus', scope.row.ordItemStatus) }}
</template>
</el-table-column>
<el-table-column label="操作" fixed="right" align="center" width="150">
<template slot-scope="scope">
<!-- <el-button type="text" @click="handleDetail(scope.row)">详情</el-button> -->
</template>
</el-table-column>
</JNPF-table>
<pagination
:total="total"
:page.sync="listQuery.currentPage"
:limit.sync="listQuery.pageSize"
@pagination="initData"
/>
</div>
</div>
</div>
</template>
<script>
import request from "@/utils/request";
import { mapGetters } from "vuex";
import { getDictionaryDataSelector } from "@/api/systemData/dictionary";
import jnpf from "@/utils/jnpf";
import { dictOptions, getLabel } from "../common/dict";
export default {
name: "tsoorder",
components: {},
data() {
return {
query: {
ordDate: undefined,
saleOrdNo: undefined,
ordItemStatus: undefined,
custName: undefined,
},
list: [],
listLoading: false,
total: 0,
listQuery: {
currentPage: 1,
pageSize: 20,
},
ordItemStatusOptions: [],
ordItemStatusProps: { label: "fullName", value: "enCode" },
ordStatusOptions: [],
};
},
computed: {
jnpf() {
return jnpf;
},
...mapGetters(["userInfo"]),
},
created() {
this.initDictData();
this.initSearchData();
this.initData();
},
methods: {
initSearchData() {
let date = new Date();
let dateWithoutTime = new Date(date.getFullYear(), date.getMonth(), 1);
let today = new Date(date.getFullYear(), date.getMonth(), date.getDate());
this.query.ordDate = [dateWithoutTime.getTime(), today.getTime()];
},
initDictData() {
getDictionaryDataSelector("811520443046428805").then((res) => {
this.ordStatusOptions = res.data.list || [];
});
// 使
this.ordItemStatusOptions = dictOptions.orderItemStatus;
},
initData() {
this.listLoading = true;
let _query = {
...this.listQuery,
...this.query,
dataType: 0,
};
console.log('查询参数:', _query);
request({
url: "/api/example/orderDetail/getOrderItemWithOrder",
method: "post",
data: _query,
})
.then((res) => {
console.log('接口返回:', res);
this.list = res.data.list || [];
this.total = res.data.pagination && res.data.pagination.total ? res.data.pagination.total : 0;
console.log('列表数据:', this.list);
this.listLoading = false;
})
.catch((err) => {
console.error('请求失败:', err);
this.listLoading = false;
});
},
search() {
this.listQuery.currentPage = 1;
this.initData();
},
reset() {
this.query = {
ordDate: undefined,
saleOrdNo: undefined,
ordItemStatus: undefined,
custName: undefined,
};
this.initSearchData();
this.search();
},
handleDetail(row) {
if (!row || !row.detailId) {
this.$message.warning("请选择订单明细");
return;
}
this.$message.info("详情功能开发中");
},
handleEdit(row) {
if (!row || !row.detailId) {
this.$message.warning("请选择订单明细");
return;
}
this.$message.info("编辑功能开发中");
},
getDictText(value, options) {
if (!value || !options || !options.length) return value;
const item = options.find((opt) => opt.enCode === value || opt.id === value);
return item ? item.fullName || item.enCode : value;
},
getLabel(type, value) {
return getLabel(type, value);
},
},
};
</script>
<style scoped>
::v-deep .el-form-item__label {
text-align: left !important;
}
.JNPF-common-layout-main {
display: flex;
flex-direction: column;
min-height: calc(100vh - 220px);
}
.tableContainer {
flex: 1;
height: auto;
min-height: 300px;
}
</style>

View File

@ -0,0 +1,17 @@
import request from '@/utils/request'
export function getOrderDetailWithOrder(data) {
return request({
url: '/api/example/OrderDetail/getOrderDetailWithOrder',
method: 'post',
data
})
}
export function exportOrderDetailWithOrder(data) {
return request({
url: '/api/example/OrderDetail/exportOrderDetailWithOrder',
method: 'post',
data
})
}

View File

@ -201,6 +201,10 @@ export default {
this.list = res.data.list || [];
this.total = res.data.pagination.total;
this.listLoading = false;
//
if (this.list.length > 0) {
this.showMachineList(this.list[0]);
}
});
},
addOrUpdateHandle(row) {
@ -217,7 +221,10 @@ export default {
},
refresh(isRefresh) {
this.formVisible = false;
if (isRefresh) this.search();
if (isRefresh) {
this.listQuery.currentPage = 1;
this.initData();
}
},
reset() {
this.query = {