diff --git a/src/main/java/cn/lihongjie/coal/common/JpaUtils.java b/src/main/java/cn/lihongjie/coal/common/JpaUtils.java index 3dde3ef3..6747e864 100644 --- a/src/main/java/cn/lihongjie/coal/common/JpaUtils.java +++ b/src/main/java/cn/lihongjie/coal/common/JpaUtils.java @@ -211,6 +211,29 @@ public class JpaUtils { return (entityManager.createQuery(query)); } + public static boolean hasDuplicateInCurrentOrg( + EntityManager entityManager, + Class clazz, + String fieldName, + Object value) { + return hasDuplicate( + entityManager, + clazz, + fieldName, + value, + Ctx.currentUser().getOrganizationId(), + null); + } + + public static boolean hasDuplicateInCurrentOrg( + EntityManager entityManager, + Class clazz, + String fieldName, + Object value, + String selfId) { + return hasDuplicate(entityManager, clazz, fieldName, value, Ctx.currentUser().getOrganizationId(), selfId); + } + public static boolean hasDuplicate( EntityManager entityManager, Class clazz, diff --git a/src/main/java/cn/lihongjie/coal/orderNoRule/controller/OrderNoRuleController.java b/src/main/java/cn/lihongjie/coal/orderNoRule/controller/OrderNoRuleController.java index 000b045a..00f15ecf 100644 --- a/src/main/java/cn/lihongjie/coal/orderNoRule/controller/OrderNoRuleController.java +++ b/src/main/java/cn/lihongjie/coal/orderNoRule/controller/OrderNoRuleController.java @@ -8,6 +8,7 @@ import cn.lihongjie.coal.base.dto.R; import cn.lihongjie.coal.orderNoRule.dto.CreateOrderNoRuleDto; import cn.lihongjie.coal.orderNoRule.dto.OrderNoRuleDto; import cn.lihongjie.coal.orderNoRule.dto.UpdateOrderNoRuleDto; +import cn.lihongjie.coal.orderNoRule.dto.UpdateOrderSeqRequest; import cn.lihongjie.coal.orderNoRule.service.OrderNoRuleService; import lombok.extern.slf4j.Slf4j; @@ -63,6 +64,11 @@ public class OrderNoRuleController { return R.success(this.service.genOrderNo(request.getId())); } + @PostMapping("/updateOrderSeq") + public R updateOrderSeq(@RequestBody UpdateOrderSeqRequest request) { + return R.success(this.service.updateOrderSeq(request)); + } + @PostMapping("/previewOrderNo") public R previewOrderNo(@RequestBody OrderNoRuleDto request) { diff --git a/src/main/java/cn/lihongjie/coal/orderNoRule/dto/CreateOrderNoRuleDto.java b/src/main/java/cn/lihongjie/coal/orderNoRule/dto/CreateOrderNoRuleDto.java index 94740278..d9285638 100644 --- a/src/main/java/cn/lihongjie/coal/orderNoRule/dto/CreateOrderNoRuleDto.java +++ b/src/main/java/cn/lihongjie/coal/orderNoRule/dto/CreateOrderNoRuleDto.java @@ -4,8 +4,14 @@ import cn.lihongjie.coal.base.dto.OrgCommonDto; import lombok.Data; +import org.hibernate.annotations.Comment; + @Data public class CreateOrderNoRuleDto extends OrgCommonDto { private String ruleTemplate; + + + @Comment("初始序列号") + private Integer initValue; } diff --git a/src/main/java/cn/lihongjie/coal/orderNoRule/dto/OrderNoRuleDto.java b/src/main/java/cn/lihongjie/coal/orderNoRule/dto/OrderNoRuleDto.java index 603fc3b9..14334beb 100644 --- a/src/main/java/cn/lihongjie/coal/orderNoRule/dto/OrderNoRuleDto.java +++ b/src/main/java/cn/lihongjie/coal/orderNoRule/dto/OrderNoRuleDto.java @@ -4,8 +4,14 @@ import cn.lihongjie.coal.base.dto.OrgCommonDto; import lombok.Data; +import org.hibernate.annotations.Comment; + @Data public class OrderNoRuleDto extends OrgCommonDto { private String ruleTemplate; + + + @Comment("初始序列号") + private Integer initValue; } diff --git a/src/main/java/cn/lihongjie/coal/orderNoRule/dto/UpdateOrderNoRuleDto.java b/src/main/java/cn/lihongjie/coal/orderNoRule/dto/UpdateOrderNoRuleDto.java index 8e9bda45..2a0bf7f4 100644 --- a/src/main/java/cn/lihongjie/coal/orderNoRule/dto/UpdateOrderNoRuleDto.java +++ b/src/main/java/cn/lihongjie/coal/orderNoRule/dto/UpdateOrderNoRuleDto.java @@ -4,8 +4,15 @@ import cn.lihongjie.coal.base.dto.OrgCommonDto; import lombok.Data; +import org.hibernate.annotations.Comment; + @Data public class UpdateOrderNoRuleDto extends OrgCommonDto { private String ruleTemplate; + + + + @Comment("初始序列号") + private Integer initValue; } diff --git a/src/main/java/cn/lihongjie/coal/orderNoRule/dto/UpdateOrderSeqRequest.java b/src/main/java/cn/lihongjie/coal/orderNoRule/dto/UpdateOrderSeqRequest.java new file mode 100644 index 00000000..a587eb48 --- /dev/null +++ b/src/main/java/cn/lihongjie/coal/orderNoRule/dto/UpdateOrderSeqRequest.java @@ -0,0 +1,11 @@ +package cn.lihongjie.coal.orderNoRule.dto; + +import lombok.Data; + +import java.util.*; + +@Data +public class UpdateOrderSeqRequest { + private String id; + private Long newSeq; +} diff --git a/src/main/java/cn/lihongjie/coal/orderNoRule/entity/OrderNoRuleEntity.java b/src/main/java/cn/lihongjie/coal/orderNoRule/entity/OrderNoRuleEntity.java index 1babf6b0..5e371b14 100644 --- a/src/main/java/cn/lihongjie/coal/orderNoRule/entity/OrderNoRuleEntity.java +++ b/src/main/java/cn/lihongjie/coal/orderNoRule/entity/OrderNoRuleEntity.java @@ -7,6 +7,8 @@ import jakarta.persistence.Table; import lombok.Data; +import org.hibernate.annotations.Comment; + @Data @Entity @Table( @@ -20,6 +22,9 @@ public class OrderNoRuleEntity extends OrgCommonEntity { + @Comment("初始序列号") + private Integer initValue; + diff --git a/src/main/java/cn/lihongjie/coal/orderNoRule/service/OrderNoGenService.java b/src/main/java/cn/lihongjie/coal/orderNoRule/service/OrderNoGenService.java index b9d64948..9028bbb2 100644 --- a/src/main/java/cn/lihongjie/coal/orderNoRule/service/OrderNoGenService.java +++ b/src/main/java/cn/lihongjie/coal/orderNoRule/service/OrderNoGenService.java @@ -74,6 +74,40 @@ public class OrderNoGenService { context); } + + public @NotNull void updateSeq(String ruleCode, String orgId, String ruleTemplate, Long newSeq) { + + RuleTemplateUtils.ResolveContext context = new RuleTemplateUtils.ResolveContext(); + context.setDateTime(LocalDateTime.now()); + RuleTemplateUtils.genNo( + ruleTemplate, + RuleTemplateUtils.CompositePlaceholderResolver.of( + new RuleTemplateUtils.PlaceholderResolver() { + @Override + public Boolean support(String placeholder) { + return placeholder.startsWith("seq:"); + } + + @Override + public String resolve( + String placeholder, RuleTemplateUtils.ResolveContext context) { + + String current = context.get("current").toString(); + + String key = orgId + ":" + ruleCode + ":" + current; + + redissonClient.getAtomicLong(key).set(newSeq); + + return String.format("%0" + placeholder.substring(4) + "d", newSeq); + + + } + }, + RuleTemplateUtils.DatePlaceholderResolver.INSTANCE, + RuleTemplateUtils.RandomPlaceholderResolver.INSTANCE), + context); + } + private @Nullable OrderNoRuleEntity getOrderNoRuleEntity(String ruleCode, String orgId) { List all = orderNoRuleService.findAll(new Specification() { @Override diff --git a/src/main/java/cn/lihongjie/coal/orderNoRule/service/OrderNoRuleService.java b/src/main/java/cn/lihongjie/coal/orderNoRule/service/OrderNoRuleService.java index 2f6d6e40..fbe22bb8 100644 --- a/src/main/java/cn/lihongjie/coal/orderNoRule/service/OrderNoRuleService.java +++ b/src/main/java/cn/lihongjie/coal/orderNoRule/service/OrderNoRuleService.java @@ -9,6 +9,7 @@ import cn.lihongjie.coal.exception.BizException; import cn.lihongjie.coal.orderNoRule.dto.CreateOrderNoRuleDto; import cn.lihongjie.coal.orderNoRule.dto.OrderNoRuleDto; import cn.lihongjie.coal.orderNoRule.dto.UpdateOrderNoRuleDto; +import cn.lihongjie.coal.orderNoRule.dto.UpdateOrderSeqRequest; import cn.lihongjie.coal.orderNoRule.entity.OrderNoRuleEntity; import cn.lihongjie.coal.orderNoRule.mapper.OrderNoRuleMapper; import cn.lihongjie.coal.orderNoRule.repository.OrderNoRuleRepository; @@ -121,11 +122,10 @@ public class OrderNoRuleService extends BaseService !isUUID(x.trim())) + .collect(Collectors.joining(",")); + return msg; } - - return R.fail("sysError", "系统异常: " + ex.getMessage()); - } - @ExceptionHandler(MethodArgumentNotValidException.class) - public R handleException( - MethodArgumentNotValidException ex, HttpServletRequest request, HandlerMethod handlerMethod) { - logEx(ex, request, handlerMethod); - List allError = - ex.getBindingResult().getAllErrors().stream() - .map(oe -> oe.unwrap(ConstraintViolation.class)) - .collect(Collectors.toList()); - List> errorData = - allError.stream() - .map( - x -> - Map.of( - "field", - x.getPropertyPath() == null? "null" : x.getPropertyPath().toString(), - "msg", - x.getMessage(), - - "annotation", - x.getConstraintDescriptor() - .getAnnotation() == null ? "null":x.getConstraintDescriptor() - .getAnnotation() - .annotationType() - .getName())) - .collect(Collectors.toList()); - - return R.fail("validError", errorData.stream().map(x -> x.get("msg") + "").collect(Collectors.joining(", ")), errorData); + return serverErrorMessage.getDetail(); } @ExceptionHandler(BizException.class) @@ -105,4 +91,117 @@ public class GlobalExceptionHandler { logEx(ex, request, handlerMethod); return R.fail("sysError", "系统异常: " + ex.getMessage()); } + + private static boolean isUUID(String x) { + + return x.matches( + "^[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}$"); + } + + @ExceptionHandler(InvalidDataAccessApiUsageException.class) + public R handleException( + InvalidDataAccessApiUsageException ex, + HttpServletRequest request, + HandlerMethod handlerMethod) { + logEx(ex, request, handlerMethod); + + Pattern pattern = Pattern.compile("\\[(.+?)\\]"); + + Matcher matcher = pattern.matcher(ex.getMessage()); + + if (matcher.find()) { + return R.fail("fieldNotExist", "字段不存在: " + matcher.group(1)); + } + + return R.fail("sysError", "系统异常: " + ex.getMessage()); + } + + @ExceptionHandler(MethodArgumentNotValidException.class) + public R handleException( + MethodArgumentNotValidException ex, + HttpServletRequest request, + HandlerMethod handlerMethod) { + logEx(ex, request, handlerMethod); + List allError = + ex.getBindingResult().getAllErrors().stream() + .map(oe -> oe.unwrap(ConstraintViolation.class)) + .collect(Collectors.toList()); + List> errorData = + allError.stream() + .map( + x -> + Map.of( + "field", + x.getPropertyPath() == null + ? "null" + : x.getPropertyPath().toString(), + "msg", + x.getMessage(), + "annotation", + x.getConstraintDescriptor().getAnnotation() == null + ? "null" + : x.getConstraintDescriptor() + .getAnnotation() + .annotationType() + .getName())) + .collect(Collectors.toList()); + + return R.fail( + "validError", + errorData.stream().map(x -> x.get("msg") + "").collect(Collectors.joining(", ")), + errorData); + } + + @ExceptionHandler(DataIntegrityViolationException.class) + public R handleException( + DataIntegrityViolationException ex, + HttpServletRequest request, + HandlerMethod handlerMethod) { + logEx(ex, request, handlerMethod); + + Throwable root = ex.getRootCause(); + + if (root instanceof PSQLException psqlException) { + ServerErrorMessage serverErrorMessage = psqlException.getServerErrorMessage(); + + String routine = serverErrorMessage.getRoutine(); + + switch (routine) { + case "_bt_check_unique" -> { + return R.fail( + "uniqueViolation", "数据重复: " + getDuplicateMsg(serverErrorMessage)); + } + + case "ExecConstraints" -> { + if (serverErrorMessage.getMessage().contains("not-null constraint")) { + + // get table name and column name from message null value in column "code" + // of relation "t_warehouse_goods" violates not-null constraint' + + String message = serverErrorMessage.getMessage(); + + Pattern pattern = + Pattern.compile( + "null value in column \"(.+?)\" of relation \"(.+?)\" violates not-null constraint"); + + Matcher matcher = pattern.matcher(message); + + if (matcher.find()) { + + String col = matcher.group(1); + String table = matcher.group(2); + + return R.fail("notNullViolation", "数据项不能为空: " + col); + } + + return R.fail("notNullViolation", "数据项不能为空"); + } + } + } + + return R.fail("dataIntegrityViolation", "数据完整性异常: " + serverErrorMessage); + } + + return R.fail("sysError", "系统异常: " + ex.getMessage()); + } } diff --git a/src/main/java/cn/lihongjie/coal/warehouseGoods/entity/WarehouseGoodsEntity.java b/src/main/java/cn/lihongjie/coal/warehouseGoods/entity/WarehouseGoodsEntity.java index 9549c247..a28c8c28 100644 --- a/src/main/java/cn/lihongjie/coal/warehouseGoods/entity/WarehouseGoodsEntity.java +++ b/src/main/java/cn/lihongjie/coal/warehouseGoods/entity/WarehouseGoodsEntity.java @@ -8,6 +8,7 @@ import cn.lihongjie.coal.warehouseGoodsUnit.entity.WarehouseGoodsUnitEntity; import cn.lihongjie.coal.warehouseShelve.entity.WarehouseShelveEntity; import cn.lihongjie.coal.warehouseSupplier.entity.WarehouseSupplierEntity; +import jakarta.persistence.Column; import jakarta.persistence.Entity; import jakarta.persistence.ManyToOne; @@ -17,11 +18,21 @@ import org.hibernate.annotations.Comment; @Data @Entity +@jakarta.persistence.Table( + indexes = { + @jakarta.persistence.Index( + name = "idx_warehouse_goods_org_id", + columnList = "organization_id"), -@jakarta.persistence.Table(indexes = @jakarta.persistence.Index(name ="idx_warehouse_goods_org_id", columnList = "organization_id")) - + @jakarta.persistence.Index( + name = "idx_warehouse_goods_code", + columnList = "code, organization_id", + unique = true) + }) public class WarehouseGoodsEntity extends OrgCommonEntity { + @Column(nullable = false) + private String code; @ManyToOne private WarehouseGoodsCategoryEntity category; diff --git a/src/main/java/cn/lihongjie/coal/warehouseGoodsBrand/entity/WarehouseGoodsBrandEntity.java b/src/main/java/cn/lihongjie/coal/warehouseGoodsBrand/entity/WarehouseGoodsBrandEntity.java index e0c81dc4..da96538c 100644 --- a/src/main/java/cn/lihongjie/coal/warehouseGoodsBrand/entity/WarehouseGoodsBrandEntity.java +++ b/src/main/java/cn/lihongjie/coal/warehouseGoodsBrand/entity/WarehouseGoodsBrandEntity.java @@ -8,7 +8,14 @@ import lombok.Data; @Data @Entity - -@jakarta.persistence.Table(indexes = @jakarta.persistence.Index(name ="idx_warehouse_goods_brand_org_id", columnList = "organization_id")) - -public class WarehouseGoodsBrandEntity extends OrgCommonEntity {} \ No newline at end of file +@jakarta.persistence.Table( + indexes = { + @jakarta.persistence.Index( + name = "idx_warehouse_goods_brand_org_id", + columnList = "organization_id"), + @jakarta.persistence.Index( + name = "idx_warehouse_goods_brand_name", + columnList = "name, organization_id", + unique = true) + }) +public class WarehouseGoodsBrandEntity extends OrgCommonEntity {} diff --git a/src/main/java/cn/lihongjie/coal/warehouseGoodsUnit/entity/WarehouseGoodsUnitEntity.java b/src/main/java/cn/lihongjie/coal/warehouseGoodsUnit/entity/WarehouseGoodsUnitEntity.java index fde2dcd3..d2bd62f9 100644 --- a/src/main/java/cn/lihongjie/coal/warehouseGoodsUnit/entity/WarehouseGoodsUnitEntity.java +++ b/src/main/java/cn/lihongjie/coal/warehouseGoodsUnit/entity/WarehouseGoodsUnitEntity.java @@ -8,7 +8,14 @@ import lombok.Data; @Data @Entity - -@jakarta.persistence.Table(indexes = @jakarta.persistence.Index(name ="idx_warehouse_goods_unit_org_id", columnList = "organization_id")) - -public class WarehouseGoodsUnitEntity extends OrgCommonEntity {} \ No newline at end of file +@jakarta.persistence.Table( + indexes = { + @jakarta.persistence.Index( + name = "idx_warehouse_goods_unit_org_id", + columnList = "organization_id") + , + @jakarta.persistence.Index( + name = "idx_warehouse_goods_unit_name", + columnList = "name, organization_id", unique = true) + }) +public class WarehouseGoodsUnitEntity extends OrgCommonEntity {} diff --git a/src/main/java/cn/lihongjie/coal/warehouseReceipt/entity/WarehouseReceiptEntity.java b/src/main/java/cn/lihongjie/coal/warehouseReceipt/entity/WarehouseReceiptEntity.java index a7662740..fc3b9bda 100644 --- a/src/main/java/cn/lihongjie/coal/warehouseReceipt/entity/WarehouseReceiptEntity.java +++ b/src/main/java/cn/lihongjie/coal/warehouseReceipt/entity/WarehouseReceiptEntity.java @@ -17,11 +17,15 @@ import java.util.List; @Data() @Entity @jakarta.persistence.Table( - indexes = - @jakarta.persistence.Index( - name = "idx_warehouse_receipt_org_id", - columnList = "organization_id")) - + indexes = { + @jakarta.persistence.Index( + name = "idx_warehouse_receipt_org_id", + columnList = "organization_id"), + @jakarta.persistence.Index( + name = "idx_warehouse_receipt_receipt_no", + columnList = "receipt_no, organization_id", + unique = true) + }) @EqualsAndHashCode(exclude = {"detail", "parent"}) public class WarehouseReceiptEntity extends OrgCommonEntity { @@ -38,6 +42,7 @@ public class WarehouseReceiptEntity extends OrgCommonEntity { // private String receiptTypeName; @Comment("单据编号") + @Column(nullable = false) private String receiptNo; @Comment("事由") @@ -58,7 +63,6 @@ public class WarehouseReceiptEntity extends OrgCommonEntity { @OneToMany(mappedBy = "receipt", cascade = CascadeType.REMOVE) private List detail; - private Double amount; private Double number; @@ -71,21 +75,14 @@ public class WarehouseReceiptEntity extends OrgCommonEntity { @ManyToOne(cascade = CascadeType.REMOVE) private WarehouseReceiptEntity receipt1; - - @ManyToOne - private WarehouseReceiptEntity parent; - - + @ManyToOne private WarehouseReceiptEntity parent; @Comment("制单人") private String creator; - - private String location; + @Comment("归档状态") @ColumnDefault("'0'") private String archiveStatus = "0"; - - }