Merge branch 'develop' of https://gitee.com/aberizofur/ruoyi-vue-pro into develop
This commit is contained in:
commit
9819e05d4e
|
@ -0,0 +1,55 @@
|
|||
|
||||
-- ----------------------------
|
||||
-- Table structure for crm_business_product
|
||||
-- ----------------------------
|
||||
DROP TABLE IF EXISTS `crm_business_product`;
|
||||
CREATE TABLE `crm_business_product` (
|
||||
`id` bigint(0) NOT NULL AUTO_INCREMENT COMMENT '主键',
|
||||
`business_id` bigint(0) NOT NULL COMMENT '商机ID',
|
||||
`product_id` bigint(0) NOT NULL COMMENT '产品ID',
|
||||
`price` decimal(18, 2) NOT NULL COMMENT '产品单价',
|
||||
`sales_price` decimal(18, 2) NULL DEFAULT NULL COMMENT '销售价格',
|
||||
`num` int(0) NULL DEFAULT NULL COMMENT '数量',
|
||||
`discount` decimal(10, 2) NULL DEFAULT NULL COMMENT '折扣',
|
||||
`subtotal` decimal(18, 2) NULL DEFAULT NULL COMMENT '小计(折扣后价格)',
|
||||
`unit` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT '' COMMENT '单位',
|
||||
`creator` varchar(64) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NULL DEFAULT '' COMMENT '创建者',
|
||||
`create_time` datetime(0) NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
|
||||
`updater` varchar(64) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NULL DEFAULT '' COMMENT '更新者',
|
||||
`update_time` datetime(0) NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP(0) COMMENT '更新时间',
|
||||
`deleted` bit(1) NOT NULL DEFAULT b'0' COMMENT '是否删除',
|
||||
`tenant_id` bigint(0) NOT NULL DEFAULT 1 COMMENT '租户编号',
|
||||
PRIMARY KEY (`id`) USING BTREE
|
||||
) ENGINE = InnoDB AUTO_INCREMENT = 29 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_unicode_ci COMMENT = '商机产品关联表' ROW_FORMAT = Dynamic;
|
||||
|
||||
-- ----------------------------
|
||||
-- Table structure for crm_business_status
|
||||
-- ----------------------------
|
||||
DROP TABLE IF EXISTS `crm_business_status`;
|
||||
CREATE TABLE `crm_business_status` (
|
||||
`id` bigint(0) NOT NULL AUTO_INCREMENT COMMENT '主键ID',
|
||||
`type_id` bigint(0) NOT NULL COMMENT '状态类型编号',
|
||||
`name` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '状态名',
|
||||
`percent` bigint(0) NULL DEFAULT NULL COMMENT '赢单率',
|
||||
`sort` int(0) NULL DEFAULT NULL COMMENT '排序',
|
||||
`tenant_id` bigint(0) NOT NULL DEFAULT 0 COMMENT '租户编号',
|
||||
PRIMARY KEY (`id`) USING BTREE
|
||||
) ENGINE = InnoDB AUTO_INCREMENT = 1 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_unicode_ci COMMENT = '商机状态' ROW_FORMAT = Dynamic;
|
||||
|
||||
-- ----------------------------
|
||||
-- Table structure for crm_business_status_type
|
||||
-- ----------------------------
|
||||
DROP TABLE IF EXISTS `crm_business_status_type`;
|
||||
CREATE TABLE `crm_business_status_type` (
|
||||
`id` bigint(0) NOT NULL AUTO_INCREMENT COMMENT '主键ID',
|
||||
`name` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '状态类型名',
|
||||
`dept_ids` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL COMMENT '使用的部门编号',
|
||||
`status` int(0) NOT NULL DEFAULT 1 COMMENT '开启状态',
|
||||
`creator` varchar(64) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NULL DEFAULT '' COMMENT '创建者',
|
||||
`create_time` datetime(0) NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
|
||||
`updater` varchar(64) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NULL DEFAULT '' COMMENT '更新者',
|
||||
`update_time` datetime(0) NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP(0) COMMENT '更新时间',
|
||||
`deleted` bit(1) NOT NULL DEFAULT b'0' COMMENT '是否删除',
|
||||
`tenant_id` bigint(0) NOT NULL DEFAULT 0 COMMENT '租户编号',
|
||||
PRIMARY KEY (`id`) USING BTREE
|
||||
) ENGINE = InnoDB AUTO_INCREMENT = 1 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_unicode_ci COMMENT = '商机状态类型' ROW_FORMAT = Dynamic;
|
|
@ -19,6 +19,7 @@ public interface ErrorCodeConstants {
|
|||
|
||||
// ========== 商机管理 1-020-002-000 ==========
|
||||
ErrorCode BUSINESS_NOT_EXISTS = new ErrorCode(1_020_002_000, "商机不存在");
|
||||
ErrorCode BUSINESS_CONTRACT_EXISTS = new ErrorCode(1_020_002_001, "商机已关联合同,不能删除");
|
||||
|
||||
// TODO @lilleo:商机状态、商机类型,都单独错误码段
|
||||
|
||||
|
|
|
@ -0,0 +1,52 @@
|
|||
package cn.iocoder.yudao.module.crm.enums.business;
|
||||
|
||||
import cn.hutool.core.util.ObjUtil;
|
||||
import cn.hutool.core.util.ObjectUtil;
|
||||
import cn.iocoder.yudao.framework.common.core.IntArrayValuable;
|
||||
import lombok.Getter;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
|
||||
import java.util.Arrays;
|
||||
|
||||
/**
|
||||
* @author lzxhqs
|
||||
* @version 1.0
|
||||
* @title CrmBizEndStatus
|
||||
* @description
|
||||
* @create 2024/1/12
|
||||
*/
|
||||
@RequiredArgsConstructor
|
||||
@Getter
|
||||
public enum CrmBizEndStatus implements IntArrayValuable {
|
||||
WIN(1, "赢单"),
|
||||
LOSE(2, "输单"),
|
||||
INVALID(3, "无效");
|
||||
|
||||
public static final int[] ARRAYS = Arrays.stream(values()).mapToInt(CrmBizEndStatus::getStatus).toArray();
|
||||
|
||||
public static boolean isWin(Integer status) {
|
||||
return ObjectUtil.equal(WIN.getStatus(), status);
|
||||
}
|
||||
|
||||
public static boolean isLose(Integer status) {
|
||||
return ObjectUtil.equal(LOSE.getStatus(), status);
|
||||
}
|
||||
|
||||
public static boolean isInvalid(Integer status) {
|
||||
return ObjectUtil.equal(INVALID.getStatus(), status);
|
||||
}
|
||||
|
||||
/**
|
||||
* 场景类型
|
||||
*/
|
||||
private final Integer status;
|
||||
/**
|
||||
* 场景名称
|
||||
*/
|
||||
private final String name;
|
||||
|
||||
@Override
|
||||
public int[] array() {
|
||||
return ARRAYS;
|
||||
}
|
||||
}
|
|
@ -22,6 +22,11 @@
|
|||
<artifactId>yudao-module-system-api</artifactId>
|
||||
<version>${revision}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>cn.iocoder.boot</groupId>
|
||||
<artifactId>yudao-module-system-biz</artifactId>
|
||||
<version>${revision}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>cn.iocoder.boot</groupId>
|
||||
<artifactId>yudao-module-crm-api</artifactId>
|
||||
|
|
|
@ -4,6 +4,7 @@ import cn.iocoder.yudao.framework.common.enums.CommonStatusEnum;
|
|||
import cn.iocoder.yudao.framework.common.pojo.CommonResult;
|
||||
import cn.iocoder.yudao.framework.common.pojo.PageParam;
|
||||
import cn.iocoder.yudao.framework.common.pojo.PageResult;
|
||||
import cn.iocoder.yudao.framework.common.util.collection.CollectionUtils;
|
||||
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
|
||||
import cn.iocoder.yudao.framework.excel.core.util.ExcelUtils;
|
||||
import cn.iocoder.yudao.framework.operatelog.core.annotations.OperateLog;
|
||||
|
@ -101,11 +102,12 @@ public class CrmBusinessStatusTypeController {
|
|||
PageResult<CrmBusinessStatusTypeDO> pageResult = businessStatusTypeService.getBusinessStatusTypePage(pageReqVO);
|
||||
// 处理部门回显
|
||||
// TODO @ljlleo:可以使用 CollectionUtils.convertSet 替代常用的 stream 操作,更简洁一点;下面几个也是哈;
|
||||
Set<Long> deptIds = pageResult.getList().stream()
|
||||
.map(CrmBusinessStatusTypeDO::getDeptIds)
|
||||
.filter(Objects::nonNull)
|
||||
.flatMap(Collection::stream)
|
||||
.collect(Collectors.toSet());
|
||||
// Set<Long> deptIds = pageResult.getList().stream()
|
||||
// .map(CrmBusinessStatusTypeDO::getDeptIds)
|
||||
// .filter(Objects::nonNull)
|
||||
// .flatMap(Collection::stream)
|
||||
// .collect(Collectors.toSet());
|
||||
Set<Long> deptIds = CollectionUtils.convertSetByFlatMap(pageResult.getList(), CrmBusinessStatusTypeDO::getDeptIds,Collection::stream);
|
||||
List<DeptRespDTO> deptList = deptApi.getDeptList(deptIds);
|
||||
return success(CrmBusinessStatusTypeConvert.INSTANCE.convertPage(pageResult, deptList));
|
||||
}
|
||||
|
|
|
@ -1,5 +1,8 @@
|
|||
package cn.iocoder.yudao.module.crm.controller.admin.business.vo.business;
|
||||
|
||||
import cn.iocoder.yudao.framework.common.validation.InEnum;
|
||||
import cn.iocoder.yudao.module.crm.controller.admin.business.vo.product.CrmBusinessProductSaveReqVO;
|
||||
import cn.iocoder.yudao.module.crm.enums.business.CrmBizEndStatus;
|
||||
import cn.iocoder.yudao.module.crm.framework.operatelog.core.CrmCustomerParseFunction;
|
||||
import com.mzt.logapi.starter.annotation.DiffLogField;
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
|
@ -9,6 +12,8 @@ import org.springframework.format.annotation.DateTimeFormat;
|
|||
|
||||
import java.math.BigDecimal;
|
||||
import java.time.LocalDateTime;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND;
|
||||
|
||||
|
@ -66,7 +71,17 @@ public class CrmBusinessSaveReqVO {
|
|||
@Schema(description = "备注", example = "随便")
|
||||
@DiffLogField(name = "备注")
|
||||
private String remark;
|
||||
|
||||
// TODO @ljileo:修改的时候,应该可以传递添加的产品;
|
||||
@Schema(description = "联系人编号", example = "110")
|
||||
@NotNull(message = "联系人编号不能为空")
|
||||
private Long contactId;
|
||||
|
||||
@Schema(description = "1赢单2输单3无效", example = "1")
|
||||
@InEnum(CrmBizEndStatus.class)
|
||||
private Integer endStatus;
|
||||
|
||||
@Schema(description = "商机产品列表", example = "")
|
||||
private List<CrmBusinessProductSaveReqVO> products = new ArrayList<>();
|
||||
|
||||
|
||||
}
|
||||
|
|
|
@ -0,0 +1,18 @@
|
|||
package cn.iocoder.yudao.module.crm.controller.admin.business.vo.product;
|
||||
|
||||
import cn.iocoder.yudao.framework.common.pojo.PageParam;
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.Data;
|
||||
import lombok.EqualsAndHashCode;
|
||||
import lombok.ToString;
|
||||
|
||||
|
||||
/**
|
||||
* @author lzxhqs
|
||||
*/
|
||||
@Schema(description = "管理后台 - 商机产品分页 Request VO")
|
||||
@Data
|
||||
@EqualsAndHashCode(callSuper = true)
|
||||
@ToString(callSuper = true)
|
||||
public class CrmBusinessProductPageReqVO extends PageParam {
|
||||
}
|
|
@ -0,0 +1,14 @@
|
|||
package cn.iocoder.yudao.module.crm.controller.admin.business.vo.product;
|
||||
|
||||
import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.Data;
|
||||
|
||||
/**
|
||||
* @author lzxhqs
|
||||
*/
|
||||
@Schema(description = "管理后台 - 商机产品关联 Response VO")
|
||||
@Data
|
||||
@ExcelIgnoreUnannotated
|
||||
public class CrmBusinessProductRespVO {
|
||||
}
|
|
@ -0,0 +1,50 @@
|
|||
package cn.iocoder.yudao.module.crm.controller.admin.business.vo.product;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import jakarta.validation.constraints.NotNull;
|
||||
import lombok.Data;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
|
||||
/**
|
||||
* @author lzxhqs
|
||||
*/
|
||||
@Schema(description = "管理后台 - CRM 商机产品关联表 创建/更新 Request VO")
|
||||
@Data
|
||||
public class CrmBusinessProductSaveReqVO {
|
||||
|
||||
@Schema(description = "主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "32129")
|
||||
private Long id;
|
||||
|
||||
@Schema(description = "商机ID", requiredMode = Schema.RequiredMode.REQUIRED, example = "30320")
|
||||
@NotNull(message = "商机ID不能为空")
|
||||
private Integer businessId;
|
||||
|
||||
@Schema(description = "产品ID", requiredMode = Schema.RequiredMode.REQUIRED, example = "30320")
|
||||
@NotNull(message = "产品ID不能为空")
|
||||
private Integer productId;
|
||||
|
||||
@Schema(description = "产品单价", requiredMode = Schema.RequiredMode.REQUIRED, example = "30320")
|
||||
@NotNull(message = "产品单价不能为空")
|
||||
private BigDecimal price;
|
||||
|
||||
@Schema(description = "销售价格", requiredMode = Schema.RequiredMode.REQUIRED, example = "30320")
|
||||
@NotNull(message = "销售价格不能为空")
|
||||
private BigDecimal salesPrice;
|
||||
|
||||
@Schema(description = "数量", requiredMode = Schema.RequiredMode.REQUIRED, example = "30320")
|
||||
@NotNull(message = "数量不能为空")
|
||||
private BigDecimal num;
|
||||
|
||||
@Schema(description = "折扣", requiredMode = Schema.RequiredMode.REQUIRED, example = "30320")
|
||||
@NotNull(message = "折扣不能为空")
|
||||
private BigDecimal discount;
|
||||
|
||||
@Schema(description = "小计(折扣后价格)", requiredMode = Schema.RequiredMode.REQUIRED, example = "30320")
|
||||
@NotNull(message = "小计(折扣后价格)不能为空")
|
||||
private BigDecimal subtotal;
|
||||
|
||||
@Schema(description = "单位", requiredMode = Schema.RequiredMode.REQUIRED, example = "30320")
|
||||
@NotNull(message = "单位不能为空")
|
||||
private String unit;
|
||||
}
|
|
@ -24,6 +24,6 @@ public class CrmBusinessStatusTypeSaveReqVO {
|
|||
|
||||
// TODO @ljlleo VO 里面,我们不使用默认值哈。这里 Lists.newArrayList() 看看怎么去掉。上面 deptIds 也是类似噢
|
||||
@Schema(description = "商机状态集合", requiredMode = Schema.RequiredMode.REQUIRED)
|
||||
private List<CrmBusinessStatusSaveReqVO> statusList = Lists.newArrayList();
|
||||
private List<CrmBusinessStatusSaveReqVO> statusList;
|
||||
|
||||
}
|
||||
|
|
|
@ -0,0 +1,20 @@
|
|||
package cn.iocoder.yudao.module.crm.convert.businessproduct;
|
||||
|
||||
import cn.iocoder.yudao.module.crm.controller.admin.business.vo.product.CrmBusinessProductSaveReqVO;
|
||||
import cn.iocoder.yudao.module.crm.dal.dataobject.business.CrmBusinessProductDO;
|
||||
import org.mapstruct.Mapper;
|
||||
import org.mapstruct.factory.Mappers;
|
||||
|
||||
/**
|
||||
* @author lzxhqs
|
||||
* @version 1.0
|
||||
* @title CrmBusinessProductConvert
|
||||
* @description
|
||||
* @create 2024/1/12
|
||||
*/
|
||||
@Mapper
|
||||
public interface CrmBusinessProductConvert {
|
||||
CrmBusinessProductConvert INSTANCE = Mappers.getMapper(CrmBusinessProductConvert.class);
|
||||
|
||||
CrmBusinessProductDO convert(CrmBusinessProductSaveReqVO product);
|
||||
}
|
|
@ -39,9 +39,9 @@ public interface CrmBusinessStatusTypeConvert {
|
|||
|
||||
default CrmBusinessStatusTypeRespVO convert(CrmBusinessStatusTypeDO bean, List<CrmBusinessStatusDO> statusList) {
|
||||
// TODO @ljlleo 可以链式赋值,简化成一行;
|
||||
CrmBusinessStatusTypeRespVO result = convert(bean);
|
||||
result.setStatusList(statusList);
|
||||
return result;
|
||||
// CrmBusinessStatusTypeRespVO result = convert(bean);
|
||||
// result.setStatusList(statusList);
|
||||
return convert(bean).setStatusList(statusList);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -1,6 +1,8 @@
|
|||
package cn.iocoder.yudao.module.crm.dal.dataobject.business;
|
||||
|
||||
import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
|
||||
import cn.iocoder.yudao.module.crm.dal.dataobject.customer.CrmCustomerDO;
|
||||
import cn.iocoder.yudao.module.system.dal.dataobject.user.AdminUserDO;
|
||||
import com.baomidou.mybatisplus.annotation.KeySequence;
|
||||
import com.baomidou.mybatisplus.annotation.TableId;
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
|
@ -52,6 +54,7 @@ public class CrmBusinessDO extends BaseDO {
|
|||
* 客户编号
|
||||
*
|
||||
* TODO @ljileo:这个字段,后续要写下关联的实体哈
|
||||
* 关联 {@link CrmCustomerDO#getId()}
|
||||
*/
|
||||
private Long customerId;
|
||||
/**
|
||||
|
@ -101,6 +104,7 @@ public class CrmBusinessDO extends BaseDO {
|
|||
* 负责人的用户编号
|
||||
*
|
||||
* 关联 AdminUserDO 的 id 字段
|
||||
* {@link AdminUserDO#getId()}
|
||||
*/
|
||||
private Long ownerUserId;
|
||||
|
||||
|
|
|
@ -0,0 +1,74 @@
|
|||
package cn.iocoder.yudao.module.crm.dal.dataobject.business;
|
||||
|
||||
import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
|
||||
import cn.iocoder.yudao.module.crm.dal.dataobject.product.CrmProductDO;
|
||||
import com.baomidou.mybatisplus.annotation.KeySequence;
|
||||
import com.baomidou.mybatisplus.annotation.TableId;
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import lombok.*;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
|
||||
/**
|
||||
* 商机产品关联表 DO
|
||||
*
|
||||
* @author lzxhqs
|
||||
*/
|
||||
@TableName("crm_business_product")
|
||||
@KeySequence("crm_business_product_seq") // 用于 Oracle、PostgreSQL、Kingbase、DB2、H2 数据库的主键自增。如果是 MySQL 等数据库,可不写。
|
||||
@Data
|
||||
@EqualsAndHashCode(callSuper = true)
|
||||
@ToString(callSuper = true)
|
||||
@Builder
|
||||
@NoArgsConstructor
|
||||
@AllArgsConstructor
|
||||
public class CrmBusinessProductDO extends BaseDO {
|
||||
|
||||
/**
|
||||
* 主键
|
||||
*/
|
||||
@TableId
|
||||
private Long id;
|
||||
|
||||
/**
|
||||
* 商机ID
|
||||
* 关联 {@link CrmBusinessDO#getId()}
|
||||
*/
|
||||
private Long businessId;
|
||||
|
||||
/**
|
||||
* 产品ID
|
||||
* 关联{@link CrmProductDO#getId()}
|
||||
*/
|
||||
private Long productId;
|
||||
|
||||
/**
|
||||
* 产品单价
|
||||
*/
|
||||
private BigDecimal price;
|
||||
|
||||
/**
|
||||
* 销售价格
|
||||
*/
|
||||
private BigDecimal salesPrice;
|
||||
|
||||
/**
|
||||
* 数量
|
||||
*/
|
||||
private BigDecimal num;
|
||||
|
||||
/**
|
||||
* 折扣
|
||||
*/
|
||||
private BigDecimal discount;
|
||||
|
||||
/**
|
||||
* 小计(折扣后价格)
|
||||
*/
|
||||
private BigDecimal subtotal;
|
||||
|
||||
/**
|
||||
* 单位
|
||||
*/
|
||||
private String unit;
|
||||
}
|
|
@ -39,7 +39,7 @@ public class CrmBusinessStatusDO {
|
|||
*
|
||||
* TODO 这里是不是改成 Integer 存储,百分比 * 100 ;
|
||||
*/
|
||||
private String percent;
|
||||
private Integer percent;
|
||||
/**
|
||||
* 排序
|
||||
*/
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
package cn.iocoder.yudao.module.crm.dal.dataobject.business;
|
||||
|
||||
import cn.iocoder.yudao.framework.common.enums.CommonStatusEnum;
|
||||
import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
|
||||
import cn.iocoder.yudao.framework.mybatis.core.type.LongListTypeHandler;
|
||||
import com.baomidou.mybatisplus.annotation.KeySequence;
|
||||
|
@ -43,6 +44,7 @@ public class CrmBusinessStatusTypeDO extends BaseDO {
|
|||
* 开启状态
|
||||
*
|
||||
* TODO 改成 Integer,关联 CommonStatus
|
||||
* {@link CommonStatusEnum}
|
||||
*/
|
||||
private Boolean status;
|
||||
|
||||
|
|
|
@ -0,0 +1,21 @@
|
|||
package cn.iocoder.yudao.module.crm.dal.mysql.business;
|
||||
|
||||
|
||||
import cn.iocoder.yudao.framework.mybatis.core.mapper.BaseMapperX;
|
||||
import cn.iocoder.yudao.module.crm.dal.dataobject.business.CrmBusinessProductDO;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
|
||||
/**
|
||||
* 商机产品 Mapper
|
||||
* @author lzxhqs
|
||||
*/
|
||||
@Mapper
|
||||
public interface CrmBusinessProductMapper extends BaseMapperX<CrmBusinessProductDO> {
|
||||
default void deleteByBusinessId(Long id) {
|
||||
delete(CrmBusinessProductDO::getBusinessId, id);
|
||||
}
|
||||
|
||||
default CrmBusinessProductDO selectByBusinessId(Long id) {
|
||||
return selectOne(CrmBusinessProductDO::getBusinessId, id);
|
||||
}
|
||||
}
|
|
@ -28,4 +28,15 @@ public interface CrmBusinessStatusTypeMapper extends BaseMapperX<CrmBusinessStat
|
|||
.eqIfPresent(CrmBusinessStatusTypeDO::getStatus, queryVO.getStatus())
|
||||
.inIfPresent(CrmBusinessStatusTypeDO::getId, queryVO.getIdList()));
|
||||
}
|
||||
|
||||
/**
|
||||
* 根据ID和name查询
|
||||
*
|
||||
* @param id 商机状态类型id
|
||||
* @param name 状态类型名
|
||||
* @return result
|
||||
*/
|
||||
default CrmBusinessStatusTypeDO selectByIdAndName(Long id, String name) {
|
||||
return selectOne(CrmBusinessStatusTypeDO::getId, id, CrmBusinessStatusTypeDO::getName, name);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -63,5 +63,8 @@ public interface CrmContractMapper extends BaseMapperX<CrmContractDO> {
|
|||
default Long selectCountByContactId(Long contactId) {
|
||||
return selectCount(CrmContractDO::getContactId, contactId);
|
||||
}
|
||||
default CrmContractDO selectByBizId(Long businessId) {
|
||||
return selectOne(CrmContractDO::getBusinessId, businessId);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -7,10 +7,18 @@ import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
|
|||
import cn.iocoder.yudao.module.crm.controller.admin.business.vo.business.CrmBusinessPageReqVO;
|
||||
import cn.iocoder.yudao.module.crm.controller.admin.business.vo.business.CrmBusinessSaveReqVO;
|
||||
import cn.iocoder.yudao.module.crm.controller.admin.business.vo.business.CrmBusinessTransferReqVO;
|
||||
import cn.iocoder.yudao.module.crm.controller.admin.business.vo.product.CrmBusinessProductSaveReqVO;
|
||||
import cn.iocoder.yudao.module.crm.controller.admin.product.vo.product.CrmProductSaveReqVO;
|
||||
import cn.iocoder.yudao.module.crm.convert.business.CrmBusinessConvert;
|
||||
import cn.iocoder.yudao.module.crm.convert.businessproduct.CrmBusinessProductConvert;
|
||||
import cn.iocoder.yudao.module.crm.dal.dataobject.business.CrmBusinessDO;
|
||||
import cn.iocoder.yudao.module.crm.dal.dataobject.business.CrmBusinessProductDO;
|
||||
import cn.iocoder.yudao.module.crm.dal.dataobject.contact.CrmContactBusinessDO;
|
||||
import cn.iocoder.yudao.module.crm.dal.dataobject.contract.CrmContractDO;
|
||||
import cn.iocoder.yudao.module.crm.dal.mysql.business.CrmBusinessMapper;
|
||||
import cn.iocoder.yudao.module.crm.dal.mysql.business.CrmBusinessProductMapper;
|
||||
import cn.iocoder.yudao.module.crm.dal.mysql.contactbusinesslink.CrmContactBusinessMapper;
|
||||
import cn.iocoder.yudao.module.crm.dal.mysql.contract.CrmContractMapper;
|
||||
import cn.iocoder.yudao.module.crm.enums.common.CrmBizTypeEnum;
|
||||
import cn.iocoder.yudao.module.crm.enums.permission.CrmPermissionLevelEnum;
|
||||
import cn.iocoder.yudao.module.crm.framework.permission.core.annotations.CrmPermission;
|
||||
|
@ -25,11 +33,14 @@ import org.springframework.stereotype.Service;
|
|||
import org.springframework.transaction.annotation.Transactional;
|
||||
import org.springframework.validation.annotation.Validated;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
|
||||
import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertSet;
|
||||
import static cn.iocoder.yudao.module.crm.enums.ErrorCodeConstants.BUSINESS_CONTRACT_EXISTS;
|
||||
import static cn.iocoder.yudao.module.crm.enums.ErrorCodeConstants.BUSINESS_NOT_EXISTS;
|
||||
import static cn.iocoder.yudao.module.crm.enums.LogRecordConstants.*;
|
||||
|
||||
|
@ -45,6 +56,13 @@ public class CrmBusinessServiceImpl implements CrmBusinessService {
|
|||
@Resource
|
||||
private CrmBusinessMapper businessMapper;
|
||||
|
||||
@Resource
|
||||
private CrmBusinessProductMapper businessProductMapper;
|
||||
@Resource
|
||||
private CrmContractMapper contractMapper;
|
||||
|
||||
@Resource
|
||||
private CrmContactBusinessMapper contactBusinessMapper;
|
||||
@Resource
|
||||
private CrmPermissionService permissionService;
|
||||
@Resource
|
||||
|
@ -61,17 +79,65 @@ public class CrmBusinessServiceImpl implements CrmBusinessService {
|
|||
.setOwnerUserId(userId);
|
||||
businessMapper.insert(business);
|
||||
// TODO 商机待定:插入商机与产品的关联表;校验商品存在
|
||||
|
||||
verifyCrmBusinessProduct(business.getId());
|
||||
if (!createReqVO.getProducts().isEmpty()) {
|
||||
createBusinessProducts(createReqVO.getProducts(), business.getId());
|
||||
}
|
||||
// TODO 商机待定:在联系人的详情页,如果直接【新建商机】,则需要关联下。这里要搞个 CrmContactBusinessDO 表
|
||||
createContactBusiness(business.getId(), createReqVO.getContactId());
|
||||
|
||||
// 2. 创建数据权限
|
||||
// 设置当前操作的人为负责人
|
||||
permissionService.createPermission(new CrmPermissionCreateReqBO().setBizType(CrmBizTypeEnum.CRM_BUSINESS.getType())
|
||||
.setBizId(business.getId()).setUserId(userId).setLevel(CrmPermissionLevelEnum.OWNER.getLevel())); // 设置当前操作的人为负责人
|
||||
.setBizId(business.getId()).setUserId(userId).setLevel(CrmPermissionLevelEnum.OWNER.getLevel()));
|
||||
|
||||
// 4. 记录操作日志上下文
|
||||
LogRecordContext.putVariable("business", business);
|
||||
return business.getId();
|
||||
}
|
||||
/**
|
||||
* @param businessId 商机id
|
||||
* @param contactId 联系人id
|
||||
* @throws
|
||||
* @description 联系人与商机的关联
|
||||
* @author lzxhqs
|
||||
*/
|
||||
private void createContactBusiness(Long businessId, Long contactId) {
|
||||
CrmContactBusinessDO contactBusiness = new CrmContactBusinessDO();
|
||||
contactBusiness.setBusinessId(businessId);
|
||||
contactBusiness.setContactId(contactId);
|
||||
contactBusinessMapper.insert(contactBusiness);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @param products 产品集合
|
||||
* @description 插入商机产品关联表
|
||||
* @author lzxhqs
|
||||
*/
|
||||
private void createBusinessProducts(List<CrmBusinessProductSaveReqVO> products, Long businessId) {
|
||||
List<CrmBusinessProductDO> list = new ArrayList<>();
|
||||
for (CrmBusinessProductSaveReqVO product : products) {
|
||||
CrmBusinessProductDO businessProductDO = CrmBusinessProductConvert.INSTANCE.convert(product);
|
||||
businessProductDO.setBusinessId(businessId);
|
||||
list.add(businessProductDO);
|
||||
}
|
||||
businessProductMapper.insertBatch(list);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param id businessId
|
||||
* @description 校验管理的产品存在则删除
|
||||
* @author lzxhqs
|
||||
*/
|
||||
private void verifyCrmBusinessProduct(Long id) {
|
||||
CrmBusinessProductDO businessProductDO = businessProductMapper.selectByBusinessId(id);
|
||||
if (businessProductDO != null) {
|
||||
//通过商机Id删除
|
||||
businessProductMapper.deleteByBusinessId(id);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
|
@ -86,6 +152,10 @@ public class CrmBusinessServiceImpl implements CrmBusinessService {
|
|||
CrmBusinessDO updateObj = BeanUtils.toBean(updateReqVO, CrmBusinessDO.class);
|
||||
businessMapper.updateById(updateObj);
|
||||
// TODO 商机待定:插入商机与产品的关联表;校验商品存在
|
||||
verifyCrmBusinessProduct(updateReqVO.getId());
|
||||
if (!updateReqVO.getProducts().isEmpty()) {
|
||||
createBusinessProducts(updateReqVO.getProducts(), updateReqVO.getId());
|
||||
}
|
||||
|
||||
// TODO @商机待定:如果状态发生变化,插入商机状态变更记录表
|
||||
// 3. 记录操作日志上下文
|
||||
|
@ -102,6 +172,7 @@ public class CrmBusinessServiceImpl implements CrmBusinessService {
|
|||
// 校验存在
|
||||
CrmBusinessDO business = validateBusinessExists(id);
|
||||
// TODO @商机待定:需要校验有没关联合同。CrmContractDO 的 businessId 字段
|
||||
validateContractExists(id);
|
||||
|
||||
// 删除
|
||||
businessMapper.deleteById(id);
|
||||
|
@ -112,6 +183,19 @@ public class CrmBusinessServiceImpl implements CrmBusinessService {
|
|||
LogRecordContext.putVariable("businessName", business.getName());
|
||||
}
|
||||
|
||||
/**
|
||||
* @param businessId 商机id
|
||||
* @throws
|
||||
* @description 删除校验合同是关联合同
|
||||
* @author lzxhqs
|
||||
*/
|
||||
private void validateContractExists(Long businessId) {
|
||||
CrmContractDO contract = contractMapper.selectByBizId(businessId);
|
||||
if(contract != null) {
|
||||
throw exception(BUSINESS_CONTRACT_EXISTS);
|
||||
}
|
||||
}
|
||||
|
||||
private CrmBusinessDO validateBusinessExists(Long id) {
|
||||
CrmBusinessDO crmBusiness = businessMapper.selectById(id);
|
||||
if (crmBusiness == null) {
|
||||
|
|
|
@ -95,14 +95,18 @@ public class CrmBusinessStatusTypeServiceImpl implements CrmBusinessStatusTypeSe
|
|||
|
||||
// TODO @ljlleo 这个方法,这个参考 validateDeptNameUnique 实现。
|
||||
private void validateBusinessStatusTypeExists(String name, Long id) {
|
||||
LambdaQueryWrapper<CrmBusinessStatusTypeDO> wrapper = new LambdaQueryWrapperX<>();
|
||||
if(null != id) {
|
||||
wrapper.ne(CrmBusinessStatusTypeDO::getId, id);
|
||||
}
|
||||
long cnt = businessStatusTypeMapper.selectCount(wrapper.eq(CrmBusinessStatusTypeDO::getName, name));
|
||||
if (cnt > 0) {
|
||||
CrmBusinessStatusTypeDO businessStatusTypeDO = businessStatusTypeMapper.selectByIdAndName(id, name);
|
||||
if (businessStatusTypeDO != null) {
|
||||
throw exception(BUSINESS_STATUS_TYPE_NAME_EXISTS);
|
||||
}
|
||||
// LambdaQueryWrapper<CrmBusinessStatusTypeDO> wrapper = new LambdaQueryWrapperX<>();
|
||||
// if(null != id) {
|
||||
// wrapper.ne(CrmBusinessStatusTypeDO::getId, id);
|
||||
// }
|
||||
// long cnt = businessStatusTypeMapper.selectCount(wrapper.eq(CrmBusinessStatusTypeDO::getName, name));
|
||||
// if (cnt > 0) {
|
||||
// throw exception(BUSINESS_STATUS_TYPE_NAME_EXISTS);
|
||||
// }
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
Loading…
Reference in New Issue