no message

main
HUOJIN\92525 2025-12-26 18:13:50 +08:00
parent 6fe921f924
commit c42824a0aa
36 changed files with 1484 additions and 62 deletions

View File

@ -98,7 +98,7 @@ public class AgvTaskController extends JeecgController<AgvTask, IAgvTaskService>
@Operation(summary = "AGV任务表-通过id删除")
@RequiresPermissions("agvTask:data_agv_task:delete")
@DeleteMapping(value = "/delete")
public Result<String> delete(@RequestParam(name = "id", required = true) String id) {
public Result<String> delete(@RequestParam(name = "id", required = true) Long id) {
agvTaskService.removeById(id);
return Result.OK("删除成功!");
}
@ -127,7 +127,7 @@ public class AgvTaskController extends JeecgController<AgvTask, IAgvTaskService>
//@AutoLog(value = "AGV任务表-通过id查询")
@Operation(summary = "AGV任务表-通过id查询")
@GetMapping(value = "/queryById")
public Result<AgvTask> queryById(@RequestParam(name = "id", required = true) String id) {
public Result<AgvTask> queryById(@RequestParam(name = "id", required = true) Long id) {
AgvTask agvTask = agvTaskService.getById(id);
if (agvTask == null) {
return Result.error("未找到对应数据");

View File

@ -2,8 +2,10 @@ package org.cpte.modules.base.controller;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import org.apache.commons.lang3.StringUtils;
@ -54,12 +56,17 @@ public class AreaController extends JeecgController<Area, IAreaService> {
@RequestParam(name = "pageNo", defaultValue = "1") Integer pageNo,
@RequestParam(name = "pageSize", defaultValue = "10") Integer pageSize,
@RequestParam(name = "keyword", required = false) String keyword,
@RequestParam(name = "areaCode", required = false) String areaCode,
HttpServletRequest req) {
QueryWrapper<Area> queryWrapper = QueryGenerator.initQueryWrapper(area, req.getParameterMap());
// 如果提供了 keyword则同时对 areaCode 和 areaName 进行模糊搜索
if (StringUtils.isNotBlank(keyword)) {
queryWrapper.and(wrapper -> wrapper.likeRight("area_code", keyword).or().likeRight("area_name", keyword));
}
if(StringUtils.isNotBlank(areaCode)){
List<String> areaCodes= Arrays.asList(areaCode.split(","));
queryWrapper.in("area_code", areaCodes);
}
Page<Area> page = new Page<Area>(pageNo, pageSize);
IPage<Area> pageList = areaService.page(page, queryWrapper);
return Result.OK(pageList);
@ -106,7 +113,7 @@ public class AreaController extends JeecgController<Area, IAreaService> {
@Operation(summary = "库区-通过id删除")
@RequiresPermissions("base:base_area:delete")
@DeleteMapping(value = "/delete")
public Result<String> delete(@RequestParam(name = "id", required = true) String id) {
public Result<String> delete(@RequestParam(name = "id", required = true) Long id) {
areaService.removeById(id);
return Result.OK("删除成功!");
}
@ -135,7 +142,7 @@ public class AreaController extends JeecgController<Area, IAreaService> {
//@AutoLog(value = "库区-通过id查询")
@Operation(summary = "库区-通过id查询")
@GetMapping(value = "/queryById")
public Result<Area> queryById(@RequestParam(name = "id", required = true) String id) {
public Result<Area> queryById(@RequestParam(name = "id", required = true) Long id) {
Area area = areaService.getById(id);
if (area == null) {
return Result.error("未找到对应数据");

View File

@ -105,7 +105,7 @@ public class ItemController extends JeecgController<Item, IItemService> {
@Operation(summary = "物料-通过id删除")
@RequiresPermissions("base:base_item:delete")
@DeleteMapping(value = "/delete")
public Result<String> delete(@RequestParam(name = "id", required = true) String id) {
public Result<String> delete(@RequestParam(name = "id", required = true) Long id) {
itemService.removeById(id);
return Result.OK("删除成功!");
}
@ -134,7 +134,7 @@ public class ItemController extends JeecgController<Item, IItemService> {
//@AutoLog(value = "物料-通过id查询")
@Operation(summary = "物料-通过id查询")
@GetMapping(value = "/queryById")
public Result<Item> queryById(@RequestParam(name = "id", required = true) String id) {
public Result<Item> queryById(@RequestParam(name = "id", required = true) Long id) {
Item item = itemService.getById(id);
if (item == null) {
return Result.error("未找到对应数据");

View File

@ -131,7 +131,7 @@ public class PointController extends JeecgController<Point, IPointService> {
@Operation(summary = "库位-通过id删除")
@RequiresPermissions("base:base_point:delete")
@DeleteMapping(value = "/delete")
public Result<String> delete(@RequestParam(name = "id", required = true) String id) {
public Result<String> delete(@RequestParam(name = "id", required = true) Long id) {
pointService.removeById(id);
return Result.OK("删除成功!");
}
@ -160,7 +160,7 @@ public class PointController extends JeecgController<Point, IPointService> {
//@AutoLog(value = "库位-通过id查询")
@Operation(summary = "库位-通过id查询")
@GetMapping(value = "/queryById")
public Result<Point> queryById(@RequestParam(name = "id", required = true) String id) {
public Result<Point> queryById(@RequestParam(name = "id", required = true) Long id) {
Point point = pointService.getById(id);
if (point == null) {
return Result.error("未找到对应数据");

View File

@ -137,7 +137,7 @@ public class StockController extends JeecgController<Stock, IStockService> {
@Operation(summary = "容器-通过id删除")
@RequiresPermissions("base:base_stock:delete")
@DeleteMapping(value = "/delete")
public Result<String> delete(@RequestParam(name = "id", required = true) String id) {
public Result<String> delete(@RequestParam(name = "id", required = true) Long id) {
stockService.removeById(id);
return Result.OK("删除成功!");
}
@ -166,7 +166,7 @@ public class StockController extends JeecgController<Stock, IStockService> {
//@AutoLog(value = "容器-通过id查询")
@Operation(summary = "容器-通过id查询")
@GetMapping(value = "/queryById")
public Result<Stock> queryById(@RequestParam(name = "id", required = true) String id) {
public Result<Stock> queryById(@RequestParam(name = "id", required = true) Long id) {
Stock stock = stockService.getById(id);
if (stock == null) {
return Result.error("未找到对应数据");

View File

@ -79,6 +79,12 @@ public class Point implements Serializable {
@Schema(description = "层")
private java.lang.String layerNum;
/**
*
*/
@Schema(description = "储位编码")
private String nodeCode;
/**
* x
*/

View File

@ -106,4 +106,13 @@ public interface IPointService extends IService<Point> {
*/
List<Point> findClusterPoint(List<Long> itemKeyIds, String areaCode);
/**
*
*
* @param pageNum
* @param pageSize
* @return Boolean
*/
Boolean syncPoint(Integer pageNum, Integer pageSize);
}

View File

@ -1,19 +1,24 @@
package org.cpte.modules.base.service.impl;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.google.common.collect.Maps;
import org.apache.commons.collections4.CollectionUtils;
import org.cpte.modules.base.entity.Point;
import org.cpte.modules.base.mapper.PointMapper;
import org.cpte.modules.base.service.IPointService;
import org.cpte.modules.constant.GeneralConstant;
import org.cpte.modules.constant.enums.AreaTypeEnum;
import org.cpte.modules.constant.enums.CommonStatusEnum;
import org.cpte.modules.utils.ElevatorMapUtil;
import org.jeecg.common.util.RedisUtil;
import org.jeecg.common.util.RestUtil;
import org.jeecg.modules.openapi.mapper.OpenApiMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.transaction.annotation.Transactional;
import java.util.Collections;
import java.util.List;
@ -31,6 +36,9 @@ public class PointServiceImpl extends ServiceImpl<PointMapper, Point> implements
@Autowired
private RedisUtil redisUtil;
@Autowired
private OpenApiMapper openApiMapper;
/**
*
*
@ -152,4 +160,38 @@ public class PointServiceImpl extends ServiceImpl<PointMapper, Point> implements
return this.baseMapper.findPointsWithSkuBatchPo(itemKeyIds, areaCode);
}
@Override
@Transactional(rollbackFor = Exception.class)
public Boolean syncPoint(Integer pageNum, Integer pageSize) {
if (pageSize > 2000) {
throw new RuntimeException("同步库位数据每页不能超过2000条");
}
// 构造请求参数
JSONObject params = new JSONObject();
params.put("warehouseID","HETU");
params.put("clientCode","WMS");
params.put("regionCode","3");
params.put("pageNum",pageNum);
params.put("pageSize", pageSize);
// 调用接口获取物料数据
JSONObject pointAddList = GetPointAddList(params);
return pointAddList.isEmpty();
}
/**
*
*
* @param params
* @return ItemResponse
*/
private JSONObject GetPointAddList(JSONObject params) {
try {
String url = openApiMapper.getRequestUrl(GeneralConstant.SYNC_POINT).getOriginUrl();
return RestUtil.post(url, params, null);
} catch (Exception e) {
throw new RuntimeException("获取库位数据失败", e);
}
}
}

View File

@ -70,10 +70,21 @@ public interface GeneralConstant {
*/
String MOVE_ORDER_NO = "move_order_no";
/**
*
*/
String COUNT_ORDER_NO = "count_order_no";
/**
* ERP-
*/
String SYNC_ITEM = "g9eq4HJn";
/**
* TES-
*/
String SYNC_POINT = "n65mQexp";
/**
* TES
*/

View File

@ -0,0 +1,30 @@
package org.cpte.modules.constant.enums;
import lombok.Getter;
@Getter
public enum CountPlanStatusEnum {
CREATED(1, "已创建"),
AUDITED(2, "已审核"),
COUNTING(3, "盘点中"),
COMPLETED(4, "盘点完成"),
CANCELED(5, "已取消"),
CLOSED(6, "已关闭"),
;
CountPlanStatusEnum(Integer value, String desc) {
this.value = value;
this.desc = desc;
}
/**
*
*/
final Integer value;
/**
*
*/
final String desc;
}

View File

@ -0,0 +1,28 @@
package org.cpte.modules.constant.enums;
import lombok.Getter;
@Getter
public enum CountPlanTypeEnum {
ITEM(0, "按物料抽盘"),
STOCK(1, "按托盘抽盘"),
;
CountPlanTypeEnum(Integer value, String desc) {
this.value = value;
this.desc = desc;
}
/**
*
*/
final Integer value;
/**
*
*/
final String desc;
}

View File

@ -0,0 +1,311 @@
package org.cpte.modules.count.controller;
import java.io.UnsupportedEncodingException;
import java.io.IOException;
import java.net.URLDecoder;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
import java.util.HashMap;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import org.apache.commons.collections4.CollectionUtils;
import org.cpte.modules.base.entity.Item;
import org.cpte.modules.base.entity.Point;
import org.cpte.modules.base.entity.Stock;
import org.cpte.modules.base.service.IItemService;
import org.cpte.modules.base.service.IPointService;
import org.cpte.modules.base.service.IStockService;
import org.jeecgframework.poi.excel.ExcelImportUtil;
import org.jeecgframework.poi.excel.def.NormalExcelConstants;
import org.jeecgframework.poi.excel.entity.ExportParams;
import org.jeecgframework.poi.excel.entity.ImportParams;
import org.jeecgframework.poi.excel.view.JeecgEntityExcelView;
import org.jeecg.common.system.vo.LoginUser;
import org.apache.shiro.SecurityUtils;
import org.jeecg.common.api.vo.Result;
import org.jeecg.common.system.query.QueryGenerator;
import org.jeecg.common.system.query.QueryRuleEnum;
import org.jeecg.common.util.oConvertUtils;
import org.cpte.modules.count.entity.CountDetail;
import org.cpte.modules.count.entity.CountPlan;
import org.cpte.modules.count.vo.CountPlanPage;
import org.cpte.modules.count.service.ICountPlanService;
import org.cpte.modules.count.service.ICountDetailService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import lombok.extern.slf4j.Slf4j;
import com.alibaba.fastjson.JSON;
import io.swagger.v3.oas.annotations.tags.Tag;
import io.swagger.v3.oas.annotations.Operation;
import org.jeecg.common.aspect.annotation.AutoLog;
import org.apache.shiro.authz.annotation.RequiresPermissions;
/**
* @Description:
* @author: cpte
* @Date: 2025-12-23
* @Version: V1.0
*/
@Tag(name="盘点")
@RestController
@RequestMapping("/count/countPlan")
@Slf4j
public class CountPlanController {
@Autowired
private IItemService itemService;
@Autowired
private IPointService pointService;
@Autowired
private IStockService stockService;
@Autowired
private ICountPlanService countPlanService;
@Autowired
private ICountDetailService countDetailService;
/**
*
*
* @param countPlan
* @param pageNo
* @param pageSize
* @param req
* @return
*/
//@AutoLog(value = "盘点-分页列表查询")
@Operation(summary="盘点-分页列表查询")
@GetMapping(value = "/list")
public Result<IPage<CountPlan>> queryPageList(CountPlan countPlan,
@RequestParam(name="pageNo", defaultValue="1") Integer pageNo,
@RequestParam(name="pageSize", defaultValue="10") Integer pageSize,
HttpServletRequest req) {
QueryWrapper<CountPlan> queryWrapper = QueryGenerator.initQueryWrapper(countPlan, req.getParameterMap());
Page<CountPlan> page = new Page<CountPlan>(pageNo, pageSize);
IPage<CountPlan> pageList = countPlanService.page(page, queryWrapper);
return Result.OK(pageList);
}
/**
*
*
* @param countPlanPage
* @return
*/
@AutoLog(value = "盘点-添加")
@Operation(summary="盘点-添加")
@RequiresPermissions("count:data_count_plan:add")
@PostMapping(value = "/add")
public Result<String> add(@RequestBody CountPlanPage countPlanPage) {
CountPlan countPlan = new CountPlan();
BeanUtils.copyProperties(countPlanPage, countPlan);
countPlanService.saveMain(countPlan);
return Result.OK("添加成功!");
}
/**
*
*
* @param countPlanPage
* @return
*/
@AutoLog(value = "盘点-编辑")
@Operation(summary="盘点-编辑")
@RequiresPermissions("count:data_count_plan:edit")
@RequestMapping(value = "/edit", method = {RequestMethod.PUT,RequestMethod.POST})
public Result<String> edit(@RequestBody CountPlanPage countPlanPage) {
CountPlan existingCountPlan = countPlanService.getById(countPlanPage.getId());
if(existingCountPlan==null) {
return Result.error("未找到对应数据");
}
BeanUtils.copyProperties(countPlanPage, existingCountPlan);
countPlanService.updateMain(existingCountPlan, countPlanPage.getCountDetailList());
return Result.OK("编辑成功!");
}
/**
* id
*
* @param id
* @return
*/
@AutoLog(value = "盘点-通过id删除")
@Operation(summary="盘点-通过id删除")
@RequiresPermissions("count:data_count_plan:delete")
@DeleteMapping(value = "/delete")
public Result<String> delete(@RequestParam(name="id",required=true) Long id) {
countPlanService.delMain(id);
return Result.OK("删除成功!");
}
/**
*
*
* @param ids
* @return
*/
@AutoLog(value = "盘点-批量删除")
@Operation(summary="盘点-批量删除")
@RequiresPermissions("count:data_count_plan:deleteBatch")
@DeleteMapping(value = "/deleteBatch")
public Result<String> deleteBatch(@RequestParam(name="ids",required=true) String ids) {
this.countPlanService.delBatchMain(Arrays.asList(ids.split(",")));
return Result.OK("批量删除成功!");
}
/**
* id
*
* @param id
* @return
*/
//@AutoLog(value = "盘点-通过id查询")
@Operation(summary="盘点-通过id查询")
@GetMapping(value = "/queryById")
public Result<CountPlan> queryById(@RequestParam(name="id",required=true) Long id) {
CountPlan countPlan = countPlanService.getById(id);
if(countPlan==null) {
return Result.error("未找到对应数据");
}
return Result.OK(countPlan);
}
/**
* id
*
* @param id
* @return
*/
//@AutoLog(value = "盘点明细通过主表ID查询")
@Operation(summary="盘点明细主表ID查询")
@GetMapping(value = "/queryCountDetailByMainId")
public Result<List<CountDetail>> queryCountDetailListByMainId(@RequestParam(name="id",required=true) Long id) {
List<CountDetail> countDetailList = countDetailService.selectByMainId(id);
if(CollectionUtils.isNotEmpty(countDetailList)){
//物料
List<Long> itemIds=countDetailList.stream().map(CountDetail::getItemId).distinct().toList();
Map<Long,Item> itemMap=itemService.queryByItemIdsToMap(itemIds);
//库位
List<Long> pointIds=countDetailList.stream().map(CountDetail::getPointId).distinct().toList();
Map<Long, Point> pointMap=pointService.queryByPointIdsToMap(pointIds);
//容器
List<Long> stockIds=countDetailList.stream().map(CountDetail::getStockId).distinct().toList();
Map<Long, Stock> stockMap=stockService.queryByStockIdsToMap(stockIds);
for(CountDetail detail:countDetailList){
Item item = itemMap.get(detail.getItemId());
Point point = pointMap.get(detail.getPointId());
Stock stock = stockMap.get(detail.getStockId());
if(item!=null){
detail.setItemCode(item.getItemCode());
}
if(point!=null){
detail.setPointCode(point.getPointCode());
}
if(stock!=null){
detail.setStockCode(stock.getStockCode());
}
}
}
return Result.OK(countDetailList);
}
/**
* excel
*
* @param request
* @param countPlan
*/
@RequiresPermissions("count:data_count_plan:exportXls")
@RequestMapping(value = "/exportXls")
public ModelAndView exportXls(HttpServletRequest request, CountPlan countPlan) {
// Step.1 组装查询条件查询数据
QueryWrapper<CountPlan> queryWrapper = QueryGenerator.initQueryWrapper(countPlan, request.getParameterMap());
LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
//配置选中数据查询条件
String selections = request.getParameter("selections");
if(oConvertUtils.isNotEmpty(selections)) {
List<String> selectionList = Arrays.asList(selections.split(","));
queryWrapper.in("id",selectionList);
}
//Step.2 获取导出数据
List<CountPlan> countPlanList = countPlanService.list(queryWrapper);
// Step.3 组装pageList
List<CountPlanPage> pageList = new ArrayList<CountPlanPage>();
for (CountPlan main : countPlanList) {
CountPlanPage vo = new CountPlanPage();
BeanUtils.copyProperties(main, vo);
List<CountDetail> countDetailList = countDetailService.selectByMainId(main.getId());
vo.setCountDetailList(countDetailList);
pageList.add(vo);
}
// Step.4 AutoPoi 导出Excel
ModelAndView mv = new ModelAndView(new JeecgEntityExcelView());
mv.addObject(NormalExcelConstants.FILE_NAME, "盘点列表");
mv.addObject(NormalExcelConstants.CLASS, CountPlanPage.class);
mv.addObject(NormalExcelConstants.PARAMS, new ExportParams("盘点数据", "导出人:"+sysUser.getRealname(), "盘点"));
mv.addObject(NormalExcelConstants.DATA_LIST, pageList);
return mv;
}
/**
* excel
*
* @param request
* @param response
* @return
*/
@RequiresPermissions("count:data_count_plan:importExcel")
@RequestMapping(value = "/importExcel", method = RequestMethod.POST)
public Result<?> importExcel(HttpServletRequest request, HttpServletResponse response) {
MultipartHttpServletRequest multipartRequest = (MultipartHttpServletRequest) request;
Map<String, MultipartFile> fileMap = multipartRequest.getFileMap();
for (Map.Entry<String, MultipartFile> entity : fileMap.entrySet()) {
// 获取上传文件对象
MultipartFile file = entity.getValue();
ImportParams params = new ImportParams();
params.setTitleRows(2);
params.setHeadRows(1);
params.setNeedSave(true);
try {
List<CountPlanPage> list = ExcelImportUtil.importExcel(file.getInputStream(), CountPlanPage.class, params);
for (CountPlanPage page : list) {
CountPlan po = new CountPlan();
BeanUtils.copyProperties(page, po);
countPlanService.saveMain(po);
}
return Result.OK("文件导入成功!数据行数:" + list.size());
} catch (Exception e) {
log.error(e.getMessage(),e);
return Result.error("文件导入失败:"+e.getMessage());
} finally {
try {
file.getInputStream().close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
return Result.OK("文件导入失败!");
}
}

View File

@ -0,0 +1,167 @@
package org.cpte.modules.count.entity;
import java.io.Serializable;
import com.baomidou.mybatisplus.annotation.*;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.NoArgsConstructor;
import org.jeecg.common.aspect.annotation.Dict;
import org.jeecg.common.constant.ProvinceCityArea;
import org.jeecg.common.util.SpringContextUtils;
import lombok.Data;
import com.fasterxml.jackson.annotation.JsonFormat;
import org.springframework.format.annotation.DateTimeFormat;
import org.jeecgframework.poi.excel.annotation.Excel;
import java.util.Date;
import io.swagger.v3.oas.annotations.media.Schema;
import java.io.UnsupportedEncodingException;
/**
* @Description:
* @author: cpte
* @Date: 2025-12-23
* @Version: V1.0
*/
@Schema(description = "盘点明细")
@Data
@Builder
@AllArgsConstructor
@NoArgsConstructor
@TableName("data_count_detail")
public class CountDetail implements Serializable {
private static final long serialVersionUID = 1L;
/**
* id
*/
@TableId(type = IdType.ASSIGN_ID)
@Schema(description = "id")
@JsonSerialize(using = ToStringSerializer.class)
private java.lang.Long id;
/**
*
*/
@Schema(description = "盘点ID")
@JsonSerialize(using = ToStringSerializer.class)
private java.lang.Long countPlanId;
/**
*
*/
@Excel(name = "物料", width = 15)
@Schema(description = "物料")
@JsonSerialize(using = ToStringSerializer.class)
private java.lang.Long itemId;
@TableField(exist = false)
private java.lang.String itemCode;
/**
*
*/
@Excel(name = "库位", width = 15)
@Schema(description = "库位")
@JsonSerialize(using = ToStringSerializer.class)
private java.lang.Long pointId;
@TableField(exist = false)
private java.lang.String pointCode;
/**
*
*/
@Excel(name = "物料属性ID", width = 15)
@Schema(description = "物料属性ID")
@JsonSerialize(using = ToStringSerializer.class)
private java.lang.Long itemKeyId;
/**
* AGV
*/
@Excel(name = "AGV", width = 15)
@Schema(description = "AGV")
@JsonSerialize(using = ToStringSerializer.class)
private java.lang.Long agvTaskId;
/**
*
*/
@Excel(name = "库存", width = 15)
@Schema(description = "库存")
@JsonSerialize(using = ToStringSerializer.class)
private java.lang.Long inventoryId;
/**
*
*/
@Excel(name = "容器", width = 15)
@Schema(description = "容器")
@JsonSerialize(using = ToStringSerializer.class)
private java.lang.Long stockId;
@TableField(exist = false)
private java.lang.String stockCode;
/**
*
*/
@Excel(name = "库存数量", width = 15)
@Schema(description = "库存数量")
private java.math.BigDecimal invQty;
/**
*
*/
@Excel(name = "盘点数量", width = 15)
@Schema(description = "盘点数量")
private java.math.BigDecimal countQty;
/**
*
*/
@Excel(name = "盘点日期", width = 20, format = "yyyy-MM-dd HH:mm:ss")
@JsonFormat(timezone = "GMT+8", pattern = "yyyy-MM-dd HH:mm:ss")
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
@Schema(description = "盘点日期")
private java.util.Date planDate;
/**
*
*/
@Excel(name = "盘点人", width = 15)
@Schema(description = "盘点人")
private java.lang.String countBy;
/**
*
*/
@Schema(description = "所属部门")
private java.lang.String sysOrgCode;
/**
* ID
*/
@Excel(name = "仓库ID", width = 15)
@Schema(description = "仓库ID")
private java.lang.Integer tenantId;
/**
*
*/
@Schema(description = "创建人")
private java.lang.String createBy;
/**
*
*/
@JsonFormat(timezone = "GMT+8", pattern = "yyyy-MM-dd HH:mm:ss")
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
@Schema(description = "创建日期")
private java.util.Date createTime;
/**
*
*/
@Schema(description = "更新人")
private java.lang.String updateBy;
/**
*
*/
@JsonFormat(timezone = "GMT+8", pattern = "yyyy-MM-dd HH:mm:ss")
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
@Schema(description = "更新日期")
private java.util.Date updateTime;
}

View File

@ -0,0 +1,137 @@
package org.cpte.modules.count.entity;
import java.io.Serializable;
import java.io.UnsupportedEncodingException;
import java.util.Date;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import com.baomidou.mybatisplus.annotation.TableLogic;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
import org.jeecg.common.constant.ProvinceCityArea;
import org.jeecg.common.util.SpringContextUtils;
import lombok.Data;
import com.fasterxml.jackson.annotation.JsonFormat;
import org.springframework.format.annotation.DateTimeFormat;
import org.jeecgframework.poi.excel.annotation.Excel;
import org.jeecg.common.aspect.annotation.Dict;
import io.swagger.v3.oas.annotations.media.Schema;
/**
* @Description:
* @author: cpte
* @Date: 2025-12-23
* @Version: V1.0
*/
@Schema(description = "盘点")
@Data
@TableName("data_count_plan")
public class CountPlan implements Serializable {
private static final long serialVersionUID = 1L;
/**
* id
*/
@TableId(type = IdType.ASSIGN_ID)
@Schema(description = "id")
@JsonSerialize(using = ToStringSerializer.class)
private java.lang.Long id;
/**
* ID
*/
@Excel(name = "库区ID", width = 15)
@Schema(description = "库区ID")
@Dict(dictTable = "base_area", dicCode = "id", dicText = "area_name")
@JsonSerialize(using = ToStringSerializer.class)
private java.lang.Long areaId;
/**
*
*/
@Excel(name = "盘点单号", width = 15)
@Schema(description = "盘点单号")
private java.lang.String orderNo;
/**
* 0.;1.
*/
@Excel(name = "盘点类型", width = 15)
@Schema(description = "盘点类型0.按物料抽盘;1.按托盘抽盘")
@Dict(dicCode = "count_type")
private java.lang.Integer countType;
/**
* :1.;2.;3.;4.5.6.
*/
@Excel(name = "订单状态", width = 15)
@Schema(description = "订单状态:1.已创建;2.已审核;3.盘点中;4.盘点完成、5.已取消、6.已关闭")
@Dict(dicCode = "count_status")
private java.lang.Integer status;
/**
*
*/
@Excel(name = "计划开始时间", width = 20, format = "yyyy-MM-dd HH:mm:ss")
@JsonFormat(timezone = "GMT+8", pattern = "yyyy-MM-dd HH:mm:ss")
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
@Schema(description = "计划开始时间")
private java.util.Date planStartTime;
/**
*
*/
@Excel(name = "计划结束时间", width = 20, format = "yyyy-MM-dd HH:mm:ss")
@JsonFormat(timezone = "GMT+8", pattern = "yyyy-MM-dd HH:mm:ss")
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
@Schema(description = "计划结束时间")
private java.util.Date planEndTime;
/**
*
*/
@Excel(name = "审核人", width = 15)
@Schema(description = "审核人")
private java.lang.String auditor;
/**
*
*/
@Excel(name = "描述", width = 15)
@Schema(description = "描述")
private java.lang.String description;
/**
*
*/
@Schema(description = "所属部门")
private java.lang.String sysOrgCode;
/**
* ID
*/
@Excel(name = "仓库ID", width = 15)
@Schema(description = "仓库ID")
private java.lang.Long tenantId;
/**
*
*/
@Schema(description = "创建人")
private java.lang.String createBy;
/**
*
*/
@JsonFormat(timezone = "GMT+8", pattern = "yyyy-MM-dd HH:mm:ss")
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
@Schema(description = "创建日期")
private java.util.Date createTime;
/**
*
*/
@Schema(description = "更新人")
private java.lang.String updateBy;
/**
*
*/
@JsonFormat(timezone = "GMT+8", pattern = "yyyy-MM-dd HH:mm:ss")
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
@Schema(description = "更新日期")
private java.util.Date updateTime;
}

View File

@ -0,0 +1,31 @@
package org.cpte.modules.count.mapper;
import java.util.List;
import org.cpte.modules.count.entity.CountDetail;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import org.apache.ibatis.annotations.Param;
/**
* @Description:
* @author: cpte
* @Date: 2025-12-23
* @Version: V1.0
*/
public interface CountDetailMapper extends BaseMapper<CountDetail> {
/**
* id
*
* @param mainId id
* @return boolean
*/
public boolean deleteByMainId(@Param("mainId") Long mainId);
/**
* id
*
* @param mainId id
* @return List<CountDetail>
*/
public List<CountDetail> selectByMainId(@Param("mainId") Long mainId);
}

View File

@ -0,0 +1,17 @@
package org.cpte.modules.count.mapper;
import java.util.List;
import org.apache.ibatis.annotations.Param;
import org.cpte.modules.count.entity.CountPlan;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
/**
* @Description:
* @author: cpte
* @Date: 2025-12-23
* @Version: V1.0
*/
public interface CountPlanMapper extends BaseMapper<CountPlan> {
}

View File

@ -0,0 +1,18 @@
<?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="org.cpte.modules.count.mapper.CountDetailMapper">
<delete id="deleteByMainId">
DELETE
FROM data_count_detail
WHERE
count_plan_id = #{mainId}
</delete>
<select id="selectByMainId" resultType="org.cpte.modules.count.entity.CountDetail">
SELECT *
FROM data_count_detail
WHERE
count_plan_id = #{mainId}
</select>
</mapper>

View File

@ -0,0 +1,5 @@
<?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="org.cpte.modules.count.mapper.CountPlanMapper">
</mapper>

View File

@ -0,0 +1,22 @@
package org.cpte.modules.count.service;
import org.cpte.modules.count.entity.CountDetail;
import com.baomidou.mybatisplus.extension.service.IService;
import java.util.List;
/**
* @Description:
* @author: cpte
* @Date: 2025-12-23
* @Version: V1.0
*/
public interface ICountDetailService extends IService<CountDetail> {
/**
* id
*
* @param mainId id
* @return List<CountDetail>
*/
public List<CountDetail> selectByMainId(Long mainId);
}

View File

@ -0,0 +1,48 @@
package org.cpte.modules.count.service;
import org.cpte.modules.count.entity.CountDetail;
import org.cpte.modules.count.entity.CountPlan;
import com.baomidou.mybatisplus.extension.service.IService;
import java.io.Serializable;
import java.util.Collection;
import java.util.List;
/**
* @Description:
* @author: cpte
* @Date: 2025-12-23
* @Version: V1.0
*/
public interface ICountPlanService extends IService<CountPlan> {
/**
*
*
* @param countPlan
*/
public void saveMain(CountPlan countPlan);
/**
*
*
* @param countPlan
* @param countDetailList
*/
public void updateMain(CountPlan countPlan, List<CountDetail> countDetailList);
/**
*
*
* @param id
*/
public void delMain(Long id);
/**
*
*
* @param idList
*/
public void delBatchMain(Collection<? extends Serializable> idList);
}

View File

@ -0,0 +1,27 @@
package org.cpte.modules.count.service.impl;
import org.cpte.modules.count.entity.CountDetail;
import org.cpte.modules.count.mapper.CountDetailMapper;
import org.cpte.modules.count.service.ICountDetailService;
import org.springframework.stereotype.Service;
import java.util.List;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
/**
* @Description:
* @author: cpte
* @Date: 2025-12-23
* @Version: V1.0
*/
@Service
public class CountDetailServiceImpl extends ServiceImpl<CountDetailMapper, CountDetail> implements ICountDetailService {
@Autowired
private CountDetailMapper countDetailMapper;
@Override
public List<CountDetail> selectByMainId(Long mainId) {
return countDetailMapper.selectByMainId(mainId);
}
}

View File

@ -0,0 +1,235 @@
package org.cpte.modules.count.service.impl;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.shiro.SecurityUtils;
import org.cpte.modules.constant.GeneralConstant;
import org.cpte.modules.constant.enums.AsnStatusEnum;
import org.cpte.modules.constant.enums.CountPlanStatusEnum;
import org.cpte.modules.constant.enums.CountPlanTypeEnum;
import org.cpte.modules.constant.enums.InventoryStatusEnum;
import org.cpte.modules.count.entity.CountPlan;
import org.cpte.modules.count.entity.CountDetail;
import org.cpte.modules.count.mapper.CountDetailMapper;
import org.cpte.modules.count.mapper.CountPlanMapper;
import org.cpte.modules.count.service.ICountPlanService;
import org.cpte.modules.inventory.entity.Inventory;
import org.cpte.modules.inventory.mapper.InventoryMapper;
import org.cpte.modules.inventory.service.IInventoryService;
import org.cpte.modules.receive.entity.Asn;
import org.cpte.modules.serialNumber.AsnSerialNumberRule;
import org.cpte.modules.serialNumber.CountSerialNumberRule;
import org.jeecg.common.system.vo.LoginUser;
import org.springframework.stereotype.Service;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import java.io.Serializable;
import java.math.BigDecimal;
import java.util.*;
import java.util.stream.Collectors;
/**
* @Description:
* @author: cpte
* @Date: 2025-12-23
* @Version: V1.0
*/
@Service
public class CountPlanServiceImpl extends ServiceImpl<CountPlanMapper, CountPlan> implements ICountPlanService {
@Autowired
private CountDetailMapper countDetailMapper;
@Autowired
private InventoryMapper inventoryMapper;
@Autowired
private IInventoryService inventoryService;
@Autowired
private CountSerialNumberRule countSerialNumberRule;
@Override
@Transactional(rollbackFor = Exception.class)
public void saveMain(CountPlan countPlan) {
LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
countPlan.setTenantId(Long.parseLong(sysUser.getRelTenantIds()));
countPlan.setSysOrgCode(sysUser.getOrgCode());
String orderNo = countSerialNumberRule.generateSerialNumber(GeneralConstant.COUNT_ORDER_NO);
countPlan.setOrderNo(orderNo);
this.baseMapper.insert(countPlan);
//2.生成盘点明细
generateCountDetails(countPlan);
}
@Override
@Transactional(rollbackFor = Exception.class)
public void updateMain(CountPlan countPlan, List<CountDetail> countDetailList) {
this.baseMapper.updateById(countPlan);
//1.还原库存状态
restoreInventory(countDetailList);
//2.先删除子表数据
countDetailMapper.deleteByMainId(countPlan.getId());
//3.生成盘点明细
generateCountDetails(countPlan);
}
@Override
@Transactional(rollbackFor = Exception.class)
public void delMain(Long id) {
CountPlan countPlan = this.getById(id);
if (!CountPlanStatusEnum.CREATED.getValue().equals(countPlan.getStatus())) {
throw new RuntimeException("操作失败:【" + countPlan.getOrderNo() + "】盘点单,非创建状态不允许删除");
}
List<CountDetail> countDetails = countDetailMapper.selectByMainId(id);
restoreInventory(countDetails);
countDetailMapper.deleteByMainId(id);
this.baseMapper.deleteById(id);
}
@Override
@Transactional(rollbackFor = Exception.class)
public void delBatchMain(Collection<? extends Serializable> idList) {
List<String> orderNoList = new ArrayList<>();
for (Serializable id : idList) {
CountPlan countPlan = this.getById(id);
if (!CountPlanStatusEnum.CREATED.getValue().equals(countPlan.getStatus())) {
orderNoList.add(countPlan.getOrderNo());
continue;
}
List<CountDetail> countDetails = countDetailMapper.selectByMainId(Long.parseLong(id.toString()));
restoreInventory(countDetails);
countDetailMapper.deleteByMainId(Long.parseLong(id.toString()));
this.baseMapper.deleteById(id);
}
if (!orderNoList.isEmpty()) {
throw new RuntimeException("操作失败:【" + orderNoList + "】盘点单,非创建状态不允许删除");
}
}
/**
*
*
* @param countPlan
*/
private void generateCountDetails(CountPlan countPlan) {
// 1. 解析物料/托盘编码
Set<String> codes = parseCodes(countPlan);
// 3. 查询库存
List<Inventory> inventories = queryInventories(countPlan, codes);
// 4. 生成盘点明细和更新库存
processInventory(countPlan, inventories);
}
/**
* /
*
* @param countPlan
* @return /
*/
private Set<String> parseCodes(CountPlan countPlan) {
if (StringUtils.isBlank(countPlan.getDescription())) {
String errorMsg = CountPlanTypeEnum.ITEM.getValue().equals(countPlan.getCountType())
? "请输入物料" : "请输入托盘";
throw new RuntimeException(errorMsg);
}
return countPlan.getDescription().lines()
.filter(StringUtils::isNotBlank)
.map(String::trim)
.collect(Collectors.toSet());
}
/**
*
*
* @param countPlan
* @param codes /
* @return
*/
private List<Inventory> queryInventories(CountPlan countPlan, Set<String> codes) {
List<Inventory> inventories = inventoryMapper.queryByAreaIdAndCountTypeAndCodes(countPlan.getAreaId(), countPlan.getCountType(), codes);
if (CollectionUtils.isEmpty(inventories)) {
//去除codes集合中的[]
String errorMsg = String.join(", ", codes);
throw new RuntimeException("【" + errorMsg + "】无库存");
}
return inventories;
}
/**
*
*
* @param countPlan
* @param inventories
*/
private void processInventory(CountPlan countPlan, List<Inventory> inventories) {
List<CountDetail> countDetails = new ArrayList<>();
List<Inventory> inventoriesToUpdate = new ArrayList<>();
for (Inventory inventory : inventories) {
// 创建盘点明细
CountDetail countDetail = buildCountDetail(countPlan, inventory);
countDetails.add(countDetail);
// 更新库存状态
inventory.setStatus(InventoryStatusEnum.COUNTING.getValue());
inventoriesToUpdate.add(inventory);
}
if (CollectionUtils.isNotEmpty(countDetails)) {
countDetailMapper.insert(countDetails);
}
if (CollectionUtils.isNotEmpty(inventoriesToUpdate)) {
inventoryMapper.updateById(inventoriesToUpdate);
}
}
/**
*
*
* @param countPlan
* @param inventory
* @return
*/
private CountDetail buildCountDetail(CountPlan countPlan, Inventory inventory) {
return CountDetail.builder()
.countPlanId(countPlan.getId())
.itemId(inventory.getItemId())
.pointId(inventory.getPointId())
.itemKeyId(inventory.getItemKeyId())
.inventoryId(inventory.getId())
.stockId(inventory.getStockId())
.invQty(inventory.getQuantity())
.countQty(BigDecimal.ZERO)
.build();
}
/**
*
*
* @param countDetailList
*/
private void restoreInventory(List<CountDetail> countDetailList) {
if (CollectionUtils.isNotEmpty(countDetailList)) {
List<Inventory> inventoriesToUpdate = new ArrayList<>();
List<Long> inventoryIds = countDetailList.stream().map(CountDetail::getInventoryId).distinct().toList();
Map<Long, Inventory> inventoryMap = inventoryService.queryByInventoryIdsToMap(inventoryIds);
for (Inventory inventory : inventoryMap.values()) {
// 更新库存状态
inventory.setStatus(InventoryStatusEnum.AVAILABLE.getValue());
inventoriesToUpdate.add(inventory);
}
if (CollectionUtils.isNotEmpty(inventoriesToUpdate)) {
inventoryMapper.updateById(inventoriesToUpdate);
}
}
}
}

View File

@ -0,0 +1,121 @@
package org.cpte.modules.count.vo;
import java.util.List;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
import org.cpte.modules.count.entity.CountPlan;
import org.cpte.modules.count.entity.CountDetail;
import lombok.Data;
import org.jeecgframework.poi.excel.annotation.Excel;
import org.jeecgframework.poi.excel.annotation.ExcelEntity;
import org.jeecgframework.poi.excel.annotation.ExcelCollection;
import com.fasterxml.jackson.annotation.JsonFormat;
import org.springframework.format.annotation.DateTimeFormat;
import java.util.Date;
import org.jeecg.common.aspect.annotation.Dict;
import org.jeecg.common.constant.ProvinceCityArea;
import org.jeecg.common.util.SpringContextUtils;
import io.swagger.v3.oas.annotations.media.Schema;
/**
* @Description:
* @author: cpte
* @Date: 2025-12-23
* @Version: V1.0
*/
@Data
@Schema(description = "盘点")
public class CountPlanPage {
/**
* id
*/
@Schema(description = "id")
private java.lang.Long id;
/**
* ID
*/
@Schema(description = "库区ID")
private java.lang.Long areaId;
/**
* 0.;1.
*/
@Excel(name = "盘点类型0.按物料抽盘;1.按托盘抽盘", width = 15)
@Schema(description = "盘点类型0.按物料抽盘;1.按托盘抽盘")
private java.lang.Integer countType;
/**
* :1.;2.;3.;4.5.6.
*/
@Excel(name = "订单状态:1.已创建;2.已审核;3.盘点中;4.盘点完成、5.已取消、6.已关闭", width = 15)
@Schema(description = "订单状态:1.已创建;2.已审核;3.盘点中;4.盘点完成、5.已取消、6.已关闭")
private java.lang.Integer status;
/**
*
*/
@Excel(name = "计划开始时间", width = 20, format = "yyyy-MM-dd HH:mm:ss")
@JsonFormat(timezone = "GMT+8", pattern = "yyyy-MM-dd HH:mm:ss")
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
@Schema(description = "计划开始时间")
private java.util.Date planStartTime;
/**
*
*/
@Excel(name = "计划结束时间", width = 20, format = "yyyy-MM-dd HH:mm:ss")
@JsonFormat(timezone = "GMT+8", pattern = "yyyy-MM-dd HH:mm:ss")
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
@Schema(description = "计划结束时间")
private java.util.Date planEndTime;
/**
*
*/
@Excel(name = "审核人", width = 15)
@Schema(description = "审核人")
private java.lang.String auditor;
@Schema(description = "描述")
private java.lang.String description;
/**
*
*/
@Schema(description = "所属部门")
private java.lang.String sysOrgCode;
/**
* ID
*/
@Excel(name = "仓库ID", width = 15)
@Schema(description = "仓库ID")
private java.lang.Long tenantId;
/**
*
*/
@Schema(description = "创建人")
private java.lang.String createBy;
/**
*
*/
@JsonFormat(timezone = "GMT+8", pattern = "yyyy-MM-dd HH:mm:ss")
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
@Schema(description = "创建日期")
private java.util.Date createTime;
/**
*
*/
@Schema(description = "更新人")
private java.lang.String updateBy;
/**
*
*/
@JsonFormat(timezone = "GMT+8", pattern = "yyyy-MM-dd HH:mm:ss")
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
@Schema(description = "更新日期")
private java.util.Date updateTime;
@ExcelCollection(name = "盘点明细")
@Schema(description = "盘点明细")
private List<CountDetail> countDetailList;
}

View File

@ -3,11 +3,11 @@ package org.cpte.modules.inventory.mapper;
import org.apache.ibatis.annotations.Param;
import org.apache.ibatis.annotations.Select;
import org.cpte.modules.base.entity.Point;
import org.cpte.modules.inventory.entity.Inventory;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import java.util.List;
import java.util.Set;
/**
* @Description:
@ -38,6 +38,7 @@ public interface InventoryMapper extends BaseMapper<Inventory> {
@Param("layerNum") String layerNum,
@Param("minDepth") String minDepth,
@Param("maxDepth") String maxDepth);
/**
* ID
*
@ -71,4 +72,15 @@ public interface InventoryMapper extends BaseMapper<Inventory> {
*/
void deleteByStockIds(List<Long> stockIds);
/**
* ID
*
* @param areaId
* @param countType 0.;1.
* @param codes /
* @return List<Inventory>
*/
List<Inventory> queryByAreaIdAndCountTypeAndCodes(@Param("areaId") Long areaId, @Param("countType") Integer countType, @Param("codes") Set<String> codes);
}

View File

@ -29,4 +29,28 @@
#{stockId}
</foreach>
</delete>
<select id="queryByAreaIdAndCountTypeAndCodes" resultType="org.cpte.modules.inventory.entity.Inventory">
SELECT inv.* FROM data_inventory inv
JOIN base_point point ON point.id = inv.point_id
AND point.area_id = #{areaId}
WHERE inv.status =1
AND inv.quantity > 0
<choose>
<when test="countType == 0">
JOIN base_item item ON item.id=inv.item_id
AND item.item_code IN
<foreach collection="codes" item="code" open="(" separator="," close=")">
#{code}
</foreach>
</when>
<when test="countType == 1">
JOIN base_stock stock ON stock.id=inv.stock_id
AND stock.stock_code IN
<foreach collection="codes" item="code" open="(" separator="," close=")">
#{code}
</foreach>
</when>
</choose>
</select>
</mapper>

View File

@ -36,7 +36,7 @@ public class SyncItemJob implements Job {
// 定义日期格式化器
private static final DateTimeFormatter DATE_FORMATTER = DateTimeFormatter.ofPattern("yyyy-MM-dd");
private static final String LAST_PROCESSED_DATE_KEY = "lastProcessedDate";
private static final String LAST_PROCESSED_DATE_KEY = "LAST_PROCESSED_DATE_KEY";
@Override
public void execute(JobExecutionContext jobExecutionContext) throws JobExecutionException {

View File

@ -0,0 +1,75 @@
package org.cpte.modules.quartz.job;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import lombok.extern.slf4j.Slf4j;
import org.cpte.modules.base.service.IItemService;
import org.cpte.modules.base.service.IPointService;
import org.jeecg.common.constant.CommonConstant;
import org.jeecg.common.util.RedisUtil;
import org.jeecg.modules.base.service.BaseCommonService;
import org.quartz.Job;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.springframework.beans.factory.annotation.Autowired;
import java.time.LocalDate;
import java.time.format.DateTimeFormatter;
/**
*
*/
@Slf4j
public class SyncPointJob implements Job {
@Autowired
private IPointService pointService;
@Autowired
private RedisUtil redisUtil;
@Autowired
private BaseCommonService baseCommonService;
private String parameter;
public void setParameter(String parameter) {
this.parameter = parameter;
}
private static final Integer MAX_PAGE_NUM=10000;
private static final String PAGE_NUM_KEY = "PAGE_NUM_KEY";
@Override
public void execute(JobExecutionContext jobExecutionContext) throws JobExecutionException {
try {
//获取配置的参数
JSONObject params = JSON.parseObject(this.parameter);
int pageSize = Integer.parseInt(params.getString("pageSize"));
int pageNum = Integer.parseInt(params.getString("pageNum"));
log.info("当前页数: {} - 每页条数: {}", pageNum, pageSize);
// 检查是否需要处理
if (pageNum>=MAX_PAGE_NUM) {
log.info("已处理到最新页数,无需继续查询");
return;
}
boolean success = pointService.syncPoint(pageNum,pageSize);
if (success) {
updateLastProcessedDate(pageNum);
}
} catch (Exception e) {
baseCommonService.addLog(String.valueOf(e), CommonConstant.LOG_TYPE_4, null);
}
}
/**
*
*/
private void updateLastProcessedDate(Integer pageNum) {
redisUtil.set(PAGE_NUM_KEY, pageNum);
}
}

View File

@ -173,7 +173,7 @@ public class AsnController {
//@AutoLog(value = "入库单-通过id查询")
@Operation(summary = "入库单-通过id查询")
@GetMapping(value = "/queryById")
public Result<Asn> queryById(@RequestParam(name = "id", required = true) String id) {
public Result<Asn> queryById(@RequestParam(name = "id", required = true) Long id) {
Asn asn = asnService.getById(id);
if (asn == null) {
return Result.error("未找到对应数据");

View File

@ -0,0 +1,41 @@
package org.cpte.modules.serialNumber;
import com.alibaba.fastjson.JSONObject;
import lombok.extern.slf4j.Slf4j;
import org.cpte.modules.utils.CodeGeneratorUtil;
import org.jeecg.common.handler.IFillRuleHandler;
import org.jeecg.modules.system.mapper.SysFillRuleMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
@Service
@Slf4j
public class CountSerialNumberRule implements IFillRuleHandler {
@Autowired
private CodeGeneratorUtil codeGeneratorUtil;
@Autowired
private SysFillRuleMapper sysFillRuleMapper;
@Override
public Object execute(JSONObject params, JSONObject formData) {
String prefix = params.getString("code");
String code = codeGeneratorUtil.generateSerialNumber(prefix);
log.info("生成业务编号:{}", code);
return code;
}
public String generateSerialNumber(String ruleCode) {
String ruleParams = sysFillRuleMapper.queryByRuleCode(ruleCode);
JSONObject jsonObject = JSONObject.parseObject(ruleParams);
String prefix = null;
if (jsonObject != null) {
prefix = jsonObject.getString("code");
} else {
prefix = "PK";
}
return codeGeneratorUtil.generateSerialNumber(prefix);
}
}

View File

@ -174,7 +174,7 @@ public class PickController {
//@AutoLog(value = "出库单-通过id查询")
@Operation(summary = "出库单-通过id查询")
@GetMapping(value = "/queryById")
public Result<Pick> queryById(@RequestParam(name = "id", required = true) String id) {
public Result<Pick> queryById(@RequestParam(name = "id", required = true) Long id) {
Pick pick = pickService.getById(id);
if (pick == null) {
return Result.error("未找到对应数据");

View File

@ -63,26 +63,20 @@ public class ITesAgvServiceImpl implements ITesAgvService {
newMovePodTaskRequest.setWarehouseID("HETU");
newMovePodTaskRequest.setRequestID(String.valueOf(System.currentTimeMillis()));
newMovePodTaskRequest.setRequestTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
newMovePodTaskRequest.setClientCode("WCS");
newMovePodTaskRequest.setClientCode("WMS");
newMovePodTaskRequest.setPriority(agvTask.getPriority());
newMovePodTaskRequest.setSrcType(1);
newMovePodTaskRequest.setPodID(agvTask.getCarrierCode());
newMovePodTaskRequest.setBizID(agvTask.getId().toString());
newMovePodTaskRequest.setReplacePodTask(0);
newMovePodTaskRequest.setDesType(1);
newMovePodTaskRequest.setDesNodeID(agvTask.getEndCode());
newMovePodTaskRequest.setDesType(2);
//newMovePodTaskRequest.setDesStorageID(agvTask.getDestination());
NewMovePodTaskRequest.DesExt desExt = new NewMovePodTaskRequest.DesExt();
desExt.setUnload(1);
desExt.setRobotFace(3.14);
newMovePodTaskRequest.setDesExt(desExt);
NewMovePodTaskRequest.TaskExt taskExt = new NewMovePodTaskRequest.TaskExt();
taskExt.setAutoToRest(1);
taskExt.setTimeoutFailed(86400);
newMovePodTaskRequest.setTaskExt(taskExt);
return JSON.toJSONString(newMovePodTaskRequest);
}
@ -108,6 +102,7 @@ public class ITesAgvServiceImpl implements ITesAgvService {
" \"taskID\":74602" +
" }\n" +
"}";
log.info("TES任务下发URL:{} - 请求参数:{} - 响应结果:{}", url, json, result);
if (StringUtils.isEmpty(result)) {
returnMsg = "Tes返回信息:接口调用失败";
throw new RuntimeException(returnMsg);

View File

@ -43,20 +43,21 @@ public class CommonController {
/**
* local miniominio alioss
*/
@Value(value="${jeecg.uploadType}")
@Value(value = "${jeecg.uploadType}")
private String uploadType;
/**
* @Author
* @return
* @Author
*/
@GetMapping("/403")
public Result<?> noauth() {
public Result<?> noauth() {
return Result.error("没有权限,请联系管理员分配权限!");
}
/**
*
*
* @param request
* @param response
* @return
@ -68,22 +69,22 @@ public class CommonController {
String bizPath = request.getParameter("biz");
MultipartHttpServletRequest multipartRequest = (MultipartHttpServletRequest) request;
MultipartFile file = multipartRequest.getFile("file");
// 文件安全校验,防止上传漏洞文件
SsrfFileTypeFilter.checkUploadFileType(file, bizPath);
if (oConvertUtils.isEmpty(bizPath)) {
bizPath = CommonConstant.UPLOAD_TYPE_OSS.equals(uploadType) ? "upload" : "";
}
if(CommonConstant.UPLOAD_TYPE_LOCAL.equals(uploadType)){
savePath = this.uploadLocal(file,bizPath);
}else{
if (CommonConstant.UPLOAD_TYPE_LOCAL.equals(uploadType)) {
savePath = this.uploadLocal(file, bizPath);
} else {
savePath = CommonUtils.upload(file, bizPath, uploadType);
}
if(oConvertUtils.isNotEmpty(savePath)){
if (oConvertUtils.isNotEmpty(savePath)) {
result.setMessage(savePath);
result.setSuccess(true);
}else {
} else {
result.setMessage("上传失败!");
result.setSuccess(false);
}
@ -92,15 +93,16 @@ public class CommonController {
/**
*
* @param mf
* @param bizPath
*
* @param mf
* @param bizPath
* @return
*/
private String uploadLocal(MultipartFile mf,String bizPath){
private String uploadLocal(MultipartFile mf, String bizPath) {
try {
String ctxPath = uploadpath;
String fileName = null;
File file = new File(ctxPath + File.separator + bizPath + File.separator );
File file = new File(ctxPath + File.separator + bizPath + File.separator);
if (!file.exists()) {
// 创建文件根目录
file.mkdirs();
@ -108,18 +110,18 @@ public class CommonController {
// 获取文件名
String orgName = mf.getOriginalFilename();
orgName = CommonUtils.getFileName(orgName);
if(orgName.indexOf(SymbolConstant.SPOT)!=-1){
if (orgName.indexOf(SymbolConstant.SPOT) != -1) {
fileName = orgName.substring(0, orgName.lastIndexOf(".")) + "_" + System.currentTimeMillis() + orgName.substring(orgName.lastIndexOf("."));
}else{
fileName = orgName+ "_" + System.currentTimeMillis();
} else {
fileName = orgName + "_" + System.currentTimeMillis();
}
String savePath = file.getPath() + File.separator + fileName;
File savefile = new File(savePath);
FileCopyUtils.copy(mf.getBytes(), savefile);
String dbpath = null;
if(oConvertUtils.isNotEmpty(bizPath)){
if (oConvertUtils.isNotEmpty(bizPath)) {
dbpath = bizPath + File.separator + fileName;
}else{
} else {
dbpath = fileName;
}
if (dbpath.contains(SymbolConstant.DOUBLE_BACKSLASH)) {
@ -180,12 +182,12 @@ public class CommonController {
public void view(HttpServletRequest request, HttpServletResponse response) {
// ISO-8859-1 ==> UTF-8 进行编码转换
String imgPath = extractPathFromPattern(request);
if(oConvertUtils.isEmpty(imgPath) || CommonConstant.STRING_NULL.equals(imgPath)){
if (oConvertUtils.isEmpty(imgPath) || CommonConstant.STRING_NULL.equals(imgPath) || imgPath.contains("上传失败")) {
return;
}
try {
imgPath = imgPath.replace("..", "").replace("../","");
imgPath = imgPath.replace("..", "").replace("../", "");
if (imgPath.endsWith(SymbolConstant.COMMA)) {
imgPath = imgPath.substring(0, imgPath.length() - 1);
}
@ -195,16 +197,16 @@ public class CommonController {
String filePath = uploadpath + File.separator + imgPath;
File file = new File(filePath);
if(!file.exists()){
if (!file.exists()) {
response.setStatus(404);
log.warn("文件["+imgPath+"]不存在..");
log.warn("文件[" + imgPath + "]不存在..");
return;
//throw new RuntimeException();
}
// 设置强制下载不打开
response.setContentType("application/force-download");
response.addHeader("Content-Disposition", "attachment;fileName=" + new String(file.getName().getBytes(StandardCharsets.UTF_8), StandardCharsets.ISO_8859_1));
// 结合 StreamingResponseBody 的流式写法
try (InputStream inputStream = new BufferedInputStream(new FileInputStream(file));
OutputStream outputStream = response.getOutputStream()) {
@ -282,9 +284,9 @@ public class CommonController {
// }
/**
* @pdfIframe
* @param modelAndView
* @return
* @pdfIframe
*/
@RequestMapping("/pdf/pdfPreviewIframe")
public ModelAndView pdfPreviewIframe(ModelAndView modelAndView) {
@ -293,8 +295,9 @@ public class CommonController {
}
/**
* URL
* URL/
* URL
* URL/
*
* @param request
* @return
*/

View File

@ -215,13 +215,13 @@ jeecg:
uploadType: local
# 前端访问地址
domainUrl:
pc: http://localhost:8080
pc: http://localhost:8000/cpte-wms/sys/common/upload
app: http://localhost:8051
path:
#文件上传根目录 设置
upload: /home/wms/java/upFiles
upload: /home/wms/upload
#webapp文件路径
webapp: /home/wms/java/webapp
webapp: /home/wms/webapp
shiro:
excludeUrls: /test/cpteDemo/demo3,/test/cpteDemo/redisDemo/**,/bigscreen/category/**,/bigscreen/visual/**,/bigscreen/map/**,/jmreport/bigscreen2/**
#阿里云oss存储和大鱼短信秘钥配置

View File

@ -207,10 +207,10 @@ jeecg:
#签名拦截接口
signUrls: /sys/dict/getDictItems/*,/sys/dict/loadDict/*,/sys/dict/loadDictOrderByValue/*,/sys/dict/loadDictItem/*,/sys/dict/loadTreeData,/sys/api/queryTableDictItemsByCode,/sys/api/queryFilterTableDictInfo,/sys/api/queryTableDictByKeys,/sys/api/translateDictFromTable,/sys/api/translateDictFromTableByKeys,/sys/sendChangePwdSms,/sys/user/sendChangePhoneSms,/sys/sms,/desform/api/sendVerifyCode
# local\minio\alioss
uploadType: alioss
uploadType: local
# 前端访问地址
domainUrl:
pc: http://localhost:8080
pc: http://localhost:8000/cpte-wms/sys/common/upload
app: http://localhost:8051
path:
#文件上传根目录 设置

View File

@ -1,9 +1,9 @@
# ????? Java ???????
project_path=D:\Project\????\Cpte-Cloud\cpte-boot-module\cpte-module-wms
project_path=D:\\Project\\ZhongYou\\Cpte-Cloud\\cpte-boot-module\\cpte-module-wms
# ?????
bussi_package=org.cpte.modules
ui_project_path=D:\\Project\\ZhongYou\\Cpte-Vue3
#default code path
#source_root_package=src
#webroot_package=WebRoot
@ -26,4 +26,4 @@ db_filed_convert=true
page_search_filed_num=1
#page_filter_fields
page_filter_fields=create_time,create_by,update_time,update_by
exclude_table=act_,ext_act_,design_,onl_,sys_,qrtz_,base_
exclude_table=act_,ext_act_,design_,onl_,sys_,qrtz_,base_,data_

View File

@ -1,8 +1,8 @@
#mysql
diver_name=com.mysql.jdbc.Driver
url=jdbc:mysql://47.103.100.52:53306/cpte-wms?useUnicode=true&characterEncoding=UTF-8
url=jdbc:mysql://10.254.27.192:3306/cpte-wms?useUnicode=true&characterEncoding=UTF-8
username=root
password=Youchain@56
password=cpte@123
database_name=cpte-wms
#oracle