diff --git a/cf-framework/cf-spring-boot-starter-web/src/main/java/com/cf/imes/framework/web/core/handler/GlobalExceptionHandler.java b/cf-framework/cf-spring-boot-starter-web/src/main/java/com/cf/imes/framework/web/core/handler/GlobalExceptionHandler.java index 9b9c2f7dd..5b734fe73 100644 --- a/cf-framework/cf-spring-boot-starter-web/src/main/java/com/cf/imes/framework/web/core/handler/GlobalExceptionHandler.java +++ b/cf-framework/cf-spring-boot-starter-web/src/main/java/com/cf/imes/framework/web/core/handler/GlobalExceptionHandler.java @@ -14,6 +14,7 @@ import com.cf.imes.framework.common.util.json.JsonUtils; import com.cf.imes.framework.common.util.servlet.ServletUtils; import lombok.AllArgsConstructor; import lombok.extern.slf4j.Slf4j; +import org.springframework.dao.DuplicateKeyException; import org.springframework.security.access.AccessDeniedException; import org.springframework.util.Assert; import org.springframework.validation.BindException; @@ -212,6 +213,18 @@ public class GlobalExceptionHandler { return CommonResult.error(ex.getCode(), ex.getMessage()); } + /** + * 处理数据库DuplicateKeyException,违反唯一约束异常 + * + * @param ex + * @return + */ + @ExceptionHandler(value = DuplicateKeyException.class) + public CommonResult duplicateKeyExceptionHandler(DuplicateKeyException ex) { + log.info("[duplicateKeyExceptionHandler]", ex); + return CommonResult.error(INTERNAL_SERVER_ERROR.getCode(), "请求数据已存在,请检查"); + } + /** * 处理系统异常,兜底处理所有的一切 */ diff --git a/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPartDatasourceApi.java b/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPartDatasourceApi.java new file mode 100644 index 000000000..b647c6859 --- /dev/null +++ b/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPartDatasourceApi.java @@ -0,0 +1,33 @@ +package com.cf.imes.module.executor.api.datasource; + +import com.cf.imes.framework.common.pojo.CommonResult; +import com.cf.imes.module.executor.api.datasource.dto.PartGoodsRespDTO; +import com.cf.imes.module.executor.enums.ApiConstants; +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.cloud.openfeign.FeignClient; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestParam; + +import java.util.List; + +/** + * @author Gqr + * @since 2024/7/30 9:22 + */ +@FeignClient(name = ApiConstants.NAME) +@Tag(name = "RPC 服务 - 配件报表数据源") +public interface OrderPartDatasourceApi { + String PREFIX = ApiConstants.PREFIX + "/order-part"; + + @GetMapping(PREFIX + "/detail") + @Operation(summary = "配件明细") + @Parameter(name = "orderId", description = "生产单id", required = true, example = "1") + CommonResult> selectPartDetail(@RequestParam("orderId") Long orderId); + + @GetMapping(PREFIX + "/summary") + @Operation(summary = "配件汇总") + @Parameter(name = "orderId", description = "生产单id", required = true, example = "1") + CommonResult> selectPartAll(@RequestParam("orderId") Long orderId); +} diff --git a/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPlateDatasourceApi.java b/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPlateDatasourceApi.java index e482d683a..b711de35d 100644 --- a/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPlateDatasourceApi.java +++ b/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPlateDatasourceApi.java @@ -21,8 +21,13 @@ import java.util.List; public interface OrderPlateDatasourceApi { String PREFIX = ApiConstants.PREFIX + "/order-plate"; - @GetMapping(PREFIX + "/summary/byPlate") - @Operation(summary = "按板材汇总板材数据") + @GetMapping(PREFIX + "/summary") + @Operation(summary = "板材汇总") @Parameter(name = "orderId", description = "生产单id", required = true, example = "1") CommonResult> selectPlateGoodsListSummary(@RequestParam("orderId") Long orderId); + + @GetMapping(PREFIX + "/detail") + @Operation(summary = "板材明细") + @Parameter(name = "orderId", description = "生产单id", required = true, example = "1") + CommonResult> selectPlateGoodsList(@RequestParam("orderId") Long orderId); } diff --git a/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/dto/PartGoodsRespDTO.java b/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/dto/PartGoodsRespDTO.java new file mode 100644 index 000000000..1c22bcf34 --- /dev/null +++ b/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/dto/PartGoodsRespDTO.java @@ -0,0 +1,80 @@ +package com.cf.imes.module.executor.api.datasource.dto; + +import io.swagger.v3.oas.annotations.media.Schema; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.time.LocalDateTime; + +@Data +@Builder +@AllArgsConstructor +@NoArgsConstructor +@Schema(description = "管理后台 - 配件对应板材信息 Resp DTO") +public class PartGoodsRespDTO { + + @Schema(description = "柜体号", example = "11087") + private Long bodyId; + + @Schema(description = "柜体名称", example = "11087") + private String bodyName; + + @Schema(description = "房间号", example = "11087") + private Long roomId; + + @Schema(description = "房间名称", example = "11087") + private String roomName; + + @Schema(description = "配件 ID", requiredMode = Schema.RequiredMode.REQUIRED, example = "29347") + private Long id; + + @Schema(description = "生产单号", requiredMode = Schema.RequiredMode.REQUIRED) + private Long orderId; + + @Schema(description = "商品ID", requiredMode = Schema.RequiredMode.REQUIRED, example = "1195") + private String goodsId; + + @Schema(description = "配件名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "晨丰") + private String name; + + @Schema(description = "材质", requiredMode = Schema.RequiredMode.REQUIRED) + private String material; + + @Schema(description = "配件类型", requiredMode = Schema.RequiredMode.REQUIRED, example = "2") + private String type; + + @Schema(description = "型号", requiredMode = Schema.RequiredMode.REQUIRED) + private String model; + + @Schema(description = "规格", requiredMode = Schema.RequiredMode.REQUIRED) + private String spec; + + @Schema(description = "品牌", requiredMode = Schema.RequiredMode.REQUIRED) + private String brand; + + @Schema(description = "厂家", requiredMode = Schema.RequiredMode.REQUIRED) + private String factory; + + @Schema(description = "单位", requiredMode = Schema.RequiredMode.REQUIRED) + private String unit; + + @Schema(description = "价格", requiredMode = Schema.RequiredMode.REQUIRED, example = "29507") + private Double price; + + @Schema(description = "是否复合部件:0 否 1 是", requiredMode = Schema.RequiredMode.REQUIRED) + private Boolean isComposite; + + @Schema(description = "备注", requiredMode = Schema.RequiredMode.REQUIRED, example = "你猜") + private String remark; + + @Schema(description = "创建时间", requiredMode = Schema.RequiredMode.REQUIRED) + private LocalDateTime createTime; + + @Schema(description = "数量", requiredMode = Schema.RequiredMode.REQUIRED, example = "29507") + private Double num; + + @Schema(description = "金额", requiredMode = Schema.RequiredMode.REQUIRED, example = "29507") + private Double totalPrice; +} diff --git a/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/dto/PlateGoodsRespDTO.java b/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/dto/PlateGoodsRespDTO.java index d77ec4f3c..6f65f2735 100644 --- a/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/dto/PlateGoodsRespDTO.java +++ b/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/api/datasource/dto/PlateGoodsRespDTO.java @@ -154,7 +154,7 @@ public class PlateGoodsRespDTO { @Schema(description = "是否孤形对角") private Boolean isArcAcross; - @Schema(description = "是否异性") + @Schema(description = "是否异形") private Boolean isSpecialShaped; @Schema(description = "是否造型") diff --git a/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/enums/OrderPlateOpenDoorTypeEnum.java b/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/enums/OrderPlateOpenDoorTypeEnum.java new file mode 100644 index 000000000..370d86ae9 --- /dev/null +++ b/cf-module-prod-executor/cf-module-prod-executor-api/src/main/java/com/cf/imes/module/executor/enums/OrderPlateOpenDoorTypeEnum.java @@ -0,0 +1,40 @@ +package com.cf.imes.module.executor.enums; + +/** + * 板材开门类型枚举 + * + * @author Gqr + * @since 2024/7/29 9:58 + */ +public enum OrderPlateOpenDoorTypeEnum { + NO(0, "无"), + LEFT(1, "左"), + RIGHT(2, "右"), + UP(3, "上"), + DOWN(4, "下"); + + private final int code; + private final String desc; + + OrderPlateOpenDoorTypeEnum(int code, String desc) { + this.code = code; + this.desc = desc; + } + + public int getCode() { + return code; + } + + public String getDesc() { + return desc; + } + + public static String getDescFromCode(int code) { + for (OrderPlateOpenDoorTypeEnum orderPlateOpenDoorTypeEnum : OrderPlateOpenDoorTypeEnum.values()) { + if (orderPlateOpenDoorTypeEnum.getCode() == code) { + return orderPlateOpenDoorTypeEnum.getDesc(); + } + } + return null; + } +} diff --git a/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPartDatasourceApiImpl.java b/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPartDatasourceApiImpl.java new file mode 100644 index 000000000..195050ed9 --- /dev/null +++ b/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPartDatasourceApiImpl.java @@ -0,0 +1,42 @@ +package com.cf.imes.module.executor.api.datasource; + +import com.cf.imes.framework.common.pojo.CommonResult; +import com.cf.imes.framework.common.util.object.BeanUtils; +import com.cf.imes.framework.security.core.util.SecurityFrameworkUtils; +import com.cf.imes.module.executor.api.datasource.dto.PartGoodsRespDTO; +import com.cf.imes.module.executor.controller.admin.orderParts.vo.PartGoodsRespVO; +import com.cf.imes.module.executor.dal.mysql.orderParts.OrderPartsMapper; +import com.cf.imes.module.executor.enums.OrderDeletedEnum; +import org.springframework.validation.annotation.Validated; +import org.springframework.web.bind.annotation.RestController; + +import javax.annotation.Resource; +import java.util.List; + +/** + * @author Gqr + * @since 2024/7/30 9:21 + */ +@RestController // 提供 RESTful API 接口,给 Feign 调用 +@Validated +public class OrderPartDatasourceApiImpl implements OrderPartDatasourceApi { + + @Resource + private OrderPartsMapper orderPartsMapper; + + @Override + public CommonResult> selectPartDetail(Long orderId) { + Integer notDeletedStatus = OrderDeletedEnum.NOT_DELETED.getStatus(); + // 查询明细列表 + List partGoodsRespVOS = orderPartsMapper.selectPartDetail(orderId, SecurityFrameworkUtils.getLoginUser().getOrganId(), notDeletedStatus); + return CommonResult.success(BeanUtils.toBean(partGoodsRespVOS, PartGoodsRespDTO.class)); + } + + @Override + public CommonResult> selectPartAll(Long orderId) { + Integer notDeletedStatus = OrderDeletedEnum.NOT_DELETED.getStatus(); + // 查询明细列表 + List partGoodsRespVOS = orderPartsMapper.selectPartAll(orderId, SecurityFrameworkUtils.getLoginUser().getOrganId(), notDeletedStatus); + return CommonResult.success(BeanUtils.toBean(partGoodsRespVOS, PartGoodsRespDTO.class)); + } +} diff --git a/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPlateDatasourceApiImpl.java b/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPlateDatasourceApiImpl.java index d27d79569..82808ab93 100644 --- a/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPlateDatasourceApiImpl.java +++ b/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/java/com/cf/imes/module/executor/api/datasource/OrderPlateDatasourceApiImpl.java @@ -31,4 +31,12 @@ public class OrderPlateDatasourceApiImpl implements OrderPlateDatasourceApi { List plateGoodsRespVOS = plateMapper.selectPlateGoodsListSummary(orderId, SecurityFrameworkUtils.getLoginUser().getOrganId(), notDeletedStatus); return CommonResult.success(BeanUtils.toBean(plateGoodsRespVOS, PlateGoodsRespDTO.class)); } + + @Override + public CommonResult> selectPlateGoodsList(Long orderId) { + // 查询分组列表 + Integer notDeletedStatus = OrderDeletedEnum.NOT_DELETED.getStatus(); + List plateGoodsRespVOS = plateMapper.selectPlateGoodsList(orderId, SecurityFrameworkUtils.getLoginUser().getOrganId(), notDeletedStatus); + return CommonResult.success(BeanUtils.toBean(plateGoodsRespVOS, PlateGoodsRespDTO.class)); + } } diff --git a/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/resources/mapper/plate/PlateMapper.xml b/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/resources/mapper/plate/PlateMapper.xml index 0b964dcea..a3ff89e51 100644 --- a/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/resources/mapper/plate/PlateMapper.xml +++ b/cf-module-prod-executor/cf-module-prod-executor-biz/src/main/resources/mapper/plate/PlateMapper.xml @@ -357,7 +357,6 @@ left join order_goods ogs on op.goods_id = ogs.id left join order_item its on op.id = its.plate_id left join order_body bdy on bdy.id = its.body_id - left join order_goods gods on gods.id = op.goods_id where op.order_id = #{orderId} and op.organ_id = #{organId} and op.deleted = #{deleted} @@ -385,7 +384,6 @@ left join order_goods ogs on op.goods_id = ogs.id left join order_item its on op.id = its.plate_id left join order_body bdy on bdy.id = its.body_id - left join order_goods gods on gods.id = op.goods_id where op.order_id = #{orderId} and op.organ_id = #{organId} and op.deleted = #{deleted} diff --git a/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/controller/admin/plate/PlateController.java b/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/controller/admin/plate/PlateController.java index 57a63ef71..7c5fa0cbc 100644 --- a/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/controller/admin/plate/PlateController.java +++ b/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/controller/admin/plate/PlateController.java @@ -62,8 +62,8 @@ public class PlateController { @DeleteMapping("/delete") @Operation(summary = "删除板材信息") @Parameters({ - @Parameter(name = "id", description = "编号", required = true), - @Parameter(name = "organId", description = "板材所属组织ID") + @Parameter(name = "id", description = "编号", required = true, example = "1024"), + @Parameter(name = "organId", description = "板材所属组织ID", example = "1024") }) // @PreAuthorize("@ss.hasPermission('manage:plate:delete')") @PreAuthorize("@ss.hasAnyPermissions('manage:plate:delete','base:plate:delete')") diff --git a/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/framework/rpc/config/RpcConfiguration.java b/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/framework/rpc/config/RpcConfiguration.java index bb930299b..5023818fe 100644 --- a/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/framework/rpc/config/RpcConfiguration.java +++ b/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/framework/rpc/config/RpcConfiguration.java @@ -1,12 +1,13 @@ package com.cf.imes.module.manage.framework.rpc.config; import com.cf.imes.module.system.api.organ.OrganApi; +import com.cf.imes.module.system.api.permission.PermissionApi; import com.cf.imes.module.system.api.process.ProcessApi; import com.cf.imes.module.system.api.user.AdminUserApi; import org.springframework.cloud.openfeign.EnableFeignClients; import org.springframework.context.annotation.Configuration; @Configuration(proxyBeanMethods = false) -@EnableFeignClients(clients = {AdminUserApi.class, OrganApi.class, ProcessApi.class}) +@EnableFeignClients(clients = {AdminUserApi.class, OrganApi.class, ProcessApi.class, PermissionApi.class}) public class RpcConfiguration { } diff --git a/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/service/plate/PlateServiceImpl.java b/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/service/plate/PlateServiceImpl.java index 750a8047f..8c557407a 100644 --- a/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/service/plate/PlateServiceImpl.java +++ b/cf-module-prod-manage/cf-module-prod-manage-biz/src/main/java/com/cf/imes/module/manage/service/plate/PlateServiceImpl.java @@ -10,6 +10,7 @@ import com.cf.imes.module.manage.controller.admin.plate.vo.plate.PlateImportResp import com.cf.imes.module.manage.controller.admin.plate.vo.plate.PlatePageReqVO; import com.cf.imes.module.manage.controller.admin.plate.vo.plate.PlateSaveReqVO; import com.cf.imes.module.system.api.organ.OrganApi; +import com.cf.imes.module.system.api.permission.PermissionApi; import com.cf.imes.module.system.enums.ErrorCodeConstants; import org.springframework.stereotype.Service; import org.springframework.validation.annotation.Validated; @@ -26,6 +27,7 @@ import com.cf.imes.module.manage.dal.mysql.plate.PlateMapper; import javax.annotation.Resource; import static com.cf.imes.framework.common.exception.util.ServiceExceptionUtil.exception; +import static com.cf.imes.framework.security.core.util.SecurityFrameworkUtils.getLoginUser; import static com.cf.imes.module.system.enums.ErrorCodeConstants.PLATE_NOT_EXISTS; /** @@ -43,22 +45,29 @@ public class PlateServiceImpl implements PlateService { @Resource private OrganApi organApi; + @Resource + private PermissionApi permissionApi; + + private final static String BASE_PLATE_IMPORT_PERMISSION = "base:plate:import"; // 导入板材 + private final static String BASE_PLATE_DELETE_PERMISSION = "base:plate:delete"; // 删除板材信息 + private final static String BASE_PLATE_CREATE_PERMISSION = "base:plate:create"; // 创建板材信息 + private final static String BASE_PLATE_UPDATE_PERMISSION = "base:plate:update"; // 更新板材信息 + private final static String BASE_PLATE_QUERY_PERMISSION = "base:plate:query"; // 获得板材信息 + @Override @OrganIgnore public Long createPlate(PlateSaveReqVO createReqVO) { PlateDO plate = BeanUtils.toBean(createReqVO, PlateDO.class); - if (createReqVO.getOrganId() != null && createReqVO.getOrganId() != 0 ){ - validateOrganExists(createReqVO.getOrganId()); - validateGoodExists(createReqVO.getGoodsId(), createReqVO.getOrganId()); - }else { + if (permissionApi.hasRoles(getLoginUser().getId(), BASE_PLATE_CREATE_PERMISSION).getData()){ + if (plate.getOrganId() != null && plate.getOrganId() != 0 ){ + validateOrganExists(plate.getOrganId()); + } + } else { plate.setOrganId(OrganContextHolder.getOrganId()); } // 判断板材是否存在 - PlateDO existPlate = plateMapper.selectByGoodID(createReqVO.getGoodsId(), plate.getOrganId()); + validateGoodExists(plate.getGoodsId(),plate.getOrganId()); - if (existPlate != null){ - throw exception(ErrorCodeConstants.PLATE_EXISTS); - } plateMapper.insert(plate);// 组织id未传输 // 返回 return plate.getId(); @@ -69,10 +78,13 @@ public class PlateServiceImpl implements PlateService { @Transactional(rollbackFor = Exception.class) public void updatePlate(PlateSaveReqVO updateReqVO) { // 更新 判断是否有组织id - if (updateReqVO.getOrganId() == null || updateReqVO.getOrganId() == 0){ + if (permissionApi.hasRoles(getLoginUser().getId(), BASE_PLATE_UPDATE_PERMISSION).getData()){ + if (updateReqVO.getOrganId() != null && updateReqVO.getOrganId() != 0 ){ + validateOrganExists(updateReqVO.getOrganId()); + } + } else { updateReqVO.setOrganId(OrganContextHolder.getOrganId()); } - validateOrganExists(updateReqVO.getOrganId()); // 校验存在 validatePlateExists(updateReqVO.getId(), updateReqVO.getOrganId()); @@ -84,10 +96,13 @@ public class PlateServiceImpl implements PlateService { @OrganIgnore @Transactional(rollbackFor = Exception.class) public void deletePlate(Long id,Long organId) { - if (organId == null || organId == 0){ + if (permissionApi.hasRoles(getLoginUser().getId(), BASE_PLATE_DELETE_PERMISSION).getData()){ + if (organId != null && organId != 0 ){ + validateOrganExists(organId); + } + } else { organId = OrganContextHolder.getOrganId(); } - validateOrganExists(organId); // 校验存在 validatePlateExists(id,organId); @@ -115,6 +130,13 @@ public class PlateServiceImpl implements PlateService { @Override @OrganIgnore public PageResult getPlatePage(PlatePageReqVO pageReqVO) { + if (permissionApi.hasRoles(getLoginUser().getId(), BASE_PLATE_QUERY_PERMISSION).getData()){ + if (pageReqVO.getOrganId() != null && pageReqVO.getOrganId() != 0 ){ + validateOrganExists(pageReqVO.getOrganId()); + } + } else { + pageReqVO.setOrganId(OrganContextHolder.getOrganId()); + } if (pageReqVO.getOrganId() == null || pageReqVO.getOrganId() == 0){ pageReqVO.setOrganId(OrganContextHolder.getOrganId()); } @@ -130,25 +152,32 @@ public class PlateServiceImpl implements PlateService { // if (CollUtil.isEmpty(importPlates)) { // throw ServiceExceptionUtil.exception(ErrorCodeConstants.PLATE_IMPORT_LIST_IS_EMPTY); // } - validateOrganExists(organId); + if (permissionApi.hasRoles(getLoginUser().getId(), BASE_PLATE_IMPORT_PERMISSION).getData()){ + if (organId != null && organId != 0 ){ + validateOrganExists(organId); + } + } else { + organId = OrganContextHolder.getOrganId(); + } PlateImportRespVO respVO = PlateImportRespVO.builder().createPlateNames(new ArrayList<>()) .updatePlateNames(new ArrayList<>()).failurePlateNames(new LinkedHashMap<>()).build(); // 批量插入集合 List insertList = new ArrayList<>(); // 批量更新集合 List updateList = new ArrayList<>(); + Long finalOrganId = organId; importPlates.forEach(importPlate -> { // 判断如果不存在,在进行插入 - PlateDO existPlate = plateMapper.selectByGoodID(importPlate.getGoodsId(), organId); + PlateDO existPlate = plateMapper.selectByGoodID(importPlate.getGoodsId(), finalOrganId); if (existPlate == null) { respVO.getCreatePlateNames().add(importPlate.getGoodsName()); - insertList.add(BeanUtils.toBean(importPlate, PlateDO.class).setOrganId(organId).setTexture(Boolean.valueOf(importPlate.getTexture()))); + insertList.add(BeanUtils.toBean(importPlate, PlateDO.class).setOrganId(finalOrganId).setTexture(Boolean.valueOf(importPlate.getTexture()))); return; } // 判断是否允许更新 if (!isUpdateSupport) { respVO.getFailurePlateNames().put(importPlate.getGoodsName(), ErrorCodeConstants.PLATE_EXISTS.getMsg()); - PlateDO plateDO = BeanUtils.toBean(importPlate, PlateDO.class).setOrganId(organId).setId(existPlate.getId()).setTexture(Boolean.valueOf(importPlate.getTexture())); + PlateDO plateDO = BeanUtils.toBean(importPlate, PlateDO.class).setOrganId(finalOrganId).setId(existPlate.getId()).setTexture(Boolean.valueOf(importPlate.getTexture())); updateList.add(plateDO); } }); diff --git a/cf-module-report/cf-module-report-api/src/main/java/com/cf/imes/module/report/enums/ErrorCodeConstants.java b/cf-module-report/cf-module-report-api/src/main/java/com/cf/imes/module/report/enums/ErrorCodeConstants.java index 030bcf8a8..db4a7d81c 100644 --- a/cf-module-report/cf-module-report-api/src/main/java/com/cf/imes/module/report/enums/ErrorCodeConstants.java +++ b/cf-module-report/cf-module-report-api/src/main/java/com/cf/imes/module/report/enums/ErrorCodeConstants.java @@ -11,16 +11,18 @@ import com.cf.imes.framework.common.exception.ErrorCode; public final class ErrorCodeConstants { // ========== UREPORT template模块 1-003-001-000 ========== - public static ErrorCode TEMPLATE_NOT_EXISTS = new ErrorCode(1_003_001_001, "报表模板信息不存在"); + public static final ErrorCode TEMPLATE_NOT_EXISTS = new ErrorCode(1_003_001_001, "报表模板信息不存在"); // ========== UREPORT datasource模块 1-003-002-000 ========== - public static ErrorCode DATASOURCE_NOT_EXISTS = new ErrorCode(1_003_002_001, "报表数据源不存在"); - public static ErrorCode DATASOURCE_CONNECT_FAIL = new ErrorCode(1_003_002_001, "报表数据源连接失败"); + public static final ErrorCode DATASOURCE_NOT_EXISTS = new ErrorCode(1_003_002_001, "报表数据源不存在"); + public static final ErrorCode DATASOURCE_CONNECT_FAIL = new ErrorCode(1_003_002_002, "报表数据源连接失败"); + public static final ErrorCode DATASOURCE_BUILDIN_OPERATION_PERMISSION_ERROR = new ErrorCode(1_003_002_003, "内置报表数据源只能由超级管理员操作"); + // ========== UREPORT dataset模块 1-003-003-000 ========== - public static ErrorCode DATASET_NOT_EXISTS = new ErrorCode(1_003_003_001, "报表数据集不存在"); - public static ErrorCode DATASET_SQL_INJECTION_RISK = new ErrorCode(1_003_003_002, "存在SQL注入风险"); - public static ErrorCode DATASET_SQL_REQUIRED = new ErrorCode(1_003_003_003, "SQL语句不能为空"); - public static ErrorCode DATASET_SQL_ILLEGAL = new ErrorCode(1_003_003_004, "SQL语句非法"); - public static ErrorCode DATASET_GET_FIELDS_ERROR = new ErrorCode(1_003_003_005, "获取表字段"); + public static final ErrorCode DATASET_NOT_EXISTS = new ErrorCode(1_003_003_001, "报表数据集不存在"); + public static final ErrorCode DATASET_SQL_INJECTION_RISK = new ErrorCode(1_003_003_002, "存在SQL注入风险"); + public static final ErrorCode DATASET_SQL_REQUIRED = new ErrorCode(1_003_003_003, "SQL语句不能为空"); + public static final ErrorCode DATASET_SQL_ILLEGAL = new ErrorCode(1_003_003_004, "SQL语句非法"); + public static final ErrorCode DATASET_GET_FIELDS_ERROR = new ErrorCode(1_003_003_005, "获取表字段"); } diff --git a/cf-module-report/cf-module-report-api/src/main/java/com/cf/imes/module/report/enums/template/ReportTemplateTypeEnum.java b/cf-module-report/cf-module-report-api/src/main/java/com/cf/imes/module/report/enums/template/ReportTemplateTypeEnum.java deleted file mode 100644 index 0aca8ef67..000000000 --- a/cf-module-report/cf-module-report-api/src/main/java/com/cf/imes/module/report/enums/template/ReportTemplateTypeEnum.java +++ /dev/null @@ -1,26 +0,0 @@ -package com.cf.imes.module.report.enums.template; - -import lombok.AllArgsConstructor; -import lombok.Getter; - -/** - * 报表模板类型 - * - * @author Gqr - * @since 2024/7/5 9:25 - */ -@Getter -@AllArgsConstructor -public enum ReportTemplateTypeEnum { - /** - * 内置 - */ - SYSTEM(1), - /** - * 自定义 - */ - CUSTOM(2); - - private final Integer type; - -} diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/dataset/vo/ReportDatasetSaveReqVO.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/dataset/vo/ReportDatasetSaveReqVO.java index 12e14ef09..dfc4eb8eb 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/dataset/vo/ReportDatasetSaveReqVO.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/dataset/vo/ReportDatasetSaveReqVO.java @@ -30,7 +30,7 @@ public class ReportDatasetSaveReqVO implements Serializable { @Schema(description = "数据集名称", example = "测试数据集") private String name; - @Schema(description = "数据源id", requiredMode = Schema.RequiredMode.REQUIRED, example = "1") + @Schema(description = "数据源id", example = "1") private Long datasourceId; @Schema(description = "动态查询SQL") diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/ReportDatasourceController.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/ReportDatasourceController.java index c96f0bc69..136d982ae 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/ReportDatasourceController.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/ReportDatasourceController.java @@ -95,6 +95,13 @@ public class ReportDatasourceController { return success(datasourceService.loadBeanMethods(beanId)); } + @GetMapping("/buildin/datasources") + @Operation(summary = "获取内置数据源") + @PreAuthorize("@ss.hasPermission('report:datasource:query')") + public CommonResult> getBuildinDatasources() { + return success(BeanUtils.toBean(datasourceService.getBuildinDatasources(), ReportDatasourceRespVO.class)); + } + @PostMapping("/datasource/connect") @Operation(summary = "测试数据源连接") @PreAuthorize("@ss.hasPermission('report:datasource:query')") diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceReqVO.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceReqVO.java index 2878f0d62..35cc87ef5 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceReqVO.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceReqVO.java @@ -30,6 +30,6 @@ public class ReportDatasourceReqVO implements Serializable { @Schema(description = "数据源名称", example = "测试库") private String name; - @Schema(description = "数据源类型,0 jdbc、1 buildin、2 spring", example = "jdbc") + @Schema(description = "类型,0 内置、1 自定义", example = "1") private Integer type; } diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceRespVO.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceRespVO.java index 82ba7889d..2505c0bd2 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceRespVO.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceRespVO.java @@ -28,8 +28,11 @@ public class ReportDatasourceRespVO { @Schema(description = "数据源名称", example = "测试库") private String name; - @Schema(description = "数据源类型,jdbc、buildin、spring", example = "jdbc") - private ReportDatasourceTypeEnum type; + @Schema(description = "数据源类型,jdbc、spring", example = "jdbc") + private ReportDatasourceTypeEnum dsType; + + @Schema(description = "模板类型,0内置、1自定义", example = "0") + private Integer type; @Schema(description = "数据源驱动类",example = "com.mysql.cj.jdbc.Driver") private String driver; diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceSaveReqVO.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceSaveReqVO.java index f0ad81190..896aceb1d 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceSaveReqVO.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/datasource/vo/ReportDatasourceSaveReqVO.java @@ -2,13 +2,13 @@ package com.cf.imes.module.report.controller.admin.datasource.vo; import com.cf.imes.module.report.controller.admin.dataset.vo.ReportDatasetSaveReqVO; import com.cf.imes.module.report.validation.datasource.ReportDatasourceTypeInEnum; +import com.cf.imes.module.report.validation.template.ReportTemplateTypeInEnum; import io.swagger.v3.oas.annotations.media.Schema; import lombok.AllArgsConstructor; import lombok.Builder; import lombok.Data; import lombok.NoArgsConstructor; -import javax.validation.constraints.NotNull; import java.io.Serial; import java.io.Serializable; import java.util.ArrayList; @@ -30,15 +30,19 @@ public class ReportDatasourceSaveReqVO implements Serializable { @Schema(description = "数据源id", example = "1") private Long id; - @Schema(description = "模板id", requiredMode = Schema.RequiredMode.REQUIRED, example = "1") + @Schema(description = "模板id", example = "1") private Long templateId; @Schema(description = "数据源名称", example = "测试库") private String name; - @Schema(description = "数据源类型,jdbc、buildin、spring", example = "jdbc") + @Schema(description = "模板类型,0内置、1自定义", example = "1") + @ReportTemplateTypeInEnum + private Integer type; + + @Schema(description = "数据源类型,jdbc、spring", example = "jdbc") @ReportDatasourceTypeInEnum - private String type; + private String dsType; @Schema(description = "spring型数据源id") private String beanId; diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/ReportTemplateController.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/ReportTemplateController.java index 0f4dec631..9a2c5023c 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/ReportTemplateController.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/ReportTemplateController.java @@ -18,11 +18,11 @@ import io.swagger.v3.oas.annotations.Parameter; import io.swagger.v3.oas.annotations.tags.Tag; import lombok.extern.slf4j.Slf4j; import org.apache.commons.io.IOUtils; -import org.springframework.beans.factory.annotation.Autowired; 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; @@ -43,7 +43,7 @@ import static com.cf.imes.framework.common.pojo.CommonResult.success; @Validated @Slf4j public class ReportTemplateController { - @Autowired + @Resource private ReportTemplateService templateService; @PutMapping("/template") diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/vo/ReportTemplateRespVO.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/vo/ReportTemplateRespVO.java index 7479e566b..5dc20d7be 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/vo/ReportTemplateRespVO.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/vo/ReportTemplateRespVO.java @@ -28,7 +28,7 @@ public class ReportTemplateRespVO { private String content; @Schema(description = "模板类型,0内置、1自定义", example = "0") - private Long type; + private Integer type; @Schema(description = "创建时间", requiredMode = Schema.RequiredMode.REQUIRED) private LocalDateTime createTime; diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/vo/ReportTemplateSaveReqVO.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/vo/ReportTemplateSaveReqVO.java index 375de199c..6dcf2360a 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/vo/ReportTemplateSaveReqVO.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/controller/admin/template/vo/ReportTemplateSaveReqVO.java @@ -1,6 +1,7 @@ package com.cf.imes.module.report.controller.admin.template.vo; import com.cf.imes.module.report.controller.admin.datasource.vo.ReportDatasourceSaveReqVO; +import com.cf.imes.module.report.validation.template.ReportTemplateTypeInEnum; import io.swagger.v3.oas.annotations.media.Schema; import lombok.AllArgsConstructor; import lombok.Builder; @@ -34,6 +35,7 @@ public class ReportTemplateSaveReqVO { private List datasource = new ArrayList<>(); @Schema(description = "模板类型,0内置、1自定义", example = "1") + @ReportTemplateTypeInEnum private Integer type; @Schema(description = "备注", example = "该模板仅供生产使用") diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/dal/dataobject/datasource/ReportDatasourceDO.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/dal/dataobject/datasource/ReportDatasourceDO.java index 3beab7a73..7e56e6a99 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/dal/dataobject/datasource/ReportDatasourceDO.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/dal/dataobject/datasource/ReportDatasourceDO.java @@ -7,6 +7,7 @@ import com.baomidou.mybatisplus.annotation.TableName; import com.cf.imes.framework.mybatis.core.dataobject.BaseDO; import com.cf.imes.module.report.dal.dataobject.dataset.ReportDatasetDO; import com.cf.imes.module.report.enums.datasource.ReportDatasourceTypeEnum; +import com.cf.imes.module.report.enums.template.ReportTemplateTypeEnum; import lombok.*; import java.util.List; @@ -40,9 +41,15 @@ public class ReportDatasourceDO extends BaseDO { */ private String name; /** - * 模板类型,jdbc、buildin、spring + * 模板类型,jdbc、spring */ - private ReportDatasourceTypeEnum type; + private ReportDatasourceTypeEnum dsType; + + /** + * 模板类型,0内置、1自定义 + */ + private ReportTemplateTypeEnum type; + /** * spring型数据源id */ diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/dal/dataobject/template/ReportTemplateDO.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/dal/dataobject/template/ReportTemplateDO.java index c6d82b70a..f621abe5c 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/dal/dataobject/template/ReportTemplateDO.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/dal/dataobject/template/ReportTemplateDO.java @@ -4,6 +4,7 @@ import com.baomidou.mybatisplus.annotation.*; import com.cf.imes.framework.mybatis.core.dataobject.BaseDO; import com.cf.imes.framework.mybatis.core.type.CompressStringTypeHandler; import com.cf.imes.module.report.dal.dataobject.datasource.ReportDatasourceDO; +import com.cf.imes.module.report.enums.template.ReportTemplateTypeEnum; import lombok.*; import java.util.List; @@ -40,7 +41,7 @@ public class ReportTemplateDO extends BaseDO { /** * 模板类型,0内置、1自定义 */ - private Integer type; + private ReportTemplateTypeEnum type; /** * 备注 */ diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/enums/datasource/ReportDatasourceTypeEnum.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/enums/datasource/ReportDatasourceTypeEnum.java index d31672640..2e2a03057 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/enums/datasource/ReportDatasourceTypeEnum.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/enums/datasource/ReportDatasourceTypeEnum.java @@ -14,8 +14,7 @@ import lombok.Getter; @AllArgsConstructor public enum ReportDatasourceTypeEnum { JDBC(0,"jdbc"), - BUILDIN(1,"buildin"), - SPRING(2,"spring"); + SPRING(1,"spring"); @EnumValue private final Integer code; diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/enums/template/ReportTemplateTypeEnum.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/enums/template/ReportTemplateTypeEnum.java new file mode 100644 index 000000000..9e24af0cf --- /dev/null +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/enums/template/ReportTemplateTypeEnum.java @@ -0,0 +1,38 @@ +package com.cf.imes.module.report.enums.template; + +import com.baomidou.mybatisplus.annotation.EnumValue; +import com.fasterxml.jackson.annotation.JsonCreator; +import lombok.AllArgsConstructor; +import lombok.Getter; + +/** + * 报表模板类型 + * + * @author Gqr + * @since 2024/7/5 9:25 + */ +@Getter +@AllArgsConstructor +public enum ReportTemplateTypeEnum { + /** + * 内置 + */ + SYSTEM(0), + /** + * 自定义 + */ + CUSTOM(1); + + @EnumValue + private final Integer type; + + @JsonCreator + public static ReportTemplateTypeEnum fromType(Integer type) { + for (ReportTemplateTypeEnum value : values()) { + if (value.getType().equals(type)) { + return value; + } + } + return null; + } +} diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/rpc/config/RpcConfiguration.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/rpc/config/RpcConfiguration.java index 03a4b3da0..ae0cb28d0 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/rpc/config/RpcConfiguration.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/rpc/config/RpcConfiguration.java @@ -1,11 +1,12 @@ package com.cf.imes.module.report.framework.rpc.config; import com.cf.imes.module.executor.api.datasource.OrderDatasourceApi; +import com.cf.imes.module.executor.api.datasource.OrderPartDatasourceApi; import com.cf.imes.module.executor.api.datasource.OrderPlateDatasourceApi; import org.springframework.cloud.openfeign.EnableFeignClients; import org.springframework.context.annotation.Configuration; @Configuration(proxyBeanMethods = false) -@EnableFeignClients(clients = {OrderPlateDatasourceApi.class, OrderDatasourceApi.class}) +@EnableFeignClients(clients = {OrderPlateDatasourceApi.class, OrderDatasourceApi.class, OrderPartDatasourceApi.class}) public class RpcConfiguration { } diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/ureport/bean/MockBeanDatasource.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/ureport/bean/MockBeanDatasource.java deleted file mode 100644 index c02c33568..000000000 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/ureport/bean/MockBeanDatasource.java +++ /dev/null @@ -1,29 +0,0 @@ -package com.cf.imes.module.report.framework.ureport.bean; - -import com.cf.imes.module.report.framework.ureport.annotation.CfReportSpringbeanDatasource; - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; -import java.util.Map; - -/** - * @author Gqr - * @since 2024/7/11 17:15 - */ -@CfReportSpringbeanDatasource(value = "MockBeanDatasource", name = "模拟bean数据源") -public class MockBeanDatasource { - - public List> mockList(String dsName, String datasetName, Map parameters) { - List> testList = new ArrayList<>(); - testList.add(new HashMap() {{ - put("a", "11111"); - put("b", "一一一一一一"); - }}); - testList.add(new HashMap() {{ - put("a", "22222"); - put("b", "二二二二二二"); - }}); - return testList; - } -} diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/ureport/bean/OrderSummaryBeanDatasource.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/ureport/bean/OrderSummaryBeanDatasource.java index f9f3f6c3e..be3a35671 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/ureport/bean/OrderSummaryBeanDatasource.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/ureport/bean/OrderSummaryBeanDatasource.java @@ -4,9 +4,12 @@ import cn.hutool.core.collection.CollUtil; import cn.hutool.core.util.ObjectUtil; import com.cf.imes.framework.common.pojo.CommonResult; import com.cf.imes.module.executor.api.datasource.OrderDatasourceApi; +import com.cf.imes.module.executor.api.datasource.OrderPartDatasourceApi; import com.cf.imes.module.executor.api.datasource.OrderPlateDatasourceApi; import com.cf.imes.module.executor.api.datasource.dto.OrderDTO; +import com.cf.imes.module.executor.api.datasource.dto.PartGoodsRespDTO; import com.cf.imes.module.executor.api.datasource.dto.PlateGoodsRespDTO; +import com.cf.imes.module.executor.enums.OrderPlateOpenDoorTypeEnum; import com.cf.imes.module.report.framework.ureport.annotation.CfReportSpringbeanDatasource; import lombok.extern.slf4j.Slf4j; @@ -33,7 +36,14 @@ public class OrderSummaryBeanDatasource { @Resource private OrderDatasourceApi orderDatasourceApi; + @Resource + private OrderPartDatasourceApi orderPartDatasourceApi; + + // 常用的字段key private static final String ORDER_ID_FIELD_NAME = "orderId"; + private static final String BODY_NAME_FIELD_NAME = "bodyName"; + private static final String ROOM_NAME_FIELD_NAME = "roomName"; + private static final String REMARK_FIELD_NAME = "remark"; /** * 生产单信息 @@ -44,6 +54,7 @@ public class OrderSummaryBeanDatasource { * @return */ public List> orderInfo(String dsName, String datasetName, Map parameters) { + log.info("报表数据源[OrderSummaryBeanDatasource][orderInfo][{}][{}]调用开始", dsName, datasetName); List> resultList = new ArrayList<>(); Object orderId = parameters.get(ORDER_ID_FIELD_NAME); @@ -57,32 +68,33 @@ public class OrderSummaryBeanDatasource { DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd"); if (orderDTO != null) { - // 把orderInfo转map并put到resultList中 - resultList.add(new HashMap<>() {{ - // 构造报表所需结构 - put(ORDER_ID_FIELD_NAME, orderDTO.getId()); - put("customOrderNo", orderDTO.getCustomOrderNo()); - put("dealer", orderDTO.getDealer()); - LocalDateTime orderDate = orderDTO.getOrderDate(); - put("orderDate", ObjectUtil.isNotNull(orderDate) ? formatter.format(orderDate) : null); - LocalDateTime deliveryDate = orderDTO.getDeliveryDate(); - put("deliveryDate", ObjectUtil.isNotNull(deliveryDate) ? formatter.format(deliveryDate) : null); - put("customer", orderDTO.getCustomer()); - put("phoneNumber", orderDTO.getPhoneNumber()); - }}); + HashMap resultMap = new HashMap<>(); + // 构造报表所需结构 + resultMap.put(ORDER_ID_FIELD_NAME, orderDTO.getId()); + resultMap.put("customOrderNo", orderDTO.getCustomOrderNo()); + resultMap.put("dealer", orderDTO.getDealer()); + LocalDateTime orderDate = orderDTO.getOrderDate(); + resultMap.put("orderDate", ObjectUtil.isNotNull(orderDate) ? formatter.format(orderDate) : null); + LocalDateTime deliveryDate = orderDTO.getDeliveryDate(); + resultMap.put("deliveryDate", ObjectUtil.isNotNull(deliveryDate) ? formatter.format(deliveryDate) : null); + resultMap.put("customer", orderDTO.getCustomer()); + resultMap.put("phoneNumber", orderDTO.getPhoneNumber()); + resultList.add(resultMap); } + log.info("报表数据源[OrderSummaryBeanDatasource][orderInfo][{}][{}]调用结束", dsName, datasetName); return resultList; } /** - * 板材汇总-按板材 + * 板材汇总 * * @param dsName * @param datasetName * @param parameters * @return */ - public List> orderPlateSummaryByPlate(String dsName, String datasetName, Map parameters) { + public List> orderPlateGoodsSummary(String dsName, String datasetName, Map parameters) { + log.info("报表数据源[OrderSummaryBeanDatasource][orderPlateGoodsSummary][{}][{}]调用开始", dsName, datasetName); List> resultList = new ArrayList<>(); Object orderId = parameters.get(ORDER_ID_FIELD_NAME); @@ -92,24 +104,159 @@ public class OrderSummaryBeanDatasource { if (CollUtil.isNotEmpty(plateGoodsRespDTOS)) { plateGoodsRespDTOS.forEach(p -> { - resultList.add(new HashMap<>() {{ - BigDecimal area = p.getArea(); - Integer count = p.getCount(); - // 构造报表所需结构 - put("roomName", p.getRoomName()); - put("bodyName", p.getBodyName()); - put("thickness", p.getThickness()); - put("name", p.getName()); - put("height", p.getHeight()); - put("width", p.getWidth()); - put("count", count); - put("area", area); - put("openDoorType", p.getOpenDoorType()); - put("remark", p.getRemark()); - put("areaAll", area.multiply(BigDecimal.valueOf(count))); - }}); + Map resultMap = new HashMap<>(); + BigDecimal area = p.getArea(); + Integer count = p.getCount(); + // 构造报表所需结构 + resultMap.put(ROOM_NAME_FIELD_NAME, p.getRoomName()); + resultMap.put(BODY_NAME_FIELD_NAME, p.getBodyName()); + resultMap.put("thickness", stripTrailingZeros(p.getThickness())); + resultMap.put("name", p.getName()); + resultMap.put("height", stripTrailingZeros(p.getHeight())); + resultMap.put("width", stripTrailingZeros(p.getWidth())); + resultMap.put("count", count); + resultMap.put("area", stripTrailingZeros(area)); + resultMap.put("openDoorType", OrderPlateOpenDoorTypeEnum.getDescFromCode(p.getOpenDoorType())); + resultMap.put("material", p.getMaterial()); + resultMap.put("color", p.getColor()); + resultMap.put(REMARK_FIELD_NAME, p.getRemark()); + resultMap.put("areaAll", stripTrailingZeros(area.multiply(BigDecimal.valueOf(count)))); + resultList.add(resultMap); }); } + log.info("报表数据源[OrderSummaryBeanDatasource][orderPlateGoodsSummary][{}][{}]调用结束", dsName, datasetName); return resultList; } + + /** + * 板材明细 + * + * @param dsName + * @param datasetName + * @param parameters + * @return + */ + public List> orderPlateGoodsList(String dsName, String datasetName, Map parameters) { + log.info("报表数据源[OrderSummaryBeanDatasource][orderPlateGoodsList][{}][{}]调用开始", dsName, datasetName); + List> resultList = new ArrayList<>(); + + Object orderId = parameters.get(ORDER_ID_FIELD_NAME); + // 查询统计信息 + CommonResult> commonResult = orderPlateDatasourceApi.selectPlateGoodsList(Long.parseLong(orderId.toString())); + List plateGoodsRespDTOS = commonResult.getData(); + + if (CollUtil.isNotEmpty(plateGoodsRespDTOS)) { + plateGoodsRespDTOS.forEach(p -> { + Map resultMap = new HashMap<>(); + BigDecimal area = p.getArea(); + Integer count = p.getCount(); + // 构造报表所需结构 + resultMap.put("goodsName", p.getGoodsName()); + resultMap.put("name", p.getName()); + resultMap.put("material", p.getMaterial()); + resultMap.put("color", p.getColor()); + resultMap.put("goodsThickness", p.getGoodsThickness()); + resultMap.put("count", p.getCount()); + resultMap.put(ROOM_NAME_FIELD_NAME, p.getRoomName()); + resultMap.put(BODY_NAME_FIELD_NAME, p.getBodyName()); + resultMap.put("plateNo", p.getPlateNo()); + resultMap.put("height", stripTrailingZeros(p.getHeight())); + resultMap.put("width", stripTrailingZeros(p.getWidth())); + resultMap.put("thickness", stripTrailingZeros(p.getThickness())); + resultMap.put("area", stripTrailingZeros(area)); + resultMap.put(REMARK_FIELD_NAME, p.getRemark()); + resultMap.put("isSpecialShaped", getBooleanString(p.getIsSpecialShaped())); + resultMap.put("isSculpt", getBooleanString(p.getIsSculpt())); + resultMap.put("openDoorType", OrderPlateOpenDoorTypeEnum.getDescFromCode(p.getOpenDoorType())); + resultMap.put("seal", String.join(",", stripTrailingZeros(p.getSealLeft()), stripTrailingZeros(p.getSealRight()), stripTrailingZeros(p.getSealUp()), stripTrailingZeros(p.getSealDown()))); + resultMap.put("areaAll", stripTrailingZeros(area.multiply(BigDecimal.valueOf(count)))); + resultList.add(resultMap); + }); + } + log.info("报表数据源[OrderSummaryBeanDatasource][orderPlateGoodsList][{}][{}]调用结束", dsName, datasetName); + return resultList; + } + + public List> orderPartDetailList(String dsName, String datasetName, Map parameters) { + log.info("报表数据源[OrderSummaryBeanDatasource][orderPartDetailList][{}][{}]调用开始", dsName, datasetName); + List> resultList = new ArrayList<>(); + + Object orderId = parameters.get(ORDER_ID_FIELD_NAME); + CommonResult> commonResult = orderPartDatasourceApi.selectPartDetail(Long.parseLong(orderId.toString())); + List partGoodsRespDTOS = commonResult.getData(); + + if (CollUtil.isNotEmpty(partGoodsRespDTOS)) { + partGoodsRespDTOS.forEach(p -> { + Map resultMap = new HashMap<>(); + // 构造报表所需结构 + resultMap.put(ROOM_NAME_FIELD_NAME, p.getRoomName()); + resultMap.put(BODY_NAME_FIELD_NAME, p.getBodyName()); + resultMap.put("name", p.getName()); + resultMap.put("brand", p.getBrand()); + resultMap.put("factory", p.getFactory()); + resultMap.put("model", p.getModel()); + resultMap.put("spec", p.getSpec()); + resultMap.put("num", p.getNum()); + resultMap.put("unit", p.getUnit()); + resultMap.put("price", p.getPrice()); + resultMap.put("totalPrice", p.getTotalPrice()); + resultMap.put(REMARK_FIELD_NAME, p.getRemark()); + resultList.add(resultMap); + }); + } + + log.info("报表数据源[OrderSummaryBeanDatasource][orderPartDetailList][{}][{}]调用结束", dsName, datasetName); + return resultList; + } + + public List> orderPartSummary(String dsName, String datasetName, Map parameters) { + log.info("报表数据源[OrderSummaryBeanDatasource][orderPartSummary][{}][{}]调用开始", dsName, datasetName); + List> resultList = new ArrayList<>(); + + Object orderId = parameters.get(ORDER_ID_FIELD_NAME); + CommonResult> commonResult = orderPartDatasourceApi.selectPartAll(Long.parseLong(orderId.toString())); + List partGoodsRespDTOS = commonResult.getData(); + + if (CollUtil.isNotEmpty(partGoodsRespDTOS)) { + partGoodsRespDTOS.forEach(p -> { + Map resultMap = new HashMap<>(); + // 构造报表所需结构 + resultMap.put("name", p.getName()); + resultMap.put("model", p.getModel()); + resultMap.put("spec", p.getSpec()); + resultMap.put("num", p.getNum()); + resultMap.put("unit", p.getUnit()); + resultMap.put("brand", p.getBrand()); + resultMap.put(REMARK_FIELD_NAME, p.getRemark()); + resultList.add(resultMap); + }); + } + + log.info("报表数据源[OrderSummaryBeanDatasource][orderPartSummary][{}][{}]调用结束", dsName, datasetName); + return resultList; + } + + /** + * 移除尾数的0,600.000 -> 600 + * + * @param data + * @return + */ + private String stripTrailingZeros(BigDecimal data) { + if (ObjectUtil.isNotNull(data)) { + return data.stripTrailingZeros().toPlainString(); + } else { + return ""; + } + } + + /** + * 布尔值转是否 + * + * @param b + * @return + */ + private String getBooleanString(Boolean b) { + return b ? "是" : "否"; + } } diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/ureport/config/CfReportSpringbeanRegistrar.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/ureport/config/CfReportSpringbeanRegistrar.java index 4854d7d04..adf961dc1 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/ureport/config/CfReportSpringbeanRegistrar.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/framework/ureport/config/CfReportSpringbeanRegistrar.java @@ -31,21 +31,22 @@ public class CfReportSpringbeanRegistrar implements ImportBeanDefinitionRegistra Set candidates = scanner.findCandidateComponents("com.cf.imes.module.report.framework.ureport.bean"); for (BeanDefinition candidate : candidates) { - if (candidate instanceof AnnotatedBeanDefinition) { - AnnotatedBeanDefinition beanDef = (AnnotatedBeanDefinition) candidate; - Map attributes = beanDef.getMetadata().getAnnotationAttributes(CfReportSpringbeanDatasource.class.getName()); - if (attributes != null) { - // 校验注解上的value - String value = (String) attributes.get("value"); - if (!StringUtils.hasText(value)) { - throw new IllegalArgumentException("@CfReportSpringbean requires a non-empty 'value' attribute."); - } - // 校验注解上的name - String name = (String) attributes.get("name"); - if (!StringUtils.hasText(name)) { - throw new IllegalArgumentException("@CfReportSpringbean requires a non-empty 'name' attribute."); - } - BeanDefinitionBuilder builder = BeanDefinitionBuilder.genericBeanDefinition(candidate.getBeanClassName()); + AnnotatedBeanDefinition beanDef = (AnnotatedBeanDefinition) candidate; + Map attributes = beanDef.getMetadata().getAnnotationAttributes(CfReportSpringbeanDatasource.class.getName()); + if (attributes != null) { + // 校验注解上的value + String value = (String) attributes.get("value"); + if (!StringUtils.hasText(value)) { + throw new IllegalArgumentException("@CfReportSpringbean requires a non-empty 'value' attribute."); + } + // 校验注解上的name + String name = (String) attributes.get("name"); + if (!StringUtils.hasText(name)) { + throw new IllegalArgumentException("@CfReportSpringbean requires a non-empty 'name' attribute."); + } + String beanClassName = candidate.getBeanClassName(); + if (StringUtils.hasText(beanClassName)) { + BeanDefinitionBuilder builder = BeanDefinitionBuilder.genericBeanDefinition(beanClassName); registry.registerBeanDefinition(value, builder.getBeanDefinition()); } } diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/datasource/ReportDatasourceService.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/datasource/ReportDatasourceService.java index d140b9363..c2d36a457 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/datasource/ReportDatasourceService.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/datasource/ReportDatasourceService.java @@ -63,6 +63,12 @@ public interface ReportDatasourceService { */ List getBeanDatasourceList(); + /** + * 获取内置数据源列表 + * @return + */ + List getBuildinDatasources(); + /** * 获取bean方法 * diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/datasource/ReportDatasourceServiceImpl.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/datasource/ReportDatasourceServiceImpl.java index 7a02e5d22..fcd29b866 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/datasource/ReportDatasourceServiceImpl.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/datasource/ReportDatasourceServiceImpl.java @@ -1,7 +1,9 @@ package com.cf.imes.module.report.service.datasource; import cn.hutool.core.annotation.AnnotationUtil; +import cn.hutool.core.collection.CollUtil; import cn.hutool.core.util.ObjectUtil; +import com.baomidou.mybatisplus.core.toolkit.sql.SqlInjectionUtils; import com.bstek.ureport.definition.dataset.Field; import com.bstek.ureport.definition.dataset.Parameter; import com.bstek.ureport.definition.dataset.SqlDatasetDefinition; @@ -9,15 +11,23 @@ import com.bstek.ureport.utils.ProcedureUtils; import com.cf.imes.framework.common.exception.ServiceException; import com.cf.imes.framework.common.util.object.BeanUtils; import com.cf.imes.framework.mybatis.core.query.LambdaQueryWrapperX; +import com.cf.imes.framework.organ.core.aop.OrganIgnore; +import com.cf.imes.framework.security.core.LoginUser; +import com.cf.imes.framework.security.core.util.SecurityFrameworkUtils; import com.cf.imes.module.report.controller.admin.dataset.vo.ReportDatasetFieldVO; import com.cf.imes.module.report.controller.admin.dataset.vo.ReportDatasetParameterVO; +import com.cf.imes.module.report.controller.admin.dataset.vo.ReportDatasetReqVO; import com.cf.imes.module.report.controller.admin.datasource.vo.ReportBeanDatasourceRespVO; import com.cf.imes.module.report.controller.admin.datasource.vo.ReportDatasourceReqVO; import com.cf.imes.module.report.controller.admin.datasource.vo.ReportDatasourceSaveReqVO; import com.cf.imes.module.report.controller.admin.datasource.vo.ReportDatasourceTestConnReqVO; +import com.cf.imes.module.report.dal.dataobject.dataset.ReportDatasetDO; import com.cf.imes.module.report.dal.dataobject.datasource.ReportDatasourceDO; +import com.cf.imes.module.report.dal.mysql.dataset.ReportDatasetMapper; import com.cf.imes.module.report.dal.mysql.datasource.ReportDatasourceMapper; +import com.cf.imes.module.report.enums.template.ReportTemplateTypeEnum; import com.cf.imes.module.report.framework.ureport.annotation.CfReportSpringbeanDatasource; +import com.cf.imes.module.report.service.dataset.ReportDatasetService; import com.cf.imes.module.report.util.SqlInjectionUtil; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang3.StringUtils; @@ -48,6 +58,7 @@ import static com.cf.imes.module.report.enums.ErrorCodeConstants.DATASET_GET_FIE import static com.cf.imes.module.report.enums.ErrorCodeConstants.DATASET_SQL_ILLEGAL; import static com.cf.imes.module.report.enums.ErrorCodeConstants.DATASET_SQL_INJECTION_RISK; import static com.cf.imes.module.report.enums.ErrorCodeConstants.DATASET_SQL_REQUIRED; +import static com.cf.imes.module.report.enums.ErrorCodeConstants.DATASOURCE_BUILDIN_OPERATION_PERMISSION_ERROR; import static com.cf.imes.module.report.enums.ErrorCodeConstants.DATASOURCE_NOT_EXISTS; /** @@ -63,6 +74,12 @@ public class ReportDatasourceServiceImpl implements ReportDatasourceService { @Resource private ReportDatasourceMapper datasourceMapper; + @Resource + private ReportDatasetService datasetService; + + @Resource + private ReportDatasetMapper datasetMapper; + private final ApplicationContext applicationContext; public ReportDatasourceServiceImpl(ApplicationContext applicationContext) { @@ -71,9 +88,13 @@ public class ReportDatasourceServiceImpl implements ReportDatasourceService { @Override public Long createDatasource(ReportDatasourceSaveReqVO createReqVO) { - // 插入 ReportDatasourceDO datasource = BeanUtils.toBean(createReqVO, ReportDatasourceDO.class); + // 校验内置数据源操作权限 + validateBuildinsource(datasource); + // 插入 datasourceMapper.insert(datasource); + // 解析数据集 + analyzeDataset(datasource); // 返回 return datasource.getId(); } @@ -82,9 +103,54 @@ public class ReportDatasourceServiceImpl implements ReportDatasourceService { public void updateDatasource(ReportDatasourceSaveReqVO updateReqVO) { // 校验存在 validateDatasourceExists(updateReqVO.getId()); - // 更新 ReportDatasourceDO updateObj = BeanUtils.toBean(updateReqVO, ReportDatasourceDO.class); + // 校验内置数据源操作权限 + validateBuildinsource(updateObj); + // 更新 datasourceMapper.updateById(updateObj); + // 解析数据集 + analyzeDataset(updateObj); + } + + /** + * 校验只有超管可以操作内置数据源 + */ + private void validateBuildinsource(ReportDatasourceDO datasource) { + LoginUser loginUser = SecurityFrameworkUtils.getLoginUser(); + boolean isSuperAdmin = loginUser != null && loginUser.getIsSupAdmin(); + // 非超管不能操作内置数据源 + if (ReportTemplateTypeEnum.SYSTEM.equals(datasource.getType()) && !isSuperAdmin) { + throw exception(DATASOURCE_BUILDIN_OPERATION_PERMISSION_ERROR); + } + } + + /** + * 解析数据源下的数据集 + * + * @param datasource + */ + private void analyzeDataset(ReportDatasourceDO datasource) { + List datasets = datasource.getDatasets(); + List batchInsertDataset = new ArrayList<>(); + List batchupdateDataset = new ArrayList<>(); + datasets.forEach(dataset -> { + // 更新/新增数据集 + if (ObjectUtil.isNotNull(dataset.getId())) { + batchupdateDataset.add(dataset); + } else { + dataset.setDatasourceId(datasource.getId()); + batchInsertDataset.add(dataset); + } + }); + + // 批量插入数据集 + if (CollUtil.isNotEmpty(batchInsertDataset)) { + datasetMapper.insertBatch(batchInsertDataset); + } + // 批量更新数据集 + if (CollUtil.isNotEmpty(batchupdateDataset)) { + datasetMapper.updateBatch(batchupdateDataset); + } } @Override @@ -108,7 +174,10 @@ public class ReportDatasourceServiceImpl implements ReportDatasourceService { @Override public ReportDatasourceDO getDatasource(Long id) { - return datasourceMapper.selectById(id); + ReportDatasourceDO reportDatasourceDO = datasourceMapper.selectById(id); + // 查询数据集 + queryDatasetInSource(reportDatasourceDO); + return reportDatasourceDO; } @Override @@ -116,8 +185,14 @@ public class ReportDatasourceServiceImpl implements ReportDatasourceService { List reportDatasourceDOS = datasourceMapper.selectList(new LambdaQueryWrapperX() .eqIfPresent(ReportDatasourceDO::getTemplateId, reqVO.getTemplateId()) .likeIfPresent(ReportDatasourceDO::getName, reqVO.getName()) - .eqIfPresent(ReportDatasourceDO::getType, reqVO.getType()) + .eqIfPresent(ReportDatasourceDO::getDsType, reqVO.getType()) .orderByDesc(ReportDatasourceDO::getCreateTime)); + // 查询数据集 + if (CollUtil.isNotEmpty(reportDatasourceDOS)) { + reportDatasourceDOS.forEach(reportDatasourceDO -> { + queryDatasetInSource(reportDatasourceDO); + }); + } return reportDatasourceDOS; } @@ -135,6 +210,21 @@ public class ReportDatasourceServiceImpl implements ReportDatasourceService { return beanDatasourceRespVOList; } + @Override + @OrganIgnore + public List getBuildinDatasources() { + List reportDatasourceDOS = datasourceMapper.selectList(new LambdaQueryWrapperX() + .eqIfPresent(ReportDatasourceDO::getType, ReportTemplateTypeEnum.SYSTEM) + .orderByDesc(ReportDatasourceDO::getCreateTime)); + // 查询数据集 + if (CollUtil.isNotEmpty(reportDatasourceDOS)) { + reportDatasourceDOS.forEach(reportDatasourceDO -> { + queryDatasetInSource(reportDatasourceDO); + }); + } + return reportDatasourceDOS; + } + @Override public List loadBeanMethods(String beanId) { Object obj = applicationContext.getBean(beanId); @@ -222,13 +312,14 @@ public class ReportDatasourceServiceImpl implements ReportDatasourceService { } // 获取数据库连接 conn = buildConn(reqVO); - // 校验sql + // 自定义工具校验sql if (SqlInjectionUtil.checkEditSql(sql)) { throw exception(DATASET_SQL_ILLEGAL); } // 检查参数sql注入 for (ReportDatasetParameterVO parameterVO : parameters) { - if (SqlInjectionUtil.checkParam(parameterVO.getDefaultValue())) { + // mybatis-plus util检查参数 + if (SqlInjectionUtils.check(parameterVO.getDefaultValue())) { throw exception(DATASET_SQL_INJECTION_RISK); } } @@ -292,4 +383,17 @@ public class ReportDatasourceServiceImpl implements ReportDatasourceService { } return conn; } + + /** + * 查询数据源下的数据集 + * + * @param reportDatasourceDO + */ + private void queryDatasetInSource(ReportDatasourceDO reportDatasourceDO) { + if (ObjectUtil.isNotNull(reportDatasourceDO)) { + // 查询数据集 + List datasetList = datasetService.getDatasetList(ReportDatasetReqVO.builder().datasourceId(reportDatasourceDO.getId()).build()); + reportDatasourceDO.setDatasets(datasetList); + } + } } diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/template/ReportTemplateServiceImpl.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/template/ReportTemplateServiceImpl.java index 442db1210..4fdf56258 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/template/ReportTemplateServiceImpl.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/service/template/ReportTemplateServiceImpl.java @@ -217,8 +217,8 @@ public class ReportTemplateServiceImpl implements ReportTemplateService { // 查询数据集 List datasetList = datasetService.getDatasetList(ReportDatasetReqVO.builder().datasourceId(ds.getId()).build()); List datasetDefinitions = new ArrayList<>(); - switch (ds.getType()) { - case JDBC, BUILDIN -> { + switch (ds.getDsType()) { + case JDBC -> { // 转换对应的ureport对象 JdbcDatasourceDefinition jdbcDatasourceDefinition = BeanUtils.toBean(ds, JdbcDatasourceDefinition.class); datasetDefinitions.addAll(BeanUtils.toBean(datasetList, SqlDatasetDefinition.class)); diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/util/SqlInjectionUtil.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/util/SqlInjectionUtil.java index 16326337b..9cd347341 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/util/SqlInjectionUtil.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/util/SqlInjectionUtil.java @@ -16,12 +16,6 @@ public class SqlInjectionUtil { private static final Pattern SQL_EDIT_PATTERN = Pattern.compile("(insert|delete|update|create|drop|truncate|grant|alter|deny|revoke|call|execute|exec|declare|show|rename|set)" + "\\s+.*(into|from|set|where|table|database|view|index|on|cursor|procedure|trigger|for|password|union|and|or)", Pattern.CASE_INSENSITIVE); - /** - * SQL语法检查正则:符合两个关键字(有先后顺序)才算匹配 - */ - private static final Pattern SQL_SYNTAX_PATTERN = Pattern.compile("(insert|delete|update|select|create|drop|truncate|grant|alter|deny|revoke|call|execute|exec|declare|show|rename|set)" + - "\\s+.*(into|from|set|where|table|database|view|index|on|cursor|procedure|trigger|for|password|union|and|or)|(select\\s*\\*\\s*from\\s+)|(and|or)\\s+.*(like|=|>|<|in|between|is|not|exists)", Pattern.CASE_INSENSITIVE); - /** * 使用'、;或注释截断SQL检查正则 */ @@ -38,26 +32,6 @@ public class SqlInjectionUtil { return SQL_COMMENT_PATTERN.matcher(sql).find() || SQL_EDIT_PATTERN.matcher(sql).find(); } - /** - * 检查参数是否存在 SQL 注入 - * - * @param value 检查参数 - * @return true 非法 false 合法 - */ - public static boolean checkParam(String value) { - Objects.requireNonNull(value); - // 处理是否包含SQL注释字符 || 检查是否包含SQL注入敏感字符 - return SQL_COMMENT_PATTERN.matcher(value).find() || SQL_SYNTAX_PATTERN.matcher(value).find(); - } - - /** - * 刪除字段转义符单引号双引号 - * - * @param text 待处理字段 - * @return - */ - public static String removeEscapeCharacter(String text) { - Objects.nonNull(text); - return text.replace("\"", "").replace("'", ""); + private SqlInjectionUtil() { } } diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/datasource/ReportDatasourceTypeInEnum.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/datasource/ReportDatasourceTypeInEnum.java index c3af82df2..c9036826c 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/datasource/ReportDatasourceTypeInEnum.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/datasource/ReportDatasourceTypeInEnum.java @@ -28,10 +28,9 @@ import java.lang.annotation.Target; validatedBy = {ReportDatasourceTypeInEnumValidator.class} ) public @interface ReportDatasourceTypeInEnum { - String message() default "数据源类型[type]错误,请检查是否jdbc/buildin/spring"; + String message() default "数据源类型[dsType]错误,请检查是否jdbc/spring"; Class[] groups() default {}; Class[] payload() default {}; - } diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/datasource/ReportDatasourceTypeInEnumValidator.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/datasource/ReportDatasourceTypeInEnumValidator.java index 76d858956..cc6c291d9 100644 --- a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/datasource/ReportDatasourceTypeInEnumValidator.java +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/datasource/ReportDatasourceTypeInEnumValidator.java @@ -2,7 +2,6 @@ package com.cf.imes.module.report.validation.datasource; import cn.hutool.core.util.ObjectUtil; import com.cf.imes.module.report.enums.datasource.ReportDatasourceTypeEnum; -import org.apache.commons.lang3.StringUtils; import javax.validation.ConstraintValidator; import javax.validation.ConstraintValidatorContext; @@ -22,15 +21,11 @@ public class ReportDatasourceTypeInEnumValidator implements ConstraintValidator< @Override public boolean isValid(String value, ConstraintValidatorContext context) { - if (StringUtils.isEmpty(value)) { + ReportDatasourceTypeEnum byType = ReportDatasourceTypeEnum.fromDesc(value); + if (ObjectUtil.isNotNull(byType)) { return true; } else { - ReportDatasourceTypeEnum byType = ReportDatasourceTypeEnum.fromDesc(value); - if (ObjectUtil.isNotNull(byType)) { - return true; - } else { - return false; - } + return false; } } diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/template/ReportTemplateTypeInEnum.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/template/ReportTemplateTypeInEnum.java new file mode 100644 index 000000000..1e2ae091d --- /dev/null +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/template/ReportTemplateTypeInEnum.java @@ -0,0 +1,36 @@ +package com.cf.imes.module.report.validation.template; + +import javax.validation.Constraint; +import javax.validation.Payload; +import java.lang.annotation.Documented; +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +/** + * 自定义报表模板类型入参校验注解 + * + * @author Gqr + * @since 2024/7/17 9:33 + */ +@Target({ + ElementType.METHOD, + ElementType.FIELD, + ElementType.ANNOTATION_TYPE, + ElementType.CONSTRUCTOR, + ElementType.PARAMETER, + ElementType.TYPE_USE +}) +@Retention(RetentionPolicy.RUNTIME) +@Documented +@Constraint( + validatedBy = {ReportTemplateTypeInEnumValidator.class} +) +public @interface ReportTemplateTypeInEnum { + String message() default "类型[type]错误,请检查是否0(内置)/1(自定义)"; + + Class[] groups() default {}; + + Class[] payload() default {}; +} diff --git a/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/template/ReportTemplateTypeInEnumValidator.java b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/template/ReportTemplateTypeInEnumValidator.java new file mode 100644 index 000000000..880ab32c1 --- /dev/null +++ b/cf-module-report/cf-module-report-biz/src/main/java/com/cf/imes/module/report/validation/template/ReportTemplateTypeInEnumValidator.java @@ -0,0 +1,33 @@ +package com.cf.imes.module.report.validation.template; + +import cn.hutool.core.util.ObjectUtil; +import com.cf.imes.module.report.enums.template.ReportTemplateTypeEnum; + +import javax.validation.ConstraintValidator; +import javax.validation.ConstraintValidatorContext; + +/** + * 自定义报表模板类型入参校验器 + * + * @author Gqr + * @since 2024/7/17 9:33 + */ +public class ReportTemplateTypeInEnumValidator implements ConstraintValidator { + + @Override + public void initialize(ReportTemplateTypeInEnum constraintAnnotation) { + ConstraintValidator.super.initialize(constraintAnnotation); + } + + @Override + public boolean isValid(Integer value, ConstraintValidatorContext context) { + ReportTemplateTypeEnum byType = ReportTemplateTypeEnum.fromType(value); + if (ObjectUtil.isNotNull(byType)) { + return true; + } else { + return false; + } + } + +} + diff --git a/cf-module-report/cf-module-report-biz/src/main/resources/application.yaml b/cf-module-report/cf-module-report-biz/src/main/resources/application.yaml index dc0ab6599..2486af452 100644 --- a/cf-module-report/cf-module-report-biz/src/main/resources/application.yaml +++ b/cf-module-report/cf-module-report-biz/src/main/resources/application.yaml @@ -84,6 +84,8 @@ jeecg: --- #################### 晨丰相关配置 #################### chenfeng: + dynamicDataSource: + enabled: true info: version: 1.0.0 base-package: com.cf.imes.module.report diff --git a/cf-module-report/cf-module-report-biz/src/main/resources/lib/ureport-core-2.3.0-SNAPSHOT.jar b/cf-module-report/cf-module-report-biz/src/main/resources/lib/ureport-core-2.3.0-SNAPSHOT.jar index e3b1628bb..88c8279ef 100644 Binary files a/cf-module-report/cf-module-report-biz/src/main/resources/lib/ureport-core-2.3.0-SNAPSHOT.jar and b/cf-module-report/cf-module-report-biz/src/main/resources/lib/ureport-core-2.3.0-SNAPSHOT.jar differ diff --git a/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportCommonServiceImplTest.java b/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportCommonServiceImplTest.java index af4954b58..9901e4668 100644 --- a/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportCommonServiceImplTest.java +++ b/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportCommonServiceImplTest.java @@ -42,7 +42,8 @@ public abstract class ReportCommonServiceImplTest { .id(id) .name("单元测试数据源") .templateId(reportId) - .type(ReportDatasourceTypeEnum.SPRING.getDesc()) + .dsType(ReportDatasourceTypeEnum.SPRING.getDesc()) + .type(ReportTemplateTypeEnum.SYSTEM.getType()) .driver("com.mysql.cj.jdbc.Driver") .url("jdbc:mysql://192.168.1.205:3307/imes_base?allowMultiQueries=true&useUnicode=true&useSSL=false&characterEncoding=UTF-8&serverTimezone=Asia/Shanghai&autoReconnect=true&nullCatalogMeansCurrent=true") .username("root") diff --git a/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportDatasetServiceImplTest.java b/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportDatasetServiceImplTest.java index 336d2ccf9..060a06a64 100644 --- a/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportDatasetServiceImplTest.java +++ b/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportDatasetServiceImplTest.java @@ -88,7 +88,7 @@ public class ReportDatasetServiceImplTest extends ReportCommonServiceImplTest{ List datasetList = reportDatasetService.getDatasetList(reqVO); assertNotNull(datasetList); - assertNotEquals(datasetList.size(), 0); + assertNotEquals(0, datasetList.size()); // 删除 reportTemplateService.deleteReportTemplate(templateId); diff --git a/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportDatasourceServiceImplTest.java b/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportDatasourceServiceImplTest.java index c9148c430..3301cab06 100644 --- a/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportDatasourceServiceImplTest.java +++ b/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportDatasourceServiceImplTest.java @@ -73,7 +73,7 @@ public class ReportDatasourceServiceImplTest extends ReportCommonServiceImplTest List templateDatasourceList = reportDatasourceService.getTemplateDatasourceList(reqVO); assertNotNull(templateDatasourceList); - assertNotEquals(templateDatasourceList.size(),0); + assertNotEquals(0, templateDatasourceList.size()); // 删除 reportTemplateService.deleteReportTemplate(templateId); diff --git a/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportTemplateServiceImplTest.java b/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportTemplateServiceImplTest.java index 1608507d1..2fc4a5da7 100644 --- a/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportTemplateServiceImplTest.java +++ b/cf-module-report/cf-module-report-biz/src/test/java/com/cf/imes/module/report/service/template/ReportTemplateServiceImplTest.java @@ -44,7 +44,7 @@ public class ReportTemplateServiceImplTest extends ReportCommonServiceImplTest { String templateUnZip = template.getContent(); System.out.println("从库中读取template大小:" + templateUnZip.length()); // 校验解压内容是否正确 - assertEquals(JsonUtil.unzipString(templateUnZip),TEMPLATE); + assertEquals(TEMPLATE, JsonUtil.unzipString(templateUnZip)); // 删除 reportTemplateService.deleteReportTemplate(templateId); } @@ -120,8 +120,8 @@ public class ReportTemplateServiceImplTest extends ReportCommonServiceImplTest { List reportTemplateList = reportTemplateService.getReportTemplateList(reqVO); assertNotNull(reportTemplateList); - assertNotEquals(reportTemplateList.size(),0); - assertEquals(reportTemplateList.get(0).getOrganId(),2L); + assertNotEquals(0, reportTemplateList.size()); + assertEquals(2L, reportTemplateList.get(0).getOrganId()); // 删除 reportTemplateService.deleteReportTemplate(templateId); diff --git a/cf-module-system/cf-module-system-api/src/main/java/com/cf/imes/module/system/api/permission/PermissionApi.java b/cf-module-system/cf-module-system-api/src/main/java/com/cf/imes/module/system/api/permission/PermissionApi.java index 501ee8825..7f2fbaae3 100644 --- a/cf-module-system/cf-module-system-api/src/main/java/com/cf/imes/module/system/api/permission/PermissionApi.java +++ b/cf-module-system/cf-module-system-api/src/main/java/com/cf/imes/module/system/api/permission/PermissionApi.java @@ -48,4 +48,17 @@ public interface PermissionApi { @Parameter(name = "userId", description = "用户编号", example = "2", required = true) CommonResult getDeptDataPermission(@RequestParam("userId") Long userId); + @GetMapping(PREFIX + "/user-role-id-list-by-user-id") + @Operation(summary = "获得拥有多个角色的用户编号集合") + @Parameter(name = "roleIds", description = "角色编号集合", example = "1,2", required = true) + CommonResult> getUserRoleIdListByUserIds(@RequestParam("userId") Long userId); + + @GetMapping(PREFIX + "/has-roles") + @Operation(summary = "判断用户是否拥有权限标识") + @Parameters({ + @Parameter(name = "userId", description = "用户编号", example = "1", required = true), + @Parameter(name = "permission", description = "权限标识", example = "2", required = true) + }) + CommonResult hasRoles(@RequestParam("userId") Long userId, + @RequestParam("permission") String permission); } diff --git a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/api/permission/PermissionApiImpl.java b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/api/permission/PermissionApiImpl.java index e4941eeab..50dd62b48 100644 --- a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/api/permission/PermissionApiImpl.java +++ b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/api/permission/PermissionApiImpl.java @@ -40,4 +40,15 @@ public class PermissionApiImpl implements PermissionApi { return success(deptDataPermission); } + @Override + public CommonResult> getUserRoleIdListByUserIds(Long userId) { + return success(permissionService.getUserPermissions(userId)); + } + + @Override + public CommonResult hasRoles(Long userId, String permission) { + Set permissions = permissionService.getUserPermissions(userId); + return success(permissions.contains(permission)); + } + } diff --git a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/permission/PermissionService.java b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/permission/PermissionService.java index a25753af1..324021b33 100644 --- a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/permission/PermissionService.java +++ b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/permission/PermissionService.java @@ -171,4 +171,14 @@ public interface PermissionService { * @return */ Set getListRoleUsers(Long roleId, Long organId); + + /** + * 获取用户权限标识 + */ + Set getUserPermissions(Long userId); + + /** + * 判断用户是否拥有相对应的权限 + */ + Boolean hasPermission(Long userId, String permission); } diff --git a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/permission/PermissionServiceImpl.java b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/permission/PermissionServiceImpl.java index 76c5947eb..a7eec5271 100644 --- a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/permission/PermissionServiceImpl.java +++ b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/permission/PermissionServiceImpl.java @@ -18,6 +18,7 @@ import com.cf.imes.module.system.api.permission.dto.DeptDataPermissionRespDTO; import com.cf.imes.module.system.constants.permission.InternalRoleConstants; import com.cf.imes.module.system.controller.admin.permission.vo.permission.PermissionAssignRoleUserReqVO; import com.cf.imes.module.system.controller.admin.permission.vo.permission.PermissionAssignUserRoleReqVO; +import com.cf.imes.module.system.convert.auth.AuthConvert; import com.cf.imes.module.system.dal.dataobject.permission.MenuDO; import com.cf.imes.module.system.dal.dataobject.permission.RoleDO; import com.cf.imes.module.system.dal.dataobject.permission.RoleMenuDO; @@ -53,8 +54,10 @@ import java.util.function.Supplier; import java.util.stream.Collectors; import static com.cf.imes.framework.common.exception.util.ServiceExceptionUtil.exception; +import static com.cf.imes.framework.common.pojo.CommonResult.success; import static com.cf.imes.framework.common.util.collection.CollectionUtils.convertSet; import static com.cf.imes.framework.common.util.json.JsonUtils.toJsonString; +import static com.cf.imes.framework.security.core.util.SecurityFrameworkUtils.getLoginUserId; import static com.cf.imes.module.system.enums.ErrorCodeConstants.ROLE_ME_ERROR; /** @@ -596,4 +599,31 @@ public class PermissionServiceImpl implements PermissionService { return SpringUtil.getBean(getClass()); } + /** + * 获取用户权限标识 + */ + @Override + public Set getUserPermissions(Long userId) { + // 1.2 获得角色列表 + Set roleIds = getUserRoleIdListByUserId(getLoginUserId()); + if (CollUtil.isEmpty(roleIds)) { + return Collections.emptySet(); + } + List roles = roleService.getRoleList1(roleIds); + roles.removeIf(role -> !CommonStatusEnum.ENABLE.getStatus().equals(role.getStatus())); // 移除禁用的角色 + + // 1.3 获得菜单列表 + Set menuIds = getRoleMenuListByRoleId2(convertSet(roles, RoleDO::getId)); + List menuList = menuService.getMenuList1(menuIds); + menuList.removeIf(menu -> !CommonStatusEnum.ENABLE.getStatus().equals(menu.getStatus())); // 移除禁用的菜单 + + return convertSet(menuList, MenuDO::getPermission); + } + + @Override + public Boolean hasPermission(Long userId, String permission) { + Set permissions = getUserPermissions(userId); + return permissions.contains(permission); + } + }