From 44d828023cd5aa6bbc2cc2ccd494cc3cd7f4901e Mon Sep 17 00:00:00 2001 From: zyna Date: Sat, 6 Jan 2024 21:06:38 +0800 Subject: [PATCH] =?UTF-8?q?crm=E8=81=94=E7=B3=BB=E4=BA=BA=E6=96=B0?= =?UTF-8?q?=E5=A2=9E=E6=93=8D=E4=BD=9C=E6=97=A5=E5=BF=97?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../module/crm/enums/ErrorCodeConstants.java | 2 +- .../admin/business/CrmBusinessController.java | 8 +- .../admin/contact/CrmContactController.java | 32 ++++-- .../contact/vo/CrmContactCreateReqVO.java | 14 --- .../admin/contact/vo/CrmContactRespVO.java | 102 +++++++++++++++--- ...ctBaseVO.java => CrmContactSaveReqVO.java} | 51 +++++---- .../contact/vo/CrmContactUpdateReqVO.java | 20 ---- .../convert/contact/CrmContactConvert.java | 4 +- .../core/CrmBooleanParseFunction.java | 37 +++++++ .../core/CrmContactParseFunction.java | 44 ++++++++ .../core/CrmCustomerParseFunction.java | 45 ++++++++ .../operatelog/core/CrmSexParseFunction.java | 39 +++++++ .../core/CrmSysUserParseFunction.java | 44 ++++++++ .../contact/CrmContactBusinessService.java | 3 + .../CrmContactBusinessServiceImpl.java | 5 + .../service/contact/CrmContactService.java | 15 +-- .../contact/CrmContactServiceImpl.java | 91 ++++++++++++---- .../service/contract/CrmContractService.java | 7 ++ .../contract/CrmContractServiceImpl.java | 6 ++ 19 files changed, 457 insertions(+), 112 deletions(-) delete mode 100644 yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactCreateReqVO.java rename yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/{CrmContactBaseVO.java => CrmContactSaveReqVO.java} (66%) delete mode 100644 yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactUpdateReqVO.java create mode 100644 yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmBooleanParseFunction.java create mode 100644 yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmContactParseFunction.java create mode 100644 yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmCustomerParseFunction.java create mode 100644 yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmSexParseFunction.java create mode 100644 yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmSysUserParseFunction.java diff --git a/yudao-module-crm/yudao-module-crm-api/src/main/java/cn/iocoder/yudao/module/crm/enums/ErrorCodeConstants.java b/yudao-module-crm/yudao-module-crm-api/src/main/java/cn/iocoder/yudao/module/crm/enums/ErrorCodeConstants.java index 137acee10..71ce6f9fc 100644 --- a/yudao-module-crm/yudao-module-crm-api/src/main/java/cn/iocoder/yudao/module/crm/enums/ErrorCodeConstants.java +++ b/yudao-module-crm/yudao-module-crm-api/src/main/java/cn/iocoder/yudao/module/crm/enums/ErrorCodeConstants.java @@ -24,7 +24,7 @@ public interface ErrorCodeConstants { // ========== 联系人管理 1-020-003-000 ========== ErrorCode CONTACT_NOT_EXISTS = new ErrorCode(1_020_003_000, "联系人不存在"); ErrorCode CONTACT_BUSINESS_LINK_NOT_EXISTS = new ErrorCode( 1_020_003_001, "联系人商机关联不存在"); - + ErrorCode CONTACT_CONTRACT_LINK_EXISTS = new ErrorCode( 1_020_003_002, "联系人已关联合同,不能删除"); // ========== 回款 1-020-004-000 ========== ErrorCode RECEIVABLE_NOT_EXISTS = new ErrorCode(1_020_004_000, "回款不存在"); diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/business/CrmBusinessController.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/business/CrmBusinessController.java index 5a5a423cd..7bfdb5ed6 100644 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/business/CrmBusinessController.java +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/business/CrmBusinessController.java @@ -2,6 +2,7 @@ package cn.iocoder.yudao.module.crm.controller.admin.business; import cn.hutool.core.collection.CollUtil; import cn.hutool.core.lang.Assert; +import cn.hutool.core.util.StrUtil; import cn.iocoder.yudao.framework.common.pojo.CommonResult; import cn.iocoder.yudao.framework.common.pojo.PageResult; import cn.iocoder.yudao.framework.excel.core.util.ExcelUtils; @@ -28,12 +29,15 @@ import org.springframework.web.bind.annotation.*; import java.io.IOException; import java.util.List; +import java.util.Optional; +import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception; import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success; import static cn.iocoder.yudao.framework.common.pojo.PageParam.PAGE_SIZE_NONE; import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertSet; import static cn.iocoder.yudao.framework.operatelog.core.enums.OperateTypeEnum.EXPORT; import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils.getLoginUserId; +import static cn.iocoder.yudao.module.crm.enums.ErrorCodeConstants.CUSTOMER_NOT_EXISTS; @Tag(name = "管理后台 - 商机") @RestController @@ -95,7 +99,9 @@ public class CrmBusinessController { @GetMapping("/page-by-customer") @Operation(summary = "获得商机分页,基于指定客户") public CommonResult> getBusinessPageByCustomer(@Valid CrmBusinessPageReqVO pageReqVO) { - Assert.notNull(pageReqVO.getCustomerId(), "客户编号不能为空"); + if(pageReqVO.getCustomerId() == null){ + throw exception(CUSTOMER_NOT_EXISTS); + } PageResult pageResult = businessService.getBusinessPageByCustomerId(pageReqVO); return success(buildBusinessDetailPageResult(pageResult)); } diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/CrmContactController.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/CrmContactController.java index dfb269c8f..5050cf07f 100644 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/CrmContactController.java +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/CrmContactController.java @@ -17,6 +17,9 @@ import cn.iocoder.yudao.module.crm.enums.ErrorCodeConstants; import cn.iocoder.yudao.module.crm.service.contact.CrmContactBusinessService; import cn.iocoder.yudao.module.crm.service.contact.CrmContactService; import cn.iocoder.yudao.module.crm.service.customer.CrmCustomerService; +import cn.iocoder.yudao.module.system.api.logger.OperateLogApi; +import cn.iocoder.yudao.module.system.api.logger.dto.OperateLogV2PageReqDTO; +import cn.iocoder.yudao.module.system.api.logger.dto.OperateLogV2RespDTO; import cn.iocoder.yudao.module.system.api.user.AdminUserApi; import cn.iocoder.yudao.module.system.api.user.dto.AdminUserRespDTO; import com.google.common.collect.Lists; @@ -44,6 +47,7 @@ import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils. import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertSet; import static cn.iocoder.yudao.framework.operatelog.core.enums.OperateTypeEnum.EXPORT; import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils.getLoginUserId; +import static cn.iocoder.yudao.module.crm.enums.LogRecordConstants.CRM_CONTACT; @Tag(name = "管理后台 - CRM 联系人") @RestController @@ -58,22 +62,25 @@ public class CrmContactController { private CrmCustomerService customerService; @Resource private AdminUserApi adminUserApi; + @Resource + private OperateLogApi operateLogApi; @Resource private CrmContactBusinessService contactBusinessLinkService; - // TODO @zyna:CrmContactCreateReqVO、CrmContactUpdateReqVO、CrmContactRespVO 按照新的 VO 规范搞哈;可以参考 dept 模块 + @PostMapping("/create") @Operation(summary = "创建联系人") @PreAuthorize("@ss.hasPermission('crm:contact:create')") - public CommonResult createContact(@Valid @RequestBody CrmContactCreateReqVO createReqVO) { + public CommonResult createContact(@Valid @RequestBody CrmContactSaveReqVO createReqVO) { return success(contactService.createContact(createReqVO, getLoginUserId())); } @PutMapping("/update") @Operation(summary = "更新联系人") + @OperateLog(enable = false) @PreAuthorize("@ss.hasPermission('crm:contact:update')") - public CommonResult updateContact(@Valid @RequestBody CrmContactUpdateReqVO updateReqVO) { + public CommonResult updateContact(@Valid @RequestBody CrmContactSaveReqVO updateReqVO) { contactService.updateContact(updateReqVO); return success(true); } @@ -112,11 +119,7 @@ public class CrmContactController { @Operation(summary = "获得联系人列表") @PreAuthorize("@ss.hasPermission('crm:contact:query')") public CommonResult> getSimpleContactList() { - // TODO @zyna:建议 contactService 单独搞个 list 接口哈 - CrmContactPageReqVO pageReqVO = new CrmContactPageReqVO(); - pageReqVO.setPageSize(PAGE_SIZE_NONE); - List list = contactService.getContactPage(pageReqVO, getLoginUserId()).getList(); - return success(BeanUtils.toBean(list, CrmContactSimpleRespVO.class)); + return success(contactService.simpleContactList()); } @GetMapping("/page") @@ -146,7 +149,16 @@ public class CrmContactController { ExcelUtils.write(response, "联系人.xls", "数据", CrmContactRespVO.class, buildContactDetailPage(pageResult).getList()); } - + @GetMapping("/operate-log-page") + @Operation(summary = "获得客户操作日志") + @PreAuthorize("@ss.hasPermission('crm:customer:query')") + public CommonResult> getCustomerOperateLog(@RequestParam("bizId")Long bizId) { + OperateLogV2PageReqDTO reqVO = new OperateLogV2PageReqDTO(); + reqVO.setPageSize(PAGE_SIZE_NONE); // 不分页 + reqVO.setBizType(CRM_CONTACT); + reqVO.setBizId(bizId); + return success(operateLogApi.getOperateLogPage(BeanUtils.toBean(reqVO, OperateLogV2PageReqDTO.class))); + } /** * 构建详细的联系人分页结果 * @@ -181,7 +193,7 @@ public class CrmContactController { // ================== 关联/取关联系人 =================== @PostMapping("/create-business-list") - @Operation(summary = "创建联系人与联系人的关联") + @Operation(summary = "创建联系人与商机的关联") @PreAuthorize("@ss.hasPermission('crm:contact:create-business')") public CommonResult createContactBusinessList(@Valid @RequestBody CrmContactBusinessReqVO createReqVO) { contactBusinessLinkService.createContactBusinessList(createReqVO); diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactCreateReqVO.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactCreateReqVO.java deleted file mode 100644 index 33f2db852..000000000 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactCreateReqVO.java +++ /dev/null @@ -1,14 +0,0 @@ -package cn.iocoder.yudao.module.crm.controller.admin.contact.vo; - -import io.swagger.v3.oas.annotations.media.Schema; -import lombok.Data; -import lombok.EqualsAndHashCode; -import lombok.ToString; - -@Schema(description = "管理后台 - CRM 联系人创建 Request VO") -@Data -@EqualsAndHashCode(callSuper = true) -@ToString(callSuper = true) -public class CrmContactCreateReqVO extends CrmContactBaseVO { - -} diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactRespVO.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactRespVO.java index e52f4d0c1..e56fc431b 100644 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactRespVO.java +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactRespVO.java @@ -1,34 +1,107 @@ package cn.iocoder.yudao.module.crm.controller.admin.contact.vo; +import cn.iocoder.yudao.framework.common.validation.Mobile; +import cn.iocoder.yudao.framework.common.validation.Telephone; +import cn.iocoder.yudao.framework.excel.core.annotations.DictFormat; +import cn.iocoder.yudao.framework.excel.core.convert.DictConvert; +import cn.iocoder.yudao.module.infra.enums.DictTypeConstants; import com.alibaba.excel.annotation.ExcelIgnoreUnannotated; import com.alibaba.excel.annotation.ExcelProperty; +import com.mzt.logapi.starter.annotation.DiffLogField; import io.swagger.v3.oas.annotations.media.Schema; +import jakarta.validation.constraints.Email; +import jakarta.validation.constraints.NotNull; import lombok.*; +import org.springframework.format.annotation.DateTimeFormat; + import java.time.LocalDateTime; +import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY; +import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND; + @Schema(description = "管理后台 - CRM 联系人 Response VO") @Data -@EqualsAndHashCode(callSuper = true) @ToString(callSuper = true) @ExcelIgnoreUnannotated -public class CrmContactRespVO extends CrmContactBaseVO { +public class CrmContactRespVO { @Schema(description = "主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "3167") private Long id; - @Schema(description = "创建时间") - @ExcelProperty(value = "创建时间", order = 8) - private LocalDateTime createTime; + @ExcelProperty(value = "姓名",order = 1) + @Schema(description = "姓名", example = "芋艿") + private String name; - @Schema(description = "更新时间") - @ExcelProperty(value = "更新时间", order = 8) - private LocalDateTime updateTime; + @Schema(description = "客户编号", example = "10795") + private Long customerId; + + @ExcelProperty(value = "性别", converter = DictConvert.class, order = 3) + @DictFormat(cn.iocoder.yudao.module.system.enums.DictTypeConstants.USER_SEX) + @Schema(description = "性别") + private Integer sex; + + @Schema(description = "职位") + @ExcelProperty(value = "职位", order = 3) + private String post; + + @Schema(description = "是否关键决策人") + @ExcelProperty(value = "是否关键决策人", converter = DictConvert.class, order = 3) + @DictFormat(DictTypeConstants.BOOLEAN_STRING) + private Boolean master; + + @Schema(description = "直属上级", example = "23457") + private Long parentId; + + @Schema(description = "手机号",example = "1387171766") + @ExcelProperty(value = "手机号",order = 4) + private String mobile; + + @Schema(description = "电话",example = "021-0029922") + @ExcelProperty(value = "电话",order = 4) + private String telephone; + + @ExcelProperty(value = "QQ",order = 4) + @Schema(description = "QQ",example = "197272662") + private Long qq; + + @ExcelProperty(value = "微信",order = 4) + @Schema(description = "微信",example = "zzz3883") + private String wechat; + + @Schema(description = "电子邮箱",example = "1111@22.com") + @ExcelProperty(value = "邮箱",order = 4) + private String email; + + @Schema(description = "地区编号", example = "20158") + private Integer areaId; + + @ExcelProperty(value = "地址",order = 5) + @Schema(description = "地址") + private String detailAddress; + + @Schema(description = "备注", example = "你说的对") + @ExcelProperty(value = "备注",order = 6) + private String remark; + + @Schema(description = "负责人用户编号", example = "14334") + @NotNull(message = "负责人不能为空") + private Long ownerUserId; + + @Schema(description = "最后跟进时间") + @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND) + @ExcelProperty(value = "最后跟进时间",order = 6) + private LocalDateTime contactLastTime; + + @Schema(description = "下次联系时间") + @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY) + @ExcelProperty(value = "下次联系时间",order = 6) + private LocalDateTime contactNextTime; @Schema(description = "创建人", example = "25682") private String creator; @Schema(description = "创建人名字", example = "test") - @ExcelProperty(value = "创建人", order = 8) + @ExcelProperty(value = "创建人",order = 8) private String creatorName; @ExcelProperty(value = "客户名称",order = 2) @@ -36,15 +109,14 @@ public class CrmContactRespVO extends CrmContactBaseVO { private String customerName; @Schema(description = "负责人", example = "test") - @ExcelProperty(value = "负责人", order = 7) + @ExcelProperty(value = "负责人",order = 7) private String ownerUserName; - @Schema(description = "直属上级名", example = "芋头") - @ExcelProperty(value = "直属上级", order = 4) + @Schema(description = "直属上级名",example = "芋头") + @ExcelProperty(value = "直属上级",order = 4) private String parentName; - @Schema(description = "地区名", example = "上海上海市浦东新区") - @ExcelProperty(value = "地区", order = 5) + @Schema(description = "地区名",example = "上海上海市浦东新区") + @ExcelProperty(value = "地区",order = 5) private String areaName; - } diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactBaseVO.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactSaveReqVO.java similarity index 66% rename from yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactBaseVO.java rename to yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactSaveReqVO.java index f210bfd8f..177c2b41f 100644 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactBaseVO.java +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactSaveReqVO.java @@ -5,12 +5,14 @@ import cn.iocoder.yudao.framework.common.validation.Telephone; import cn.iocoder.yudao.framework.excel.core.annotations.DictFormat; import cn.iocoder.yudao.framework.excel.core.convert.DictConvert; import cn.iocoder.yudao.module.infra.enums.DictTypeConstants; -import com.alibaba.excel.annotation.ExcelIgnoreUnannotated; import com.alibaba.excel.annotation.ExcelProperty; +import com.mzt.logapi.starter.annotation.DiffLogField; import io.swagger.v3.oas.annotations.media.Schema; import jakarta.validation.constraints.Email; import jakarta.validation.constraints.NotNull; import lombok.Data; +import lombok.EqualsAndHashCode; +import lombok.ToString; import org.springframework.format.annotation.DateTimeFormat; import java.time.LocalDateTime; @@ -18,86 +20,91 @@ import java.time.LocalDateTime; import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY; import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND; -// TODO zyna:要不按照新的,干掉这个 basevo,都放子类里 -/** - * CRM 联系人 Base VO,提供给添加、修改、详细的子 VO 使用 - * 如果子 VO 存在差异的字段,请不要添加到这里,影响 Swagger 文档生成 - */ +@Schema(description = "管理后台 - CRM 联系人创建/更新 Request VO") @Data -@ExcelIgnoreUnannotated -public class CrmContactBaseVO { +@ToString(callSuper = true) +public class CrmContactSaveReqVO { + + @Schema(description = "主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "3167") + private Long id; - @ExcelProperty(value = "姓名",order = 1) @Schema(description = "姓名", example = "芋艿") @NotNull(message = "姓名不能为空") + @DiffLogField(name = "姓名") private String name; @Schema(description = "客户编号", example = "10795") + @DiffLogField(name = "姓名",function = "getCustomerById") private Long customerId; - @ExcelProperty(value = "性别", converter = DictConvert.class, order = 3) @DictFormat(cn.iocoder.yudao.module.system.enums.DictTypeConstants.USER_SEX) @Schema(description = "性别") + @DiffLogField(name = "性别",function = "getSexById") private Integer sex; @Schema(description = "职位") - @ExcelProperty(value = "职位", order = 3) + @DiffLogField(name = "职位") private String post; @Schema(description = "是否关键决策人") - @ExcelProperty(value = "是否关键决策人", converter = DictConvert.class, order = 3) @DictFormat(DictTypeConstants.BOOLEAN_STRING) + @DiffLogField(name = "关键决策人", function = "getBooleanById") private Boolean master; @Schema(description = "直属上级", example = "23457") + @DiffLogField(name = "直属上级",function = "getContactById") private Long parentId; @Schema(description = "手机号",example = "1387171766") @Mobile - @ExcelProperty(value = "手机号",order = 4) + @DiffLogField(name = "手机号") private String mobile; - @Schema(description = "座机",example = "021-0029922") + @Schema(description = "电话",example = "021-0029922") @Telephone - @ExcelProperty(value = "座机",order = 4) + @DiffLogField(name = "电话") private String telephone; - @ExcelProperty(value = "QQ",order = 4) @Schema(description = "QQ",example = "197272662") + @DiffLogField(name = "QQ") private Long qq; - @ExcelProperty(value = "微信",order = 4) @Schema(description = "微信",example = "zzz3883") + @DiffLogField(name = "微信") private String wechat; @Schema(description = "电子邮箱",example = "1111@22.com") + @DiffLogField(name = "邮箱") @Email - @ExcelProperty(value = "邮箱",order = 4) private String email; @Schema(description = "地区编号", example = "20158") + @DiffLogField(name = "所在地", function = "getAreaById") private Integer areaId; - @ExcelProperty(value = "地址",order = 5) @Schema(description = "地址") + @DiffLogField(name = "地址") private String detailAddress; @Schema(description = "备注", example = "你说的对") - @ExcelProperty(value = "备注",order = 6) + @DiffLogField(name = "备注") private String remark; @Schema(description = "负责人用户编号", example = "14334") @NotNull(message = "负责人不能为空") + @DiffLogField(name = "负责人",function = "getUserById") private Long ownerUserId; @Schema(description = "最后跟进时间") @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND) - @ExcelProperty(value = "最后跟进时间",order = 6) + @DiffLogField(name = "最后跟进时间") private LocalDateTime contactLastTime; @Schema(description = "下次联系时间") @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY) - @ExcelProperty(value = "下次联系时间",order = 6) + @DiffLogField(name = "下次联系时间") private LocalDateTime contactNextTime; + @Schema(description = "关联商机ID", example = "122233") + private Long businessId; } diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactUpdateReqVO.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactUpdateReqVO.java deleted file mode 100644 index 0f705d5cb..000000000 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/contact/vo/CrmContactUpdateReqVO.java +++ /dev/null @@ -1,20 +0,0 @@ -package cn.iocoder.yudao.module.crm.controller.admin.contact.vo; - -import io.swagger.v3.oas.annotations.media.Schema; -import lombok.Data; -import lombok.EqualsAndHashCode; -import lombok.ToString; - -import jakarta.validation.constraints.NotNull; - -@Schema(description = "管理后台 - CRM 联系人更新 Request VO") -@Data -@EqualsAndHashCode(callSuper = true) -@ToString(callSuper = true) -public class CrmContactUpdateReqVO extends CrmContactBaseVO { - - @Schema(description = "主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "3167") - @NotNull(message = "主键不能为空") - private Long id; - -} diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/convert/contact/CrmContactConvert.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/convert/contact/CrmContactConvert.java index de248d2c6..2c0c59e43 100644 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/convert/contact/CrmContactConvert.java +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/convert/contact/CrmContactConvert.java @@ -29,9 +29,7 @@ public interface CrmContactConvert { CrmContactConvert INSTANCE = Mappers.getMapper(CrmContactConvert.class); - CrmContactDO convert(CrmContactCreateReqVO bean); - - CrmContactDO convert(CrmContactUpdateReqVO bean); + CrmContactDO convert(CrmContactSaveReqVO bean); CrmContactRespVO convert(CrmContactDO bean); diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmBooleanParseFunction.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmBooleanParseFunction.java new file mode 100644 index 000000000..a7e5be1ee --- /dev/null +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmBooleanParseFunction.java @@ -0,0 +1,37 @@ +package cn.iocoder.yudao.module.crm.framework.operatelog.core; + +import cn.hutool.core.util.StrUtil; +import cn.iocoder.yudao.framework.dict.core.util.DictFrameworkUtils; +import cn.iocoder.yudao.module.infra.enums.DictTypeConstants; +import com.mzt.logapi.service.IParseFunction; +import lombok.extern.slf4j.Slf4j; +import org.springframework.stereotype.Component; + +/** + * 行业的 {@link IParseFunction} 实现类 + * + * @author HUIHUI + */ +@Slf4j +@Component +public class CrmBooleanParseFunction implements IParseFunction { + + @Override + public boolean executeBefore() { + return true; // 先转换值后对比 + } + + @Override + public String functionName() { + return "getBooleanById"; + } + + @Override + public String apply(Object value) { + if (StrUtil.isEmptyIfStr(value)) { + return ""; + } + return DictFrameworkUtils.getDictDataLabel(DictTypeConstants.BOOLEAN_STRING, value.toString()); + } + +} diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmContactParseFunction.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmContactParseFunction.java new file mode 100644 index 000000000..1243ab0a5 --- /dev/null +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmContactParseFunction.java @@ -0,0 +1,44 @@ +package cn.iocoder.yudao.module.crm.framework.operatelog.core; + +import cn.hutool.core.util.StrUtil; +import cn.iocoder.yudao.module.crm.dal.dataobject.contact.CrmContactDO; +import cn.iocoder.yudao.module.crm.service.contact.CrmContactService; +import cn.iocoder.yudao.module.system.api.user.AdminUserApi; +import cn.iocoder.yudao.module.system.api.user.dto.AdminUserRespDTO; +import com.mzt.logapi.service.IParseFunction; +import jakarta.annotation.Resource; +import lombok.extern.slf4j.Slf4j; +import org.springframework.stereotype.Component; + +/** + * 行业的 {@link IParseFunction} 实现类 + * + * @author HUIHUI + */ +@Slf4j +@Component +public class CrmContactParseFunction implements IParseFunction { + + @Resource + private CrmContactService contactService; + + @Override + public boolean executeBefore() { + return true; // 先转换值后对比 + } + + @Override + public String functionName() { + return "getContactById"; + } + + @Override + public String apply(Object value) { + if (StrUtil.isEmptyIfStr(value)) { + return ""; + } + CrmContactDO contactDO = contactService.getContact(Long.parseLong(value.toString())); + return contactDO == null ? "" : contactDO.getName(); + } + +} diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmCustomerParseFunction.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmCustomerParseFunction.java new file mode 100644 index 000000000..34170aa3d --- /dev/null +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmCustomerParseFunction.java @@ -0,0 +1,45 @@ +package cn.iocoder.yudao.module.crm.framework.operatelog.core; + +import cn.hutool.core.util.StrUtil; +import cn.iocoder.yudao.framework.dict.core.util.DictFrameworkUtils; +import cn.iocoder.yudao.module.crm.dal.dataobject.customer.CrmCustomerDO; +import cn.iocoder.yudao.module.crm.service.customer.CrmCustomerService; +import cn.iocoder.yudao.module.system.enums.DictTypeConstants; +import com.mzt.logapi.service.IParseFunction; +import jakarta.annotation.Resource; +import lombok.extern.slf4j.Slf4j; +import org.springframework.stereotype.Component; + +import java.util.Optional; + +/** + * 行业的 {@link IParseFunction} 实现类 + * + * @author HUIHUI + */ +@Slf4j +@Component +public class CrmCustomerParseFunction implements IParseFunction { + + @Resource + private CrmCustomerService customerService; + @Override + public boolean executeBefore() { + return true; // 先转换值后对比 + } + + @Override + public String functionName() { + return "getCustomerById"; + } + + @Override + public String apply(Object value) { + if (StrUtil.isEmptyIfStr(value)) { + return ""; + } + CrmCustomerDO crmCustomerDO = customerService.getCustomer(Long.parseLong(value.toString())); + return crmCustomerDO == null ? "" : crmCustomerDO.getName(); + } + +} diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmSexParseFunction.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmSexParseFunction.java new file mode 100644 index 000000000..6001e8bfa --- /dev/null +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmSexParseFunction.java @@ -0,0 +1,39 @@ +package cn.iocoder.yudao.module.crm.framework.operatelog.core; + +import cn.hutool.core.util.StrUtil; +import cn.iocoder.yudao.framework.dict.core.util.DictFrameworkUtils; +import cn.iocoder.yudao.module.system.enums.DictTypeConstants; +import com.mzt.logapi.service.IParseFunction; +import lombok.extern.slf4j.Slf4j; +import org.springframework.stereotype.Component; + +import static cn.iocoder.yudao.module.crm.enums.DictTypeConstants.CRM_CUSTOMER_INDUSTRY; + +/** + * 行业的 {@link IParseFunction} 实现类 + * + * @author HUIHUI + */ +@Slf4j +@Component +public class CrmSexParseFunction implements IParseFunction { + + @Override + public boolean executeBefore() { + return true; // 先转换值后对比 + } + + @Override + public String functionName() { + return "getSexById"; + } + + @Override + public String apply(Object value) { + if (StrUtil.isEmptyIfStr(value)) { + return ""; + } + return DictFrameworkUtils.getDictDataLabel(DictTypeConstants.USER_SEX, value.toString()); + } + +} diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmSysUserParseFunction.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmSysUserParseFunction.java new file mode 100644 index 000000000..8fb65518e --- /dev/null +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/framework/operatelog/core/CrmSysUserParseFunction.java @@ -0,0 +1,44 @@ +package cn.iocoder.yudao.module.crm.framework.operatelog.core; + +import cn.hutool.core.util.StrUtil; +import cn.iocoder.yudao.framework.dict.core.util.DictFrameworkUtils; +import cn.iocoder.yudao.module.system.api.user.AdminUserApi; +import cn.iocoder.yudao.module.system.api.user.dto.AdminUserRespDTO; +import cn.iocoder.yudao.module.system.enums.DictTypeConstants; +import com.mzt.logapi.service.IParseFunction; +import jakarta.annotation.Resource; +import lombok.extern.slf4j.Slf4j; +import org.springframework.stereotype.Component; + +/** + * 行业的 {@link IParseFunction} 实现类 + * + * @author HUIHUI + */ +@Slf4j +@Component +public class CrmSysUserParseFunction implements IParseFunction { + + @Resource + private AdminUserApi adminUserApi; + + @Override + public boolean executeBefore() { + return true; // 先转换值后对比 + } + + @Override + public String functionName() { + return "getUserById"; + } + + @Override + public String apply(Object value) { + if (StrUtil.isEmptyIfStr(value)) { + return ""; + } + AdminUserRespDTO adminUserRespDTO = adminUserApi.getUser(Long.parseLong(value.toString())); + return adminUserRespDTO == null ? "" : adminUserRespDTO.getNickname(); + } + +} diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactBusinessService.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactBusinessService.java index 4a4d7a42d..3baef8bc6 100644 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactBusinessService.java +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactBusinessService.java @@ -35,4 +35,7 @@ public interface CrmContactBusinessService { */ List getContactBusinessListByContactId(Long contactId); + + void deleteContactBusinessByContactId(Long contactId); + } \ No newline at end of file diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactBusinessServiceImpl.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactBusinessServiceImpl.java index d0c92b548..9b3fe9e49 100644 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactBusinessServiceImpl.java +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactBusinessServiceImpl.java @@ -80,4 +80,9 @@ public class CrmContactBusinessServiceImpl implements CrmContactBusinessService return contactBusinessMapper.selectListByContactId(contactId); } + @Override + public void deleteContactBusinessByContactId(Long contactId) { + contactBusinessMapper.delete(CrmContactBusinessDO::getContactId,contactId); + } + } \ No newline at end of file diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactService.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactService.java index 7d0c1dc0c..525201139 100644 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactService.java +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactService.java @@ -1,10 +1,7 @@ package cn.iocoder.yudao.module.crm.service.contact; import cn.iocoder.yudao.framework.common.pojo.PageResult; -import cn.iocoder.yudao.module.crm.controller.admin.contact.vo.CrmContactCreateReqVO; -import cn.iocoder.yudao.module.crm.controller.admin.contact.vo.CrmContactPageReqVO; -import cn.iocoder.yudao.module.crm.controller.admin.contact.vo.CrmContactTransferReqVO; -import cn.iocoder.yudao.module.crm.controller.admin.contact.vo.CrmContactUpdateReqVO; +import cn.iocoder.yudao.module.crm.controller.admin.contact.vo.*; import cn.iocoder.yudao.module.crm.dal.dataobject.contact.CrmContactDO; import cn.iocoder.yudao.module.crm.dal.dataobject.customer.CrmCustomerDO; import jakarta.validation.Valid; @@ -26,14 +23,14 @@ public interface CrmContactService { * @param userId 用户编号 * @return 编号 */ - Long createContact(@Valid CrmContactCreateReqVO createReqVO, Long userId); + Long createContact(@Valid CrmContactSaveReqVO createReqVO, Long userId); /** * 更新联系人 * * @param updateReqVO 更新信息 */ - void updateContact(@Valid CrmContactUpdateReqVO updateReqVO); + void updateContact(@Valid CrmContactSaveReqVO updateReqVO); /** * 删除联系人 @@ -88,4 +85,10 @@ public interface CrmContactService { */ void transferContact(CrmContactTransferReqVO reqVO, Long userId); + /** + * 获取联系人简单列表 + * @return 联系人 + */ + List simpleContactList(); + } diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactServiceImpl.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactServiceImpl.java index d55ce447b..ab8e8aeec 100644 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactServiceImpl.java +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contact/CrmContactServiceImpl.java @@ -2,29 +2,43 @@ package cn.iocoder.yudao.module.crm.service.contact; import cn.hutool.core.collection.CollUtil; import cn.hutool.core.collection.ListUtil; +import cn.hutool.core.util.StrUtil; import cn.iocoder.yudao.framework.common.pojo.PageResult; +import cn.iocoder.yudao.framework.common.util.object.BeanUtils; import cn.iocoder.yudao.module.crm.controller.admin.contact.vo.*; import cn.iocoder.yudao.module.crm.convert.contact.CrmContactConvert; +import cn.iocoder.yudao.module.crm.dal.dataobject.business.CrmBusinessDO; import cn.iocoder.yudao.module.crm.dal.dataobject.contact.CrmContactDO; +import cn.iocoder.yudao.module.crm.dal.dataobject.contract.CrmContractDO; import cn.iocoder.yudao.module.crm.dal.mysql.contact.CrmContactMapper; 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; +import cn.iocoder.yudao.module.crm.service.business.CrmBusinessService; +import cn.iocoder.yudao.module.crm.service.contract.CrmContractService; import cn.iocoder.yudao.module.crm.service.customer.CrmCustomerService; import cn.iocoder.yudao.module.crm.service.permission.CrmPermissionService; import cn.iocoder.yudao.module.crm.service.permission.bo.CrmPermissionCreateReqBO; import cn.iocoder.yudao.module.system.api.user.AdminUserApi; +import com.mzt.logapi.context.LogRecordContext; +import com.mzt.logapi.service.impl.DiffParseFunction; +import com.mzt.logapi.starter.annotation.LogRecord; import jakarta.annotation.Resource; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import org.springframework.validation.annotation.Validated; +import java.util.Arrays; import java.util.Collection; import java.util.List; +import java.util.Optional; import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception; -import static cn.iocoder.yudao.module.crm.enums.ErrorCodeConstants.CONTACT_NOT_EXISTS; -import static cn.iocoder.yudao.module.crm.enums.ErrorCodeConstants.CUSTOMER_NOT_EXISTS; +import static cn.iocoder.yudao.framework.common.pojo.PageParam.PAGE_SIZE_NONE; +import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils.getLoginUserId; +import static cn.iocoder.yudao.module.crm.enums.ErrorCodeConstants.*; +import static cn.iocoder.yudao.module.crm.enums.LogRecordConstants.CRM_CONTACT; +import static cn.iocoder.yudao.module.system.enums.ErrorCodeConstants.ERROR_CODE_DUPLICATE; import static cn.iocoder.yudao.module.system.enums.ErrorCodeConstants.USER_NOT_EXISTS; /** @@ -38,45 +52,68 @@ public class CrmContactServiceImpl implements CrmContactService { @Resource private CrmContactMapper contactMapper; - @Resource private CrmCustomerService customerService; @Resource private CrmPermissionService crmPermissionService; @Resource private AdminUserApi adminUserApi; + @Resource + private CrmContractService crmContractService; + @Resource + private CrmContactBusinessService contactBusinessService; + @Resource + private CrmBusinessService businessService; @Override @Transactional(rollbackFor = Exception.class) - // TODO @zyna:增加操作日志,可以参考 CustomerService;内容是 新建了联系人【名字】 - public Long createContact(CrmContactCreateReqVO createReqVO, Long userId) { + @LogRecord(type = CRM_CONTACT, subType = "创建联系人[{{#contactName}}]", bizNo = "{{#contactId}}", success = "创建了联系人") + public Long createContact(CrmContactSaveReqVO createReqVO, Long userId) { // 1. 校验 validateRelationDataExists(createReqVO); // 2. 插入联系人 CrmContactDO contact = CrmContactConvert.INSTANCE.convert(createReqVO); - contactMapper.insert(contact); + int contactId = contactMapper.insert(contact); // 3. 创建数据权限 crmPermissionService.createPermission(new CrmPermissionCreateReqBO().setUserId(userId) .setBizType(CrmBizTypeEnum.CRM_CONTACT.getType()).setBizId(contact.getId()) .setLevel(CrmPermissionLevelEnum.OWNER.getLevel())); - // TODO @zyna:特殊逻辑:如果在【商机】详情那,点击【新增联系人】时,可以自动绑定商机 + //4.若传businessId自动关联商机 + Optional.ofNullable(createReqVO.getBusinessId()).ifPresent(businessId -> { + CrmBusinessDO crmBusinessDO = businessService.getBusiness(createReqVO.getBusinessId()); + if(crmBusinessDO == null){ + throw exception(BUSINESS_NOT_EXISTS); + } + CrmContactBusinessReqVO crmContactBusinessReqVO = new CrmContactBusinessReqVO(); + crmContactBusinessReqVO.setContactId(contact.getId()); + crmContactBusinessReqVO.setBusinessIds(List.of(businessId)); + contactBusinessService.createContactBusinessList(crmContactBusinessReqVO); + }); + + // 5. 记录操作日志 + LogRecordContext.putVariable("contactId", contact.getId()); + LogRecordContext.putVariable("contactName", contact.getName()); return contact.getId(); } @Override + @Transactional(rollbackFor = Exception.class) + @LogRecord(type = CRM_CONTACT, subType = "更新联系人", bizNo = "{{#updateReqVO.id}}", success = "更新了联系人{_DIFF{#updateReqVO}}") @CrmPermission(bizType = CrmBizTypeEnum.CRM_CONTACT, bizId = "#updateReqVO.id", level = CrmPermissionLevelEnum.WRITE) - // TODO @zyna:增加操作日志,可以参考 CustomerService;需要 diff 出字段 - public void updateContact(CrmContactUpdateReqVO updateReqVO) { + public void updateContact(CrmContactSaveReqVO updateReqVO) { // 1. 校验存在 - validateContactExists(updateReqVO.getId()); + CrmContactDO contactDO = validateContactExists(updateReqVO.getId()); validateRelationDataExists(updateReqVO); // 2. 更新联系人 CrmContactDO updateObj = CrmContactConvert.INSTANCE.convert(updateReqVO); contactMapper.updateById(updateObj); + + // 3. 记录操作日志 + LogRecordContext.putVariable(DiffParseFunction.OLD_OBJECT, BeanUtils.toBean(contactDO, CrmContactSaveReqVO.class)); } /** @@ -84,7 +121,7 @@ public class CrmContactServiceImpl implements CrmContactService { * * @param saveReqVO 新增/修改请求 VO */ - private void validateRelationDataExists(CrmContactBaseVO saveReqVO) { + private void validateRelationDataExists(CrmContactSaveReqVO saveReqVO) { // 1. 校验客户 if (saveReqVO.getCustomerId() != null && customerService.getCustomer(saveReqVO.getCustomerId()) == null) { throw exception(CUSTOMER_NOT_EXISTS); @@ -101,24 +138,30 @@ public class CrmContactServiceImpl implements CrmContactService { @Override @CrmPermission(bizType = CrmBizTypeEnum.CRM_CONTACT, bizId = "#id", level = CrmPermissionLevelEnum.OWNER) + @Transactional(rollbackFor = Exception.class) public void deleteContact(Long id) { - // 校验存在 + //1. 校验存在 validateContactExists(id); - // TODO @zyna:如果有关联的合同,不允许删除;Contract.contactId - - // 删除 + //2.校验是否关联合同 + CrmContractDO crmContractDO = crmContractService.getContractByContactId(id); + if(crmContractDO != null){ + throw exception(CONTACT_CONTRACT_LINK_EXISTS); + } + //3.删除联系人 contactMapper.deleteById(id); - // 删除数据权限 + //4.删除数据权限 crmPermissionService.deletePermission(CrmBizTypeEnum.CRM_CONTACT.getType(), id); - // TODO @zyna:删除商机联系人关联 - + //5.删除商机关联 + contactBusinessService.deleteContactBusinessByContactId(id); // TODO @puhui999:删除跟进记录 } - private void validateContactExists(Long id) { - if (contactMapper.selectById(id) == null) { + private CrmContactDO validateContactExists(Long id) { + CrmContactDO contactDO = contactMapper.selectById(id); + if (contactDO == null) { throw exception(CONTACT_NOT_EXISTS); } + return contactDO; } @Override @@ -162,4 +205,12 @@ public class CrmContactServiceImpl implements CrmContactService { // 3. TODO 记录转移日志 } + @Override + public List simpleContactList() { + CrmContactPageReqVO pageReqVO = new CrmContactPageReqVO(); + pageReqVO.setPageSize(PAGE_SIZE_NONE); + List list =contactMapper.selectPage(pageReqVO, getLoginUserId()).getList(); + return BeanUtils.toBean(list, CrmContactSimpleRespVO.class); + } + } \ No newline at end of file diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contract/CrmContractService.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contract/CrmContractService.java index 7d3f83335..570c9307c 100644 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contract/CrmContractService.java +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contract/CrmContractService.java @@ -87,4 +87,11 @@ public interface CrmContractService { */ void transferContract(CrmContractTransferReqVO reqVO, Long userId); + /** + * 查询合同,基于联系人 + * @param contactId 联系人ID + * @return 合同 + */ + CrmContractDO getContractByContactId(Long contactId); + } diff --git a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contract/CrmContractServiceImpl.java b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contract/CrmContractServiceImpl.java index bb010265f..5eefb402f 100644 --- a/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contract/CrmContractServiceImpl.java +++ b/yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/contract/CrmContractServiceImpl.java @@ -2,6 +2,7 @@ package cn.iocoder.yudao.module.crm.service.contract; import cn.hutool.core.collection.CollUtil; import cn.hutool.core.collection.ListUtil; +import cn.hutool.core.util.StrUtil; import cn.iocoder.yudao.framework.common.pojo.PageResult; import cn.iocoder.yudao.module.crm.controller.admin.contract.vo.CrmContractCreateReqVO; import cn.iocoder.yudao.module.crm.controller.admin.contract.vo.CrmContractPageReqVO; @@ -135,5 +136,10 @@ public class CrmContractServiceImpl implements CrmContractService { contractMapper.updateOwnerUserIdById(reqVO.getId(), reqVO.getNewOwnerUserId()); } + @Override + public CrmContractDO getContractByContactId(Long contactId) { + return contractMapper.selectOne(CrmContractDO::getContactId, contactId); + } + // TODO @合同待定:需要新增一个 ContractConfigDO 表,合同配置,重点是到期提醒; }