Prechádzať zdrojové kódy

pms功能优化 库存相关功能优化

zhangcl 4 mesiacov pred
rodič
commit
1bf589ab30
26 zmenil súbory, kde vykonal 1928 pridanie a 0 odobranie
  1. 3 0
      yudao-module-pms/yudao-module-pms-api/src/main/java/cn/iocoder/yudao/module/pms/enums/ErrorCodeConstant.java
  2. 93 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotlockstock/IotLockStockController.java
  3. 80 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotlockstock/vo/IotLockStockPageReqVO.java
  4. 96 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotlockstock/vo/IotLockStockRespVO.java
  5. 70 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotlockstock/vo/IotLockStockSaveReqVO.java
  6. 93 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotoutbound/IotOutboundController.java
  7. 89 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotoutbound/vo/IotOutboundPageReqVO.java
  8. 108 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotoutbound/vo/IotOutboundRespVO.java
  9. 79 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotoutbound/vo/IotOutboundSaveReqVO.java
  10. 93 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotsapstock/IotSapStockController.java
  11. 86 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotsapstock/vo/IotSapStockPageReqVO.java
  12. 104 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotsapstock/vo/IotSapStockRespVO.java
  13. 76 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotsapstock/vo/IotSapStockSaveReqVO.java
  14. 105 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/dataobject/iotlockstock/IotLockStockDO.java
  15. 117 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/dataobject/iotoutbound/IotOutboundDO.java
  16. 113 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/dataobject/iotsapstock/IotSapStockDO.java
  17. 42 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/mysql/iotlockstock/IotLockStockMapper.java
  18. 45 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/mysql/iotoutbound/IotOutboundMapper.java
  19. 44 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/mysql/iotsapstock/IotSapStockMapper.java
  20. 55 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotlockstock/IotLockStockService.java
  21. 71 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotlockstock/IotLockStockServiceImpl.java
  22. 55 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotoutbound/IotOutboundService.java
  23. 71 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotoutbound/IotOutboundServiceImpl.java
  24. 55 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotsapstock/IotSapStockService.java
  25. 71 0
      yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotsapstock/IotSapStockServiceImpl.java
  26. 14 0
      yudao-module-system/yudao-module-system-biz/src/main/java/cn/iocoder/yudao/module/system/dal/dataobject/dept/DeptDO.java

+ 3 - 0
yudao-module-pms/yudao-module-pms-api/src/main/java/cn/iocoder/yudao/module/pms/enums/ErrorCodeConstant.java

@@ -25,4 +25,7 @@ public interface ErrorCodeConstant{
     ErrorCode IOT_INFO_EXISTS = new ErrorCode(126, "存在子分类");
     ErrorCode IOT_FAILURE_REPORT_NOT_EXISTS = new ErrorCode(127, "故障上报不存在");
     ErrorCode IOT_MAINTAIN_NOT_EXISTS = new ErrorCode(128, "维修工单不存在");
+    ErrorCode IOT_LOCK_STOCK_NOT_EXISTS = new ErrorCode(129, "PMS 本地 库存不存在");
+    ErrorCode IOT_OUTBOUND_NOT_EXISTS = new ErrorCode(130, "PMS 出库不存在");
+    ErrorCode IOT_SAP_STOCK_NOT_EXISTS = new ErrorCode(131, "PMS SAP 库存(通用库存/项目部库存)不存在");
 }

+ 93 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotlockstock/IotLockStockController.java

@@ -0,0 +1,93 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotlockstock;
+
+import cn.iocoder.yudao.framework.apilog.core.annotation.ApiAccessLog;
+import cn.iocoder.yudao.framework.common.pojo.CommonResult;
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
+import cn.iocoder.yudao.framework.excel.core.util.ExcelUtils;
+import cn.iocoder.yudao.module.pms.controller.admin.iotlockstock.vo.IotLockStockPageReqVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotlockstock.vo.IotLockStockRespVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotlockstock.vo.IotLockStockSaveReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotlockstock.IotLockStockDO;
+import cn.iocoder.yudao.module.pms.service.iotlockstock.IotLockStockService;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.Parameter;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import javax.servlet.http.HttpServletResponse;
+import javax.validation.Valid;
+import java.io.IOException;
+import java.util.List;
+
+import static cn.iocoder.yudao.framework.apilog.core.enums.OperateTypeEnum.EXPORT;
+import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
+
+@Tag(name = "管理后台 - PMS 本地 库存")
+@RestController
+@RequestMapping("/pms/iot-lock-stock")
+@Validated
+public class IotLockStockController {
+
+    @Resource
+    private IotLockStockService iotLockStockService;
+
+    @PostMapping("/create")
+    @Operation(summary = "创建PMS 本地 库存")
+    @PreAuthorize("@ss.hasPermission('pms:iot-lock-stock:create')")
+    public CommonResult<Long> createIotLockStock(@Valid @RequestBody IotLockStockSaveReqVO createReqVO) {
+        return success(iotLockStockService.createIotLockStock(createReqVO));
+    }
+
+    @PutMapping("/update")
+    @Operation(summary = "更新PMS 本地 库存")
+    @PreAuthorize("@ss.hasPermission('pms:iot-lock-stock:update')")
+    public CommonResult<Boolean> updateIotLockStock(@Valid @RequestBody IotLockStockSaveReqVO updateReqVO) {
+        iotLockStockService.updateIotLockStock(updateReqVO);
+        return success(true);
+    }
+
+    @DeleteMapping("/delete")
+    @Operation(summary = "删除PMS 本地 库存")
+    @Parameter(name = "id", description = "编号", required = true)
+    @PreAuthorize("@ss.hasPermission('pms:iot-lock-stock:delete')")
+    public CommonResult<Boolean> deleteIotLockStock(@RequestParam("id") Long id) {
+        iotLockStockService.deleteIotLockStock(id);
+        return success(true);
+    }
+
+    @GetMapping("/get")
+    @Operation(summary = "获得PMS 本地 库存")
+    @Parameter(name = "id", description = "编号", required = true, example = "1024")
+    @PreAuthorize("@ss.hasPermission('pms:iot-lock-stock:query')")
+    public CommonResult<IotLockStockRespVO> getIotLockStock(@RequestParam("id") Long id) {
+        IotLockStockDO iotLockStock = iotLockStockService.getIotLockStock(id);
+        return success(BeanUtils.toBean(iotLockStock, IotLockStockRespVO.class));
+    }
+
+    @GetMapping("/page")
+    @Operation(summary = "获得PMS 本地 库存分页")
+    @PreAuthorize("@ss.hasPermission('pms:iot-lock-stock:query')")
+    public CommonResult<PageResult<IotLockStockRespVO>> getIotLockStockPage(@Valid IotLockStockPageReqVO pageReqVO) {
+        PageResult<IotLockStockDO> pageResult = iotLockStockService.getIotLockStockPage(pageReqVO);
+        return success(BeanUtils.toBean(pageResult, IotLockStockRespVO.class));
+    }
+
+    @GetMapping("/export-excel")
+    @Operation(summary = "导出PMS 本地 库存 Excel")
+    @PreAuthorize("@ss.hasPermission('pms:iot-lock-stock:export')")
+    @ApiAccessLog(operateType = EXPORT)
+    public void exportIotLockStockExcel(@Valid IotLockStockPageReqVO pageReqVO,
+              HttpServletResponse response) throws IOException {
+        pageReqVO.setPageSize(PageParam.PAGE_SIZE_NONE);
+        List<IotLockStockDO> list = iotLockStockService.getIotLockStockPage(pageReqVO).getList();
+        // 导出 Excel
+        ExcelUtils.write(response, "PMS 本地 库存.xls", "数据", IotLockStockRespVO.class,
+                        BeanUtils.toBean(list, IotLockStockRespVO.class));
+    }
+
+}

+ 80 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotlockstock/vo/IotLockStockPageReqVO.java

@@ -0,0 +1,80 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotlockstock.vo;
+
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.ToString;
+import org.springframework.format.annotation.DateTimeFormat;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND;
+
+@Schema(description = "管理后台 - PMS 本地 库存分页 Request VO")
+@Data
+@EqualsAndHashCode(callSuper = true)
+@ToString(callSuper = true)
+public class IotLockStockPageReqVO extends PageParam {
+
+    @Schema(description = "组织部门id", example = "4517")
+    private Long deptId;
+
+    @Schema(description = "工厂(SAP) 专业公司")
+    private String factory;
+
+    @Schema(description = "库存地点 - SAP 部门 项目部级")
+    private String projectDepartment;
+
+    @Schema(description = "成本中心(SAP) 库存地点 小队")
+    private String costCenter;
+
+    @Schema(description = "领料单号")
+    private String pickingListNumber;
+
+    @Schema(description = "物料编码")
+    private String materialCode;
+
+    @Schema(description = "物料名称", example = "王五")
+    private String materialName;
+
+    @Schema(description = "物料组", example = "芋艿")
+    private String materialGroupName;
+
+    @Schema(description = "物料组id", example = "23371")
+    private Long materialGroupId;
+
+    @Schema(description = "数量")
+    private BigDecimal quantity;
+
+    @Schema(description = "单价", example = "5632")
+    private BigDecimal unitPrice;
+
+    @Schema(description = "单位")
+    private String unit;
+
+    @Schema(description = "入库时间")
+    @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND)
+    private LocalDateTime[] storageTime;
+
+    @Schema(description = "排序")
+    private Integer sort;
+
+    @Schema(description = "状态 0启用  1停用", example = "2")
+    private Integer status;
+
+    @Schema(description = "流程实例id", example = "11671")
+    private String processInstanceId;
+
+    @Schema(description = "审批状态 未提交、审批中、审批通过、审批不通过、已取消", example = "2")
+    private Integer auditStatus;
+
+    @Schema(description = "备注", example = "你猜")
+    private String remark;
+
+    @Schema(description = "创建时间")
+    @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND)
+    private LocalDateTime[] createTime;
+
+}

+ 96 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotlockstock/vo/IotLockStockRespVO.java

@@ -0,0 +1,96 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotlockstock.vo;
+
+import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
+import com.alibaba.excel.annotation.ExcelProperty;
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+@Schema(description = "管理后台 - PMS 本地 库存 Response VO")
+@Data
+@ExcelIgnoreUnannotated
+public class IotLockStockRespVO {
+
+    @Schema(description = "主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "26886")
+    @ExcelProperty("主键")
+    private Long id;
+
+    @Schema(description = "组织部门id", example = "4517")
+    @ExcelProperty("组织部门id")
+    private Long deptId;
+
+    @Schema(description = "工厂(SAP) 专业公司")
+    @ExcelProperty("工厂(SAP) 专业公司")
+    private String factory;
+
+    @Schema(description = "库存地点 - SAP 部门 项目部级")
+    @ExcelProperty("库存地点 - SAP 部门 项目部级")
+    private String projectDepartment;
+
+    @Schema(description = "成本中心(SAP) 库存地点 小队")
+    @ExcelProperty("成本中心(SAP) 库存地点 小队")
+    private String costCenter;
+
+    @Schema(description = "领料单号")
+    @ExcelProperty("领料单号")
+    private String pickingListNumber;
+
+    @Schema(description = "物料编码")
+    @ExcelProperty("物料编码")
+    private String materialCode;
+
+    @Schema(description = "物料名称", example = "王五")
+    @ExcelProperty("物料名称")
+    private String materialName;
+
+    @Schema(description = "物料组", example = "芋艿")
+    @ExcelProperty("物料组")
+    private String materialGroupName;
+
+    @Schema(description = "物料组id", example = "23371")
+    @ExcelProperty("物料组id")
+    private Long materialGroupId;
+
+    @Schema(description = "数量")
+    @ExcelProperty("数量")
+    private BigDecimal quantity;
+
+    @Schema(description = "单价", example = "5632")
+    @ExcelProperty("单价")
+    private BigDecimal unitPrice;
+
+    @Schema(description = "单位")
+    @ExcelProperty("单位")
+    private String unit;
+
+    @Schema(description = "入库时间")
+    @ExcelProperty("入库时间")
+    private LocalDateTime storageTime;
+
+    @Schema(description = "排序")
+    @ExcelProperty("排序")
+    private Integer sort;
+
+    @Schema(description = "状态 0启用  1停用", example = "2")
+    @ExcelProperty("状态 0启用  1停用")
+    private Integer status;
+
+    @Schema(description = "流程实例id", example = "11671")
+    @ExcelProperty("流程实例id")
+    private String processInstanceId;
+
+    @Schema(description = "审批状态 未提交、审批中、审批通过、审批不通过、已取消", example = "2")
+    @ExcelProperty("审批状态 未提交、审批中、审批通过、审批不通过、已取消")
+    private Integer auditStatus;
+
+    @Schema(description = "备注", example = "你猜")
+    @ExcelProperty("备注")
+    private String remark;
+
+    @Schema(description = "创建时间", requiredMode = Schema.RequiredMode.REQUIRED)
+    @ExcelProperty("创建时间")
+    private LocalDateTime createTime;
+
+}

+ 70 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotlockstock/vo/IotLockStockSaveReqVO.java

@@ -0,0 +1,70 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotlockstock.vo;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+@Schema(description = "管理后台 - PMS 本地 库存新增/修改 Request VO")
+@Data
+public class IotLockStockSaveReqVO {
+
+    @Schema(description = "主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "26886")
+    private Long id;
+
+    @Schema(description = "组织部门id", example = "4517")
+    private Long deptId;
+
+    @Schema(description = "工厂(SAP) 专业公司")
+    private String factory;
+
+    @Schema(description = "库存地点 - SAP 部门 项目部级")
+    private String projectDepartment;
+
+    @Schema(description = "成本中心(SAP) 库存地点 小队")
+    private String costCenter;
+
+    @Schema(description = "领料单号")
+    private String pickingListNumber;
+
+    @Schema(description = "物料编码")
+    private String materialCode;
+
+    @Schema(description = "物料名称", example = "王五")
+    private String materialName;
+
+    @Schema(description = "物料组", example = "芋艿")
+    private String materialGroupName;
+
+    @Schema(description = "物料组id", example = "23371")
+    private Long materialGroupId;
+
+    @Schema(description = "数量")
+    private BigDecimal quantity;
+
+    @Schema(description = "单价", example = "5632")
+    private BigDecimal unitPrice;
+
+    @Schema(description = "单位")
+    private String unit;
+
+    @Schema(description = "入库时间")
+    private LocalDateTime storageTime;
+
+    @Schema(description = "排序")
+    private Integer sort;
+
+    @Schema(description = "状态 0启用  1停用", example = "2")
+    private Integer status;
+
+    @Schema(description = "流程实例id", example = "11671")
+    private String processInstanceId;
+
+    @Schema(description = "审批状态 未提交、审批中、审批通过、审批不通过、已取消", example = "2")
+    private Integer auditStatus;
+
+    @Schema(description = "备注", example = "你猜")
+    private String remark;
+
+}

+ 93 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotoutbound/IotOutboundController.java

@@ -0,0 +1,93 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotoutbound;
+
+import cn.iocoder.yudao.framework.apilog.core.annotation.ApiAccessLog;
+import cn.iocoder.yudao.framework.common.pojo.CommonResult;
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
+import cn.iocoder.yudao.framework.excel.core.util.ExcelUtils;
+import cn.iocoder.yudao.module.pms.controller.admin.iotoutbound.vo.IotOutboundPageReqVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotoutbound.vo.IotOutboundRespVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotoutbound.vo.IotOutboundSaveReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotoutbound.IotOutboundDO;
+import cn.iocoder.yudao.module.pms.service.iotoutbound.IotOutboundService;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.Parameter;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import javax.servlet.http.HttpServletResponse;
+import javax.validation.Valid;
+import java.io.IOException;
+import java.util.List;
+
+import static cn.iocoder.yudao.framework.apilog.core.enums.OperateTypeEnum.EXPORT;
+import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
+
+@Tag(name = "管理后台 - PMS 出库")
+@RestController
+@RequestMapping("/pms/iot-outbound")
+@Validated
+public class IotOutboundController {
+
+    @Resource
+    private IotOutboundService iotOutboundService;
+
+    @PostMapping("/create")
+    @Operation(summary = "创建PMS 出库")
+    @PreAuthorize("@ss.hasPermission('pms:iot-outbound:create')")
+    public CommonResult<Long> createIotOutbound(@Valid @RequestBody IotOutboundSaveReqVO createReqVO) {
+        return success(iotOutboundService.createIotOutbound(createReqVO));
+    }
+
+    @PutMapping("/update")
+    @Operation(summary = "更新PMS 出库")
+    @PreAuthorize("@ss.hasPermission('pms:iot-outbound:update')")
+    public CommonResult<Boolean> updateIotOutbound(@Valid @RequestBody IotOutboundSaveReqVO updateReqVO) {
+        iotOutboundService.updateIotOutbound(updateReqVO);
+        return success(true);
+    }
+
+    @DeleteMapping("/delete")
+    @Operation(summary = "删除PMS 出库")
+    @Parameter(name = "id", description = "编号", required = true)
+    @PreAuthorize("@ss.hasPermission('pms:iot-outbound:delete')")
+    public CommonResult<Boolean> deleteIotOutbound(@RequestParam("id") Long id) {
+        iotOutboundService.deleteIotOutbound(id);
+        return success(true);
+    }
+
+    @GetMapping("/get")
+    @Operation(summary = "获得PMS 出库")
+    @Parameter(name = "id", description = "编号", required = true, example = "1024")
+    @PreAuthorize("@ss.hasPermission('pms:iot-outbound:query')")
+    public CommonResult<IotOutboundRespVO> getIotOutbound(@RequestParam("id") Long id) {
+        IotOutboundDO iotOutbound = iotOutboundService.getIotOutbound(id);
+        return success(BeanUtils.toBean(iotOutbound, IotOutboundRespVO.class));
+    }
+
+    @GetMapping("/page")
+    @Operation(summary = "获得PMS 出库分页")
+    @PreAuthorize("@ss.hasPermission('pms:iot-outbound:query')")
+    public CommonResult<PageResult<IotOutboundRespVO>> getIotOutboundPage(@Valid IotOutboundPageReqVO pageReqVO) {
+        PageResult<IotOutboundDO> pageResult = iotOutboundService.getIotOutboundPage(pageReqVO);
+        return success(BeanUtils.toBean(pageResult, IotOutboundRespVO.class));
+    }
+
+    @GetMapping("/export-excel")
+    @Operation(summary = "导出PMS 出库 Excel")
+    @PreAuthorize("@ss.hasPermission('pms:iot-outbound:export')")
+    @ApiAccessLog(operateType = EXPORT)
+    public void exportIotOutboundExcel(@Valid IotOutboundPageReqVO pageReqVO,
+              HttpServletResponse response) throws IOException {
+        pageReqVO.setPageSize(PageParam.PAGE_SIZE_NONE);
+        List<IotOutboundDO> list = iotOutboundService.getIotOutboundPage(pageReqVO).getList();
+        // 导出 Excel
+        ExcelUtils.write(response, "PMS 出库.xls", "数据", IotOutboundRespVO.class,
+                        BeanUtils.toBean(list, IotOutboundRespVO.class));
+    }
+
+}

+ 89 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotoutbound/vo/IotOutboundPageReqVO.java

@@ -0,0 +1,89 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotoutbound.vo;
+
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.ToString;
+import org.springframework.format.annotation.DateTimeFormat;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND;
+
+@Schema(description = "管理后台 - PMS 出库分页 Request VO")
+@Data
+@EqualsAndHashCode(callSuper = true)
+@ToString(callSuper = true)
+public class IotOutboundPageReqVO extends PageParam {
+
+    @Schema(description = "入库id", example = "27552")
+    private Long storageId;
+
+    @Schema(description = "组织部门id", example = "10467")
+    private Long deptId;
+
+    @Schema(description = "工厂(SAP) 专业公司")
+    private String factory;
+
+    @Schema(description = "库存地点 - SAP 部门 项目部级")
+    private String projectDepartment;
+
+    @Schema(description = "成本中心(SAP) 库存地点 小队")
+    private String costCenter;
+
+    @Schema(description = "物料编码")
+    private String materialCode;
+
+    @Schema(description = "物料名称", example = "王五")
+    private String materialName;
+
+    @Schema(description = "物料组", example = "王五")
+    private String materialGroupName;
+
+    @Schema(description = "物料组id", example = "27897")
+    private Long materialGroupId;
+
+    @Schema(description = "出库数量")
+    private BigDecimal quantity;
+
+    @Schema(description = "单价", example = "19965")
+    private BigDecimal unitPrice;
+
+    @Schema(description = "单位")
+    private String unit;
+
+    @Schema(description = "使用方向 对应BOM节点", example = "2254")
+    private Long bomNodeId;
+
+    @Schema(description = "使用类型(1维修 2保养 3临时)", example = "1")
+    private Integer type;
+
+    @Schema(description = "出库时间")
+    @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND)
+    private LocalDateTime[] deliveryTime;
+
+    @Schema(description = "出库原因", example = "不香")
+    private String reason;
+
+    @Schema(description = "排序")
+    private Integer sort;
+
+    @Schema(description = "状态 0启用  1停用", example = "1")
+    private Integer status;
+
+    @Schema(description = "备注", example = "你说的对")
+    private String remark;
+
+    @Schema(description = "流程实例id", example = "19361")
+    private String processInstanceId;
+
+    @Schema(description = "审批状态 未提交、审批中、审批通过、审批不通过、已取消", example = "1")
+    private Integer auditStatus;
+
+    @Schema(description = "创建时间")
+    @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND)
+    private LocalDateTime[] createTime;
+
+}

+ 108 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotoutbound/vo/IotOutboundRespVO.java

@@ -0,0 +1,108 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotoutbound.vo;
+
+import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
+import com.alibaba.excel.annotation.ExcelProperty;
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+@Schema(description = "管理后台 - PMS 出库 Response VO")
+@Data
+@ExcelIgnoreUnannotated
+public class IotOutboundRespVO {
+
+    @Schema(description = "主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "15543")
+    @ExcelProperty("主键")
+    private Long id;
+
+    @Schema(description = "入库id", example = "27552")
+    @ExcelProperty("入库id")
+    private Long storageId;
+
+    @Schema(description = "组织部门id", example = "10467")
+    @ExcelProperty("组织部门id")
+    private Long deptId;
+
+    @Schema(description = "工厂(SAP) 专业公司")
+    @ExcelProperty("工厂(SAP) 专业公司")
+    private String factory;
+
+    @Schema(description = "库存地点 - SAP 部门 项目部级")
+    @ExcelProperty("库存地点 - SAP 部门 项目部级")
+    private String projectDepartment;
+
+    @Schema(description = "成本中心(SAP) 库存地点 小队")
+    @ExcelProperty("成本中心(SAP) 库存地点 小队")
+    private String costCenter;
+
+    @Schema(description = "物料编码")
+    @ExcelProperty("物料编码")
+    private String materialCode;
+
+    @Schema(description = "物料名称", example = "王五")
+    @ExcelProperty("物料名称")
+    private String materialName;
+
+    @Schema(description = "物料组", example = "王五")
+    @ExcelProperty("物料组")
+    private String materialGroupName;
+
+    @Schema(description = "物料组id", example = "27897")
+    @ExcelProperty("物料组id")
+    private Long materialGroupId;
+
+    @Schema(description = "出库数量")
+    @ExcelProperty("出库数量")
+    private BigDecimal quantity;
+
+    @Schema(description = "单价", example = "19965")
+    @ExcelProperty("单价")
+    private BigDecimal unitPrice;
+
+    @Schema(description = "单位")
+    @ExcelProperty("单位")
+    private String unit;
+
+    @Schema(description = "使用方向 对应BOM节点", example = "2254")
+    @ExcelProperty("使用方向 对应BOM节点")
+    private Long bomNodeId;
+
+    @Schema(description = "使用类型(1维修 2保养 3临时)", example = "1")
+    @ExcelProperty("使用类型(1维修 2保养 3临时)")
+    private Integer type;
+
+    @Schema(description = "出库时间")
+    @ExcelProperty("出库时间")
+    private LocalDateTime deliveryTime;
+
+    @Schema(description = "出库原因", example = "不香")
+    @ExcelProperty("出库原因")
+    private String reason;
+
+    @Schema(description = "排序")
+    @ExcelProperty("排序")
+    private Integer sort;
+
+    @Schema(description = "状态 0启用  1停用", example = "1")
+    @ExcelProperty("状态 0启用  1停用")
+    private Integer status;
+
+    @Schema(description = "备注", example = "你说的对")
+    @ExcelProperty("备注")
+    private String remark;
+
+    @Schema(description = "流程实例id", example = "19361")
+    @ExcelProperty("流程实例id")
+    private String processInstanceId;
+
+    @Schema(description = "审批状态 未提交、审批中、审批通过、审批不通过、已取消", example = "1")
+    @ExcelProperty("审批状态 未提交、审批中、审批通过、审批不通过、已取消")
+    private Integer auditStatus;
+
+    @Schema(description = "创建时间", requiredMode = Schema.RequiredMode.REQUIRED)
+    @ExcelProperty("创建时间")
+    private LocalDateTime createTime;
+
+}

+ 79 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotoutbound/vo/IotOutboundSaveReqVO.java

@@ -0,0 +1,79 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotoutbound.vo;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+@Schema(description = "管理后台 - PMS 出库新增/修改 Request VO")
+@Data
+public class IotOutboundSaveReqVO {
+
+    @Schema(description = "主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "15543")
+    private Long id;
+
+    @Schema(description = "入库id", example = "27552")
+    private Long storageId;
+
+    @Schema(description = "组织部门id", example = "10467")
+    private Long deptId;
+
+    @Schema(description = "工厂(SAP) 专业公司")
+    private String factory;
+
+    @Schema(description = "库存地点 - SAP 部门 项目部级")
+    private String projectDepartment;
+
+    @Schema(description = "成本中心(SAP) 库存地点 小队")
+    private String costCenter;
+
+    @Schema(description = "物料编码")
+    private String materialCode;
+
+    @Schema(description = "物料名称", example = "王五")
+    private String materialName;
+
+    @Schema(description = "物料组", example = "王五")
+    private String materialGroupName;
+
+    @Schema(description = "物料组id", example = "27897")
+    private Long materialGroupId;
+
+    @Schema(description = "出库数量")
+    private BigDecimal quantity;
+
+    @Schema(description = "单价", example = "19965")
+    private BigDecimal unitPrice;
+
+    @Schema(description = "单位")
+    private String unit;
+
+    @Schema(description = "使用方向 对应BOM节点", example = "2254")
+    private Long bomNodeId;
+
+    @Schema(description = "使用类型(1维修 2保养 3临时)", example = "1")
+    private Integer type;
+
+    @Schema(description = "出库时间")
+    private LocalDateTime deliveryTime;
+
+    @Schema(description = "出库原因", example = "不香")
+    private String reason;
+
+    @Schema(description = "排序")
+    private Integer sort;
+
+    @Schema(description = "状态 0启用  1停用", example = "1")
+    private Integer status;
+
+    @Schema(description = "备注", example = "你说的对")
+    private String remark;
+
+    @Schema(description = "流程实例id", example = "19361")
+    private String processInstanceId;
+
+    @Schema(description = "审批状态 未提交、审批中、审批通过、审批不通过、已取消", example = "1")
+    private Integer auditStatus;
+
+}

+ 93 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotsapstock/IotSapStockController.java

@@ -0,0 +1,93 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotsapstock;
+
+import cn.iocoder.yudao.framework.apilog.core.annotation.ApiAccessLog;
+import cn.iocoder.yudao.framework.common.pojo.CommonResult;
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
+import cn.iocoder.yudao.framework.excel.core.util.ExcelUtils;
+import cn.iocoder.yudao.module.pms.controller.admin.iotsapstock.vo.IotSapStockPageReqVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotsapstock.vo.IotSapStockRespVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotsapstock.vo.IotSapStockSaveReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotsapstock.IotSapStockDO;
+import cn.iocoder.yudao.module.pms.service.iotsapstock.IotSapStockService;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.Parameter;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import javax.servlet.http.HttpServletResponse;
+import javax.validation.Valid;
+import java.io.IOException;
+import java.util.List;
+
+import static cn.iocoder.yudao.framework.apilog.core.enums.OperateTypeEnum.EXPORT;
+import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
+
+@Tag(name = "管理后台 - PMS SAP 库存(通用库存/项目部库存)")
+@RestController
+@RequestMapping("/pms/iot-sap-stock")
+@Validated
+public class IotSapStockController {
+
+    @Resource
+    private IotSapStockService iotSapStockService;
+
+    @PostMapping("/create")
+    @Operation(summary = "创建PMS SAP 库存(通用库存/项目部库存)")
+    @PreAuthorize("@ss.hasPermission('pms:iot-sap-stock:create')")
+    public CommonResult<Long> createIotSapStock(@Valid @RequestBody IotSapStockSaveReqVO createReqVO) {
+        return success(iotSapStockService.createIotSapStock(createReqVO));
+    }
+
+    @PutMapping("/update")
+    @Operation(summary = "更新PMS SAP 库存(通用库存/项目部库存)")
+    @PreAuthorize("@ss.hasPermission('pms:iot-sap-stock:update')")
+    public CommonResult<Boolean> updateIotSapStock(@Valid @RequestBody IotSapStockSaveReqVO updateReqVO) {
+        iotSapStockService.updateIotSapStock(updateReqVO);
+        return success(true);
+    }
+
+    @DeleteMapping("/delete")
+    @Operation(summary = "删除PMS SAP 库存(通用库存/项目部库存)")
+    @Parameter(name = "id", description = "编号", required = true)
+    @PreAuthorize("@ss.hasPermission('pms:iot-sap-stock:delete')")
+    public CommonResult<Boolean> deleteIotSapStock(@RequestParam("id") Long id) {
+        iotSapStockService.deleteIotSapStock(id);
+        return success(true);
+    }
+
+    @GetMapping("/get")
+    @Operation(summary = "获得PMS SAP 库存(通用库存/项目部库存)")
+    @Parameter(name = "id", description = "编号", required = true, example = "1024")
+    @PreAuthorize("@ss.hasPermission('pms:iot-sap-stock:query')")
+    public CommonResult<IotSapStockRespVO> getIotSapStock(@RequestParam("id") Long id) {
+        IotSapStockDO iotSapStock = iotSapStockService.getIotSapStock(id);
+        return success(BeanUtils.toBean(iotSapStock, IotSapStockRespVO.class));
+    }
+
+    @GetMapping("/page")
+    @Operation(summary = "获得PMS SAP 库存(通用库存/项目部库存)分页")
+    @PreAuthorize("@ss.hasPermission('pms:iot-sap-stock:query')")
+    public CommonResult<PageResult<IotSapStockRespVO>> getIotSapStockPage(@Valid IotSapStockPageReqVO pageReqVO) {
+        PageResult<IotSapStockDO> pageResult = iotSapStockService.getIotSapStockPage(pageReqVO);
+        return success(BeanUtils.toBean(pageResult, IotSapStockRespVO.class));
+    }
+
+    @GetMapping("/export-excel")
+    @Operation(summary = "导出PMS SAP 库存(通用库存/项目部库存) Excel")
+    @PreAuthorize("@ss.hasPermission('pms:iot-sap-stock:export')")
+    @ApiAccessLog(operateType = EXPORT)
+    public void exportIotSapStockExcel(@Valid IotSapStockPageReqVO pageReqVO,
+              HttpServletResponse response) throws IOException {
+        pageReqVO.setPageSize(PageParam.PAGE_SIZE_NONE);
+        List<IotSapStockDO> list = iotSapStockService.getIotSapStockPage(pageReqVO).getList();
+        // 导出 Excel
+        ExcelUtils.write(response, "PMS SAP 库存(通用库存/项目部库存).xls", "数据", IotSapStockRespVO.class,
+                        BeanUtils.toBean(list, IotSapStockRespVO.class));
+    }
+
+}

+ 86 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotsapstock/vo/IotSapStockPageReqVO.java

@@ -0,0 +1,86 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotsapstock.vo;
+
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.ToString;
+import org.springframework.format.annotation.DateTimeFormat;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND;
+
+@Schema(description = "管理后台 - PMS SAP 库存(通用库存/项目部库存)分页 Request VO")
+@Data
+@EqualsAndHashCode(callSuper = true)
+@ToString(callSuper = true)
+public class IotSapStockPageReqVO extends PageParam {
+
+    @Schema(description = "组织部门id", example = "10123")
+    private Long deptId;
+
+    @Schema(description = "工厂(SAP) 专业公司")
+    private String factory;
+
+    @Schema(description = "库存地点 - SAP 部门 项目部级 通用库 项目部库")
+    private String projectDepartment;
+
+    @Schema(description = "物料编码")
+    private String materialCode;
+
+    @Schema(description = "物料名称", example = "张三")
+    private String materialName;
+
+    @Schema(description = "物料组", example = "芋艿")
+    private String materialGroupName;
+
+    @Schema(description = "物料组id", example = "14906")
+    private Long materialGroupId;
+
+    @Schema(description = "数量")
+    private BigDecimal quantity;
+
+    @Schema(description = "单价", example = "14017")
+    private BigDecimal unitPrice;
+
+    @Schema(description = "单位")
+    private String unit;
+
+    @Schema(description = "安全库存")
+    private BigDecimal safetyStock;
+
+    @Schema(description = "货架id", example = "24365")
+    private Long shelvesId;
+
+    @Schema(description = "库位id", example = "16905")
+    private Long cargoLocationId;
+
+    @Schema(description = "类型(通用库 项目部库)", example = "1")
+    private Integer type;
+
+    @Schema(description = "同步状态 0未同步 1同步成功 2同步失败", example = "2")
+    private Integer syncStatus;
+
+    @Schema(description = "最后一次同步时间")
+    @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND)
+    private LocalDateTime[] syncTime;
+
+    @Schema(description = "同步失败时的错误信息")
+    private String syncError;
+
+    @Schema(description = "排序")
+    private Integer sort;
+
+    @Schema(description = "状态 0启用  1停用", example = "2")
+    private Integer status;
+
+    @Schema(description = "备注", example = "你说的对")
+    private String remark;
+
+    @Schema(description = "创建时间")
+    @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND)
+    private LocalDateTime[] createTime;
+
+}

+ 104 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotsapstock/vo/IotSapStockRespVO.java

@@ -0,0 +1,104 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotsapstock.vo;
+
+import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
+import com.alibaba.excel.annotation.ExcelProperty;
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+@Schema(description = "管理后台 - PMS SAP 库存(通用库存/项目部库存) Response VO")
+@Data
+@ExcelIgnoreUnannotated
+public class IotSapStockRespVO {
+
+    @Schema(description = "主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "12946")
+    @ExcelProperty("主键")
+    private Long id;
+
+    @Schema(description = "组织部门id", example = "10123")
+    @ExcelProperty("组织部门id")
+    private Long deptId;
+
+    @Schema(description = "工厂(SAP) 专业公司")
+    @ExcelProperty("工厂(SAP) 专业公司")
+    private String factory;
+
+    @Schema(description = "库存地点 - SAP 部门 项目部级 通用库 项目部库")
+    @ExcelProperty("库存地点 - SAP 部门 项目部级 通用库 项目部库")
+    private String projectDepartment;
+
+    @Schema(description = "物料编码")
+    @ExcelProperty("物料编码")
+    private String materialCode;
+
+    @Schema(description = "物料名称", example = "张三")
+    @ExcelProperty("物料名称")
+    private String materialName;
+
+    @Schema(description = "物料组", example = "芋艿")
+    @ExcelProperty("物料组")
+    private String materialGroupName;
+
+    @Schema(description = "物料组id", example = "14906")
+    @ExcelProperty("物料组id")
+    private Long materialGroupId;
+
+    @Schema(description = "数量")
+    @ExcelProperty("数量")
+    private BigDecimal quantity;
+
+    @Schema(description = "单价", example = "14017")
+    @ExcelProperty("单价")
+    private BigDecimal unitPrice;
+
+    @Schema(description = "单位")
+    @ExcelProperty("单位")
+    private String unit;
+
+    @Schema(description = "安全库存")
+    @ExcelProperty("安全库存")
+    private BigDecimal safetyStock;
+
+    @Schema(description = "货架id", example = "24365")
+    @ExcelProperty("货架id")
+    private Long shelvesId;
+
+    @Schema(description = "库位id", example = "16905")
+    @ExcelProperty("库位id")
+    private Long cargoLocationId;
+
+    @Schema(description = "类型(通用库 项目部库)", example = "1")
+    @ExcelProperty("类型(通用库 项目部库)")
+    private Integer type;
+
+    @Schema(description = "同步状态 0未同步 1同步成功 2同步失败", example = "2")
+    @ExcelProperty("同步状态 0未同步 1同步成功 2同步失败")
+    private Integer syncStatus;
+
+    @Schema(description = "最后一次同步时间")
+    @ExcelProperty("最后一次同步时间")
+    private LocalDateTime syncTime;
+
+    @Schema(description = "同步失败时的错误信息")
+    @ExcelProperty("同步失败时的错误信息")
+    private String syncError;
+
+    @Schema(description = "排序")
+    @ExcelProperty("排序")
+    private Integer sort;
+
+    @Schema(description = "状态 0启用  1停用", example = "2")
+    @ExcelProperty("状态 0启用  1停用")
+    private Integer status;
+
+    @Schema(description = "备注", example = "你说的对")
+    @ExcelProperty("备注")
+    private String remark;
+
+    @Schema(description = "创建时间", requiredMode = Schema.RequiredMode.REQUIRED)
+    @ExcelProperty("创建时间")
+    private LocalDateTime createTime;
+
+}

+ 76 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotsapstock/vo/IotSapStockSaveReqVO.java

@@ -0,0 +1,76 @@
+package cn.iocoder.yudao.module.pms.controller.admin.iotsapstock.vo;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+@Schema(description = "管理后台 - PMS SAP 库存(通用库存/项目部库存)新增/修改 Request VO")
+@Data
+public class IotSapStockSaveReqVO {
+
+    @Schema(description = "主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "12946")
+    private Long id;
+
+    @Schema(description = "组织部门id", example = "10123")
+    private Long deptId;
+
+    @Schema(description = "工厂(SAP) 专业公司")
+    private String factory;
+
+    @Schema(description = "库存地点 - SAP 部门 项目部级 通用库 项目部库")
+    private String projectDepartment;
+
+    @Schema(description = "物料编码")
+    private String materialCode;
+
+    @Schema(description = "物料名称", example = "张三")
+    private String materialName;
+
+    @Schema(description = "物料组", example = "芋艿")
+    private String materialGroupName;
+
+    @Schema(description = "物料组id", example = "14906")
+    private Long materialGroupId;
+
+    @Schema(description = "数量")
+    private BigDecimal quantity;
+
+    @Schema(description = "单价", example = "14017")
+    private BigDecimal unitPrice;
+
+    @Schema(description = "单位")
+    private String unit;
+
+    @Schema(description = "安全库存")
+    private BigDecimal safetyStock;
+
+    @Schema(description = "货架id", example = "24365")
+    private Long shelvesId;
+
+    @Schema(description = "库位id", example = "16905")
+    private Long cargoLocationId;
+
+    @Schema(description = "类型(通用库 项目部库)", example = "1")
+    private Integer type;
+
+    @Schema(description = "同步状态 0未同步 1同步成功 2同步失败", example = "2")
+    private Integer syncStatus;
+
+    @Schema(description = "最后一次同步时间")
+    private LocalDateTime syncTime;
+
+    @Schema(description = "同步失败时的错误信息")
+    private String syncError;
+
+    @Schema(description = "排序")
+    private Integer sort;
+
+    @Schema(description = "状态 0启用  1停用", example = "2")
+    private Integer status;
+
+    @Schema(description = "备注", example = "你说的对")
+    private String remark;
+
+}

+ 105 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/dataobject/iotlockstock/IotLockStockDO.java

@@ -0,0 +1,105 @@
+package cn.iocoder.yudao.module.pms.dal.dataobject.iotlockstock;
+
+import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
+import com.baomidou.mybatisplus.annotation.KeySequence;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.*;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+/**
+ * PMS 本地 库存 DO
+ *
+ * @author ruiqi
+ */
+@TableName("rq_iot_lock_stock")
+@KeySequence("rq_iot_lock_stock_seq") // 用于 Oracle、PostgreSQL、Kingbase、DB2、H2 数据库的主键自增。如果是 MySQL 等数据库,可不写。
+@Data
+@EqualsAndHashCode(callSuper = true)
+@ToString(callSuper = true)
+@Builder
+@NoArgsConstructor
+@AllArgsConstructor
+public class IotLockStockDO extends BaseDO {
+
+    /**
+     * 主键
+     */
+    @TableId
+    private Long id;
+    /**
+     * 组织部门id
+     */
+    private Long deptId;
+    /**
+     * 工厂(SAP) 专业公司
+     */
+    private String factory;
+    /**
+     * 库存地点 - SAP 部门 项目部级
+     */
+    private String projectDepartment;
+    /**
+     * 成本中心(SAP) 库存地点 小队
+     */
+    private String costCenter;
+    /**
+     * 领料单号
+     */
+    private String pickingListNumber;
+    /**
+     * 物料编码
+     */
+    private String materialCode;
+    /**
+     * 物料名称
+     */
+    private String materialName;
+    /**
+     * 物料组
+     */
+    private String materialGroupName;
+    /**
+     * 物料组id
+     */
+    private Long materialGroupId;
+    /**
+     * 数量
+     */
+    private BigDecimal quantity;
+    /**
+     * 单价
+     */
+    private BigDecimal unitPrice;
+    /**
+     * 单位
+     */
+    private String unit;
+    /**
+     * 入库时间
+     */
+    private LocalDateTime storageTime;
+    /**
+     * 排序
+     */
+    private Integer sort;
+    /**
+     * 状态 0启用  1停用
+     */
+    private Integer status;
+    /**
+     * 流程实例id
+     */
+    private String processInstanceId;
+    /**
+     * 审批状态 未提交、审批中、审批通过、审批不通过、已取消
+     */
+    private Integer auditStatus;
+    /**
+     * 备注
+     */
+    private String remark;
+
+}

+ 117 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/dataobject/iotoutbound/IotOutboundDO.java

@@ -0,0 +1,117 @@
+package cn.iocoder.yudao.module.pms.dal.dataobject.iotoutbound;
+
+import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
+import com.baomidou.mybatisplus.annotation.KeySequence;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.*;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+/**
+ * PMS 出库 DO
+ *
+ * @author ruiqi
+ */
+@TableName("rq_iot_outbound")
+@KeySequence("rq_iot_outbound_seq") // 用于 Oracle、PostgreSQL、Kingbase、DB2、H2 数据库的主键自增。如果是 MySQL 等数据库,可不写。
+@Data
+@EqualsAndHashCode(callSuper = true)
+@ToString(callSuper = true)
+@Builder
+@NoArgsConstructor
+@AllArgsConstructor
+public class IotOutboundDO extends BaseDO {
+
+    /**
+     * 主键
+     */
+    @TableId
+    private Long id;
+    /**
+     * 入库id
+     */
+    private Long storageId;
+    /**
+     * 组织部门id
+     */
+    private Long deptId;
+    /**
+     * 工厂(SAP) 专业公司
+     */
+    private String factory;
+    /**
+     * 库存地点 - SAP 部门 项目部级
+     */
+    private String projectDepartment;
+    /**
+     * 成本中心(SAP) 库存地点 小队
+     */
+    private String costCenter;
+    /**
+     * 物料编码
+     */
+    private String materialCode;
+    /**
+     * 物料名称
+     */
+    private String materialName;
+    /**
+     * 物料组
+     */
+    private String materialGroupName;
+    /**
+     * 物料组id
+     */
+    private Long materialGroupId;
+    /**
+     * 出库数量
+     */
+    private BigDecimal quantity;
+    /**
+     * 单价
+     */
+    private BigDecimal unitPrice;
+    /**
+     * 单位
+     */
+    private String unit;
+    /**
+     * 使用方向 对应BOM节点
+     */
+    private Long bomNodeId;
+    /**
+     * 使用类型(1维修 2保养 3临时)
+     */
+    private Integer type;
+    /**
+     * 出库时间
+     */
+    private LocalDateTime deliveryTime;
+    /**
+     * 出库原因
+     */
+    private String reason;
+    /**
+     * 排序
+     */
+    private Integer sort;
+    /**
+     * 状态 0启用  1停用
+     */
+    private Integer status;
+    /**
+     * 备注
+     */
+    private String remark;
+    /**
+     * 流程实例id
+     */
+    private String processInstanceId;
+    /**
+     * 审批状态 未提交、审批中、审批通过、审批不通过、已取消
+     */
+    private Integer auditStatus;
+
+}

+ 113 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/dataobject/iotsapstock/IotSapStockDO.java

@@ -0,0 +1,113 @@
+package cn.iocoder.yudao.module.pms.dal.dataobject.iotsapstock;
+
+import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
+import com.baomidou.mybatisplus.annotation.KeySequence;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.*;
+
+import java.math.BigDecimal;
+import java.time.LocalDateTime;
+
+/**
+ * PMS SAP 库存(通用库存/项目部库存) DO
+ *
+ * @author ruiqi
+ */
+@TableName("rq_iot_sap_stock")
+@KeySequence("rq_iot_sap_stock_seq") // 用于 Oracle、PostgreSQL、Kingbase、DB2、H2 数据库的主键自增。如果是 MySQL 等数据库,可不写。
+@Data
+@EqualsAndHashCode(callSuper = true)
+@ToString(callSuper = true)
+@Builder
+@NoArgsConstructor
+@AllArgsConstructor
+public class IotSapStockDO extends BaseDO {
+
+    /**
+     * 主键
+     */
+    @TableId
+    private Long id;
+    /**
+     * 组织部门id
+     */
+    private Long deptId;
+    /**
+     * 工厂(SAP) 专业公司
+     */
+    private String factory;
+    /**
+     * 库存地点 - SAP 部门 项目部级 通用库 项目部库
+     */
+    private String projectDepartment;
+    /**
+     * 物料编码
+     */
+    private String materialCode;
+    /**
+     * 物料名称
+     */
+    private String materialName;
+    /**
+     * 物料组
+     */
+    private String materialGroupName;
+    /**
+     * 物料组id
+     */
+    private Long materialGroupId;
+    /**
+     * 数量
+     */
+    private BigDecimal quantity;
+    /**
+     * 单价
+     */
+    private BigDecimal unitPrice;
+    /**
+     * 单位
+     */
+    private String unit;
+    /**
+     * 安全库存
+     */
+    private BigDecimal safetyStock;
+    /**
+     * 货架id
+     */
+    private Long shelvesId;
+    /**
+     * 库位id
+     */
+    private Long cargoLocationId;
+    /**
+     * 类型(通用库 项目部库)
+     */
+    private Integer type;
+    /**
+     * 同步状态 0未同步 1同步成功 2同步失败
+     */
+    private Integer syncStatus;
+    /**
+     * 最后一次同步时间
+     */
+    private LocalDateTime syncTime;
+    /**
+     * 同步失败时的错误信息
+     */
+    private String syncError;
+    /**
+     * 排序
+     */
+    private Integer sort;
+    /**
+     * 状态 0启用  1停用
+     */
+    private Integer status;
+    /**
+     * 备注
+     */
+    private String remark;
+
+}

+ 42 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/mysql/iotlockstock/IotLockStockMapper.java

@@ -0,0 +1,42 @@
+package cn.iocoder.yudao.module.pms.dal.mysql.iotlockstock;
+
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.framework.mybatis.core.mapper.BaseMapperX;
+import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX;
+import cn.iocoder.yudao.module.pms.controller.admin.iotlockstock.vo.IotLockStockPageReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotlockstock.IotLockStockDO;
+import org.apache.ibatis.annotations.Mapper;
+
+/**
+ * PMS 本地 库存 Mapper
+ *
+ * @author ruiqi
+ */
+@Mapper
+public interface IotLockStockMapper extends BaseMapperX<IotLockStockDO> {
+
+    default PageResult<IotLockStockDO> selectPage(IotLockStockPageReqVO reqVO) {
+        return selectPage(reqVO, new LambdaQueryWrapperX<IotLockStockDO>()
+                .eqIfPresent(IotLockStockDO::getDeptId, reqVO.getDeptId())
+                .eqIfPresent(IotLockStockDO::getFactory, reqVO.getFactory())
+                .eqIfPresent(IotLockStockDO::getProjectDepartment, reqVO.getProjectDepartment())
+                .eqIfPresent(IotLockStockDO::getCostCenter, reqVO.getCostCenter())
+                .eqIfPresent(IotLockStockDO::getPickingListNumber, reqVO.getPickingListNumber())
+                .eqIfPresent(IotLockStockDO::getMaterialCode, reqVO.getMaterialCode())
+                .likeIfPresent(IotLockStockDO::getMaterialName, reqVO.getMaterialName())
+                .likeIfPresent(IotLockStockDO::getMaterialGroupName, reqVO.getMaterialGroupName())
+                .eqIfPresent(IotLockStockDO::getMaterialGroupId, reqVO.getMaterialGroupId())
+                .eqIfPresent(IotLockStockDO::getQuantity, reqVO.getQuantity())
+                .eqIfPresent(IotLockStockDO::getUnitPrice, reqVO.getUnitPrice())
+                .eqIfPresent(IotLockStockDO::getUnit, reqVO.getUnit())
+                .betweenIfPresent(IotLockStockDO::getStorageTime, reqVO.getStorageTime())
+                .eqIfPresent(IotLockStockDO::getSort, reqVO.getSort())
+                .eqIfPresent(IotLockStockDO::getStatus, reqVO.getStatus())
+                .eqIfPresent(IotLockStockDO::getProcessInstanceId, reqVO.getProcessInstanceId())
+                .eqIfPresent(IotLockStockDO::getAuditStatus, reqVO.getAuditStatus())
+                .eqIfPresent(IotLockStockDO::getRemark, reqVO.getRemark())
+                .betweenIfPresent(IotLockStockDO::getCreateTime, reqVO.getCreateTime())
+                .orderByDesc(IotLockStockDO::getId));
+    }
+
+}

+ 45 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/mysql/iotoutbound/IotOutboundMapper.java

@@ -0,0 +1,45 @@
+package cn.iocoder.yudao.module.pms.dal.mysql.iotoutbound;
+
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.framework.mybatis.core.mapper.BaseMapperX;
+import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX;
+import cn.iocoder.yudao.module.pms.controller.admin.iotoutbound.vo.IotOutboundPageReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotoutbound.IotOutboundDO;
+import org.apache.ibatis.annotations.Mapper;
+
+/**
+ * PMS 出库 Mapper
+ *
+ * @author ruiqi
+ */
+@Mapper
+public interface IotOutboundMapper extends BaseMapperX<IotOutboundDO> {
+
+    default PageResult<IotOutboundDO> selectPage(IotOutboundPageReqVO reqVO) {
+        return selectPage(reqVO, new LambdaQueryWrapperX<IotOutboundDO>()
+                .eqIfPresent(IotOutboundDO::getStorageId, reqVO.getStorageId())
+                .eqIfPresent(IotOutboundDO::getDeptId, reqVO.getDeptId())
+                .eqIfPresent(IotOutboundDO::getFactory, reqVO.getFactory())
+                .eqIfPresent(IotOutboundDO::getProjectDepartment, reqVO.getProjectDepartment())
+                .eqIfPresent(IotOutboundDO::getCostCenter, reqVO.getCostCenter())
+                .eqIfPresent(IotOutboundDO::getMaterialCode, reqVO.getMaterialCode())
+                .likeIfPresent(IotOutboundDO::getMaterialName, reqVO.getMaterialName())
+                .likeIfPresent(IotOutboundDO::getMaterialGroupName, reqVO.getMaterialGroupName())
+                .eqIfPresent(IotOutboundDO::getMaterialGroupId, reqVO.getMaterialGroupId())
+                .eqIfPresent(IotOutboundDO::getQuantity, reqVO.getQuantity())
+                .eqIfPresent(IotOutboundDO::getUnitPrice, reqVO.getUnitPrice())
+                .eqIfPresent(IotOutboundDO::getUnit, reqVO.getUnit())
+                .eqIfPresent(IotOutboundDO::getBomNodeId, reqVO.getBomNodeId())
+                .eqIfPresent(IotOutboundDO::getType, reqVO.getType())
+                .betweenIfPresent(IotOutboundDO::getDeliveryTime, reqVO.getDeliveryTime())
+                .eqIfPresent(IotOutboundDO::getReason, reqVO.getReason())
+                .eqIfPresent(IotOutboundDO::getSort, reqVO.getSort())
+                .eqIfPresent(IotOutboundDO::getStatus, reqVO.getStatus())
+                .eqIfPresent(IotOutboundDO::getRemark, reqVO.getRemark())
+                .eqIfPresent(IotOutboundDO::getProcessInstanceId, reqVO.getProcessInstanceId())
+                .eqIfPresent(IotOutboundDO::getAuditStatus, reqVO.getAuditStatus())
+                .betweenIfPresent(IotOutboundDO::getCreateTime, reqVO.getCreateTime())
+                .orderByDesc(IotOutboundDO::getId));
+    }
+
+}

+ 44 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/mysql/iotsapstock/IotSapStockMapper.java

@@ -0,0 +1,44 @@
+package cn.iocoder.yudao.module.pms.dal.mysql.iotsapstock;
+
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.framework.mybatis.core.mapper.BaseMapperX;
+import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX;
+import cn.iocoder.yudao.module.pms.controller.admin.iotsapstock.vo.IotSapStockPageReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotsapstock.IotSapStockDO;
+import org.apache.ibatis.annotations.Mapper;
+
+/**
+ * PMS SAP 库存(通用库存/项目部库存) Mapper
+ *
+ * @author ruiqi
+ */
+@Mapper
+public interface IotSapStockMapper extends BaseMapperX<IotSapStockDO> {
+
+    default PageResult<IotSapStockDO> selectPage(IotSapStockPageReqVO reqVO) {
+        return selectPage(reqVO, new LambdaQueryWrapperX<IotSapStockDO>()
+                .eqIfPresent(IotSapStockDO::getDeptId, reqVO.getDeptId())
+                .eqIfPresent(IotSapStockDO::getFactory, reqVO.getFactory())
+                .eqIfPresent(IotSapStockDO::getProjectDepartment, reqVO.getProjectDepartment())
+                .eqIfPresent(IotSapStockDO::getMaterialCode, reqVO.getMaterialCode())
+                .likeIfPresent(IotSapStockDO::getMaterialName, reqVO.getMaterialName())
+                .likeIfPresent(IotSapStockDO::getMaterialGroupName, reqVO.getMaterialGroupName())
+                .eqIfPresent(IotSapStockDO::getMaterialGroupId, reqVO.getMaterialGroupId())
+                .eqIfPresent(IotSapStockDO::getQuantity, reqVO.getQuantity())
+                .eqIfPresent(IotSapStockDO::getUnitPrice, reqVO.getUnitPrice())
+                .eqIfPresent(IotSapStockDO::getUnit, reqVO.getUnit())
+                .eqIfPresent(IotSapStockDO::getSafetyStock, reqVO.getSafetyStock())
+                .eqIfPresent(IotSapStockDO::getShelvesId, reqVO.getShelvesId())
+                .eqIfPresent(IotSapStockDO::getCargoLocationId, reqVO.getCargoLocationId())
+                .eqIfPresent(IotSapStockDO::getType, reqVO.getType())
+                .eqIfPresent(IotSapStockDO::getSyncStatus, reqVO.getSyncStatus())
+                .betweenIfPresent(IotSapStockDO::getSyncTime, reqVO.getSyncTime())
+                .eqIfPresent(IotSapStockDO::getSyncError, reqVO.getSyncError())
+                .eqIfPresent(IotSapStockDO::getSort, reqVO.getSort())
+                .eqIfPresent(IotSapStockDO::getStatus, reqVO.getStatus())
+                .eqIfPresent(IotSapStockDO::getRemark, reqVO.getRemark())
+                .betweenIfPresent(IotSapStockDO::getCreateTime, reqVO.getCreateTime())
+                .orderByDesc(IotSapStockDO::getId));
+    }
+
+}

+ 55 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotlockstock/IotLockStockService.java

@@ -0,0 +1,55 @@
+package cn.iocoder.yudao.module.pms.service.iotlockstock;
+
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.module.pms.controller.admin.iotlockstock.vo.IotLockStockPageReqVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotlockstock.vo.IotLockStockSaveReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotlockstock.IotLockStockDO;
+
+import javax.validation.Valid;
+
+/**
+ * PMS 本地 库存 Service 接口
+ *
+ * @author ruiqi
+ */
+public interface IotLockStockService {
+
+    /**
+     * 创建PMS 本地 库存
+     *
+     * @param createReqVO 创建信息
+     * @return 编号
+     */
+    Long createIotLockStock(@Valid IotLockStockSaveReqVO createReqVO);
+
+    /**
+     * 更新PMS 本地 库存
+     *
+     * @param updateReqVO 更新信息
+     */
+    void updateIotLockStock(@Valid IotLockStockSaveReqVO updateReqVO);
+
+    /**
+     * 删除PMS 本地 库存
+     *
+     * @param id 编号
+     */
+    void deleteIotLockStock(Long id);
+
+    /**
+     * 获得PMS 本地 库存
+     *
+     * @param id 编号
+     * @return PMS 本地 库存
+     */
+    IotLockStockDO getIotLockStock(Long id);
+
+    /**
+     * 获得PMS 本地 库存分页
+     *
+     * @param pageReqVO 分页查询
+     * @return PMS 本地 库存分页
+     */
+    PageResult<IotLockStockDO> getIotLockStockPage(IotLockStockPageReqVO pageReqVO);
+
+}

+ 71 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotlockstock/IotLockStockServiceImpl.java

@@ -0,0 +1,71 @@
+package cn.iocoder.yudao.module.pms.service.iotlockstock;
+
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
+import cn.iocoder.yudao.module.pms.controller.admin.iotlockstock.vo.IotLockStockPageReqVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotlockstock.vo.IotLockStockSaveReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotlockstock.IotLockStockDO;
+import cn.iocoder.yudao.module.pms.dal.mysql.iotlockstock.IotLockStockMapper;
+import org.springframework.stereotype.Service;
+import org.springframework.validation.annotation.Validated;
+
+import javax.annotation.Resource;
+
+import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
+import static cn.iocoder.yudao.module.pms.enums.ErrorCodeConstant.IOT_LOCK_STOCK_NOT_EXISTS;
+
+/**
+ * PMS 本地 库存 Service 实现类
+ *
+ * @author ruiqi
+ */
+@Service
+@Validated
+public class IotLockStockServiceImpl implements IotLockStockService {
+
+    @Resource
+    private IotLockStockMapper iotLockStockMapper;
+
+    @Override
+    public Long createIotLockStock(IotLockStockSaveReqVO createReqVO) {
+        // 插入
+        IotLockStockDO iotLockStock = BeanUtils.toBean(createReqVO, IotLockStockDO.class);
+        iotLockStockMapper.insert(iotLockStock);
+        // 返回
+        return iotLockStock.getId();
+    }
+
+    @Override
+    public void updateIotLockStock(IotLockStockSaveReqVO updateReqVO) {
+        // 校验存在
+        validateIotLockStockExists(updateReqVO.getId());
+        // 更新
+        IotLockStockDO updateObj = BeanUtils.toBean(updateReqVO, IotLockStockDO.class);
+        iotLockStockMapper.updateById(updateObj);
+    }
+
+    @Override
+    public void deleteIotLockStock(Long id) {
+        // 校验存在
+        validateIotLockStockExists(id);
+        // 删除
+        iotLockStockMapper.deleteById(id);
+    }
+
+    private void validateIotLockStockExists(Long id) {
+        if (iotLockStockMapper.selectById(id) == null) {
+            throw exception(IOT_LOCK_STOCK_NOT_EXISTS);
+        }
+    }
+
+    @Override
+    public IotLockStockDO getIotLockStock(Long id) {
+        return iotLockStockMapper.selectById(id);
+    }
+
+    @Override
+    public PageResult<IotLockStockDO> getIotLockStockPage(IotLockStockPageReqVO pageReqVO) {
+        return iotLockStockMapper.selectPage(pageReqVO);
+    }
+
+}

+ 55 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotoutbound/IotOutboundService.java

@@ -0,0 +1,55 @@
+package cn.iocoder.yudao.module.pms.service.iotoutbound;
+
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.module.pms.controller.admin.iotoutbound.vo.IotOutboundPageReqVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotoutbound.vo.IotOutboundSaveReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotoutbound.IotOutboundDO;
+
+import javax.validation.Valid;
+
+/**
+ * PMS 出库 Service 接口
+ *
+ * @author ruiqi
+ */
+public interface IotOutboundService {
+
+    /**
+     * 创建PMS 出库
+     *
+     * @param createReqVO 创建信息
+     * @return 编号
+     */
+    Long createIotOutbound(@Valid IotOutboundSaveReqVO createReqVO);
+
+    /**
+     * 更新PMS 出库
+     *
+     * @param updateReqVO 更新信息
+     */
+    void updateIotOutbound(@Valid IotOutboundSaveReqVO updateReqVO);
+
+    /**
+     * 删除PMS 出库
+     *
+     * @param id 编号
+     */
+    void deleteIotOutbound(Long id);
+
+    /**
+     * 获得PMS 出库
+     *
+     * @param id 编号
+     * @return PMS 出库
+     */
+    IotOutboundDO getIotOutbound(Long id);
+
+    /**
+     * 获得PMS 出库分页
+     *
+     * @param pageReqVO 分页查询
+     * @return PMS 出库分页
+     */
+    PageResult<IotOutboundDO> getIotOutboundPage(IotOutboundPageReqVO pageReqVO);
+
+}

+ 71 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotoutbound/IotOutboundServiceImpl.java

@@ -0,0 +1,71 @@
+package cn.iocoder.yudao.module.pms.service.iotoutbound;
+
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
+import cn.iocoder.yudao.module.pms.controller.admin.iotoutbound.vo.IotOutboundPageReqVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotoutbound.vo.IotOutboundSaveReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotoutbound.IotOutboundDO;
+import cn.iocoder.yudao.module.pms.dal.mysql.iotoutbound.IotOutboundMapper;
+import org.springframework.stereotype.Service;
+import org.springframework.validation.annotation.Validated;
+
+import javax.annotation.Resource;
+
+import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
+import static cn.iocoder.yudao.module.pms.enums.ErrorCodeConstant.IOT_OUTBOUND_NOT_EXISTS;
+
+/**
+ * PMS 出库 Service 实现类
+ *
+ * @author ruiqi
+ */
+@Service
+@Validated
+public class IotOutboundServiceImpl implements IotOutboundService {
+
+    @Resource
+    private IotOutboundMapper iotOutboundMapper;
+
+    @Override
+    public Long createIotOutbound(IotOutboundSaveReqVO createReqVO) {
+        // 插入
+        IotOutboundDO iotOutbound = BeanUtils.toBean(createReqVO, IotOutboundDO.class);
+        iotOutboundMapper.insert(iotOutbound);
+        // 返回
+        return iotOutbound.getId();
+    }
+
+    @Override
+    public void updateIotOutbound(IotOutboundSaveReqVO updateReqVO) {
+        // 校验存在
+        validateIotOutboundExists(updateReqVO.getId());
+        // 更新
+        IotOutboundDO updateObj = BeanUtils.toBean(updateReqVO, IotOutboundDO.class);
+        iotOutboundMapper.updateById(updateObj);
+    }
+
+    @Override
+    public void deleteIotOutbound(Long id) {
+        // 校验存在
+        validateIotOutboundExists(id);
+        // 删除
+        iotOutboundMapper.deleteById(id);
+    }
+
+    private void validateIotOutboundExists(Long id) {
+        if (iotOutboundMapper.selectById(id) == null) {
+            throw exception(IOT_OUTBOUND_NOT_EXISTS);
+        }
+    }
+
+    @Override
+    public IotOutboundDO getIotOutbound(Long id) {
+        return iotOutboundMapper.selectById(id);
+    }
+
+    @Override
+    public PageResult<IotOutboundDO> getIotOutboundPage(IotOutboundPageReqVO pageReqVO) {
+        return iotOutboundMapper.selectPage(pageReqVO);
+    }
+
+}

+ 55 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotsapstock/IotSapStockService.java

@@ -0,0 +1,55 @@
+package cn.iocoder.yudao.module.pms.service.iotsapstock;
+
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.module.pms.controller.admin.iotsapstock.vo.IotSapStockPageReqVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotsapstock.vo.IotSapStockSaveReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotsapstock.IotSapStockDO;
+
+import javax.validation.Valid;
+
+/**
+ * PMS SAP 库存(通用库存/项目部库存) Service 接口
+ *
+ * @author ruiqi
+ */
+public interface IotSapStockService {
+
+    /**
+     * 创建PMS SAP 库存(通用库存/项目部库存)
+     *
+     * @param createReqVO 创建信息
+     * @return 编号
+     */
+    Long createIotSapStock(@Valid IotSapStockSaveReqVO createReqVO);
+
+    /**
+     * 更新PMS SAP 库存(通用库存/项目部库存)
+     *
+     * @param updateReqVO 更新信息
+     */
+    void updateIotSapStock(@Valid IotSapStockSaveReqVO updateReqVO);
+
+    /**
+     * 删除PMS SAP 库存(通用库存/项目部库存)
+     *
+     * @param id 编号
+     */
+    void deleteIotSapStock(Long id);
+
+    /**
+     * 获得PMS SAP 库存(通用库存/项目部库存)
+     *
+     * @param id 编号
+     * @return PMS SAP 库存(通用库存/项目部库存)
+     */
+    IotSapStockDO getIotSapStock(Long id);
+
+    /**
+     * 获得PMS SAP 库存(通用库存/项目部库存)分页
+     *
+     * @param pageReqVO 分页查询
+     * @return PMS SAP 库存(通用库存/项目部库存)分页
+     */
+    PageResult<IotSapStockDO> getIotSapStockPage(IotSapStockPageReqVO pageReqVO);
+
+}

+ 71 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotsapstock/IotSapStockServiceImpl.java

@@ -0,0 +1,71 @@
+package cn.iocoder.yudao.module.pms.service.iotsapstock;
+
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
+import cn.iocoder.yudao.module.pms.controller.admin.iotsapstock.vo.IotSapStockPageReqVO;
+import cn.iocoder.yudao.module.pms.controller.admin.iotsapstock.vo.IotSapStockSaveReqVO;
+import cn.iocoder.yudao.module.pms.dal.dataobject.iotsapstock.IotSapStockDO;
+import cn.iocoder.yudao.module.pms.dal.mysql.iotsapstock.IotSapStockMapper;
+import org.springframework.stereotype.Service;
+import org.springframework.validation.annotation.Validated;
+
+import javax.annotation.Resource;
+
+import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
+import static cn.iocoder.yudao.module.pms.enums.ErrorCodeConstant.IOT_SAP_STOCK_NOT_EXISTS;
+
+/**
+ * PMS SAP 库存(通用库存/项目部库存) Service 实现类
+ *
+ * @author ruiqi
+ */
+@Service
+@Validated
+public class IotSapStockServiceImpl implements IotSapStockService {
+
+    @Resource
+    private IotSapStockMapper iotSapStockMapper;
+
+    @Override
+    public Long createIotSapStock(IotSapStockSaveReqVO createReqVO) {
+        // 插入
+        IotSapStockDO iotSapStock = BeanUtils.toBean(createReqVO, IotSapStockDO.class);
+        iotSapStockMapper.insert(iotSapStock);
+        // 返回
+        return iotSapStock.getId();
+    }
+
+    @Override
+    public void updateIotSapStock(IotSapStockSaveReqVO updateReqVO) {
+        // 校验存在
+        validateIotSapStockExists(updateReqVO.getId());
+        // 更新
+        IotSapStockDO updateObj = BeanUtils.toBean(updateReqVO, IotSapStockDO.class);
+        iotSapStockMapper.updateById(updateObj);
+    }
+
+    @Override
+    public void deleteIotSapStock(Long id) {
+        // 校验存在
+        validateIotSapStockExists(id);
+        // 删除
+        iotSapStockMapper.deleteById(id);
+    }
+
+    private void validateIotSapStockExists(Long id) {
+        if (iotSapStockMapper.selectById(id) == null) {
+            throw exception(IOT_SAP_STOCK_NOT_EXISTS);
+        }
+    }
+
+    @Override
+    public IotSapStockDO getIotSapStock(Long id) {
+        return iotSapStockMapper.selectById(id);
+    }
+
+    @Override
+    public PageResult<IotSapStockDO> getIotSapStockPage(IotSapStockPageReqVO pageReqVO) {
+        return iotSapStockMapper.selectPage(pageReqVO);
+    }
+
+}

+ 14 - 0
yudao-module-system/yudao-module-system-biz/src/main/java/cn/iocoder/yudao/module/system/dal/dataobject/dept/DeptDO.java

@@ -4,11 +4,15 @@ import cn.iocoder.yudao.framework.common.enums.CommonStatusEnum;
 import cn.iocoder.yudao.framework.tenant.core.db.TenantBaseDO;
 import cn.iocoder.yudao.module.system.dal.dataobject.user.AdminUserDO;
 import com.baomidou.mybatisplus.annotation.KeySequence;
+import com.baomidou.mybatisplus.annotation.TableField;
 import com.baomidou.mybatisplus.annotation.TableId;
 import com.baomidou.mybatisplus.annotation.TableName;
+import com.baomidou.mybatisplus.extension.handlers.JacksonTypeHandler;
 import lombok.Data;
 import lombok.EqualsAndHashCode;
 
+import java.util.Set;
+
 /**
  * 部门表
  *
@@ -56,6 +60,16 @@ public class DeptDO extends TenantBaseDO {
      * 邮箱
      */
     private String email;
+    /**
+     * 工厂(SAP)编号数组
+     */
+    @TableField(typeHandler = JacksonTypeHandler.class)
+    private Set<Long> factoryIds;
+    /**
+     * 成本中心(SAP)编号数组
+     */
+    @TableField(typeHandler = JacksonTypeHandler.class)
+    private Set<Long> costCenterIds;
     /**
      * 部门状态
      *