mirror of
https://gitee.com/huangge1199_admin/vue-pro.git
synced 2024-11-23 07:41:53 +08:00
CRM: 新增客户区域数据统计
This commit is contained in:
parent
ce013a2562
commit
22191e81e3
@ -2,6 +2,7 @@ package cn.iocoder.yudao.module.crm.controller.admin.statistics;
|
|||||||
|
|
||||||
import cn.iocoder.yudao.framework.common.pojo.CommonResult;
|
import cn.iocoder.yudao.framework.common.pojo.CommonResult;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.*;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.*;
|
||||||
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerAreaRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerIndustryRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerIndustryRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerLevelRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerLevelRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerSourceRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerSourceRespVO;
|
||||||
@ -106,4 +107,11 @@ public class CrmStatisticsCustomerController {
|
|||||||
return success(customerService.getCustomerLevel(reqVO));
|
return success(customerService.getCustomerLevel(reqVO));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@GetMapping("/get-customer-area-summary")
|
||||||
|
@Operation(summary = "获取客户地区统计数据")
|
||||||
|
@PreAuthorize("@ss.hasPermission('crm:statistics-customer:query')")
|
||||||
|
public CommonResult<List<CrmStatisticCustomerAreaRespVO>> getCustomerArea(@Valid CrmStatisticsCustomerReqVO reqVO) {
|
||||||
|
return success(customerService.getCustomerArea(reqVO));
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1,27 @@
|
|||||||
|
package cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
@Schema(description = "管理后台 - CRM 客户省份分析 VO")
|
||||||
|
@Data
|
||||||
|
public class CrmStatisticCustomerAreaRespVO {
|
||||||
|
|
||||||
|
@Schema(description = "省份编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
|
||||||
|
private Integer areaId;
|
||||||
|
@Schema(description = "省份名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "浙江省")
|
||||||
|
private String areaName;
|
||||||
|
|
||||||
|
@Schema(description = "客户个数", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
|
||||||
|
private Integer customerCount;
|
||||||
|
|
||||||
|
@Schema(description = "成交个数", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
|
||||||
|
private Integer dealCount;
|
||||||
|
|
||||||
|
@Schema(description = "省份占比(%)", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
|
||||||
|
private Double areaPortion;
|
||||||
|
|
||||||
|
@Schema(description = "成交占比(%)", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
|
||||||
|
private Double dealPortion;
|
||||||
|
|
||||||
|
}
|
@ -1,6 +1,7 @@
|
|||||||
package cn.iocoder.yudao.module.crm.dal.mysql.statistics;
|
package cn.iocoder.yudao.module.crm.dal.mysql.statistics;
|
||||||
|
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.*;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.*;
|
||||||
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerAreaRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerIndustryRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerIndustryRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerLevelRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerLevelRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerSourceRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerSourceRespVO;
|
||||||
@ -51,4 +52,6 @@ public interface CrmStatisticsCustomerMapper {
|
|||||||
|
|
||||||
List<CrmStatisticCustomerLevelRespVO> selectCustomerLevelListGroupbyLevel(CrmStatisticsCustomerReqVO reqVO);
|
List<CrmStatisticCustomerLevelRespVO> selectCustomerLevelListGroupbyLevel(CrmStatisticsCustomerReqVO reqVO);
|
||||||
|
|
||||||
|
List<CrmStatisticCustomerAreaRespVO> selectSummaryListByAreaId(CrmStatisticsCustomerReqVO reqVO);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
package cn.iocoder.yudao.module.crm.service.statistics;
|
package cn.iocoder.yudao.module.crm.service.statistics;
|
||||||
|
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.*;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.*;
|
||||||
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerAreaRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerIndustryRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerIndustryRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerLevelRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerLevelRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerSourceRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerSourceRespVO;
|
||||||
@ -104,4 +105,12 @@ public interface CrmStatisticsCustomerService {
|
|||||||
*/
|
*/
|
||||||
List<CrmStatisticCustomerLevelRespVO> getCustomerLevel(CrmStatisticsCustomerReqVO reqVO);
|
List<CrmStatisticCustomerLevelRespVO> getCustomerLevel(CrmStatisticsCustomerReqVO reqVO);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取客户地区统计数据
|
||||||
|
*
|
||||||
|
* @param reqVO 请求参数
|
||||||
|
* @return 统计数据
|
||||||
|
*/
|
||||||
|
List<CrmStatisticCustomerAreaRespVO> getCustomerArea(CrmStatisticsCustomerReqVO reqVO);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -5,7 +5,11 @@ import cn.hutool.core.date.LocalDateTimeUtil;
|
|||||||
import cn.hutool.core.util.ObjUtil;
|
import cn.hutool.core.util.ObjUtil;
|
||||||
import cn.iocoder.yudao.framework.common.util.collection.MapUtils;
|
import cn.iocoder.yudao.framework.common.util.collection.MapUtils;
|
||||||
import cn.iocoder.yudao.framework.common.util.number.NumberUtils;
|
import cn.iocoder.yudao.framework.common.util.number.NumberUtils;
|
||||||
|
import cn.iocoder.yudao.framework.ip.core.Area;
|
||||||
|
import cn.iocoder.yudao.framework.ip.core.enums.AreaTypeEnum;
|
||||||
|
import cn.iocoder.yudao.framework.ip.core.utils.AreaUtils;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.*;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.*;
|
||||||
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerAreaRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerIndustryRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerIndustryRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerLevelRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerLevelRespVO;
|
||||||
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerSourceRespVO;
|
import cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerSourceRespVO;
|
||||||
@ -30,6 +34,7 @@ import java.util.Map;
|
|||||||
import java.util.stream.Stream;
|
import java.util.stream.Stream;
|
||||||
|
|
||||||
import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.*;
|
import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.*;
|
||||||
|
import static cn.iocoder.yudao.framework.common.util.collection.MapUtils.findAndThen;
|
||||||
import static cn.iocoder.yudao.module.crm.enums.DictTypeConstants.*;
|
import static cn.iocoder.yudao.module.crm.enums.DictTypeConstants.*;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -256,11 +261,11 @@ public class CrmStatisticsCustomerServiceImpl implements CrmStatisticsCustomerSe
|
|||||||
vo -> Stream.of(NumberUtils.parseLong(vo.getCreatorUserId()), vo.getOwnerUserId())));
|
vo -> Stream.of(NumberUtils.parseLong(vo.getCreatorUserId()), vo.getOwnerUserId())));
|
||||||
|
|
||||||
respVoList.forEach(vo -> {
|
respVoList.forEach(vo -> {
|
||||||
MapUtils.findAndThen(industryMap, vo.getIndustryId(), vo::setIndustryName);
|
findAndThen(industryMap, vo.getIndustryId(), vo::setIndustryName);
|
||||||
MapUtils.findAndThen(sourceMap, vo.getSource(), vo::setSourceName);
|
findAndThen(sourceMap, vo.getSource(), vo::setSourceName);
|
||||||
MapUtils.findAndThen(userMap, NumberUtils.parseLong(vo.getCreatorUserId()),
|
findAndThen(userMap, NumberUtils.parseLong(vo.getCreatorUserId()),
|
||||||
user -> vo.setCreatorUserName(user.getNickname()));
|
user -> vo.setCreatorUserName(user.getNickname()));
|
||||||
MapUtils.findAndThen(userMap, vo.getOwnerUserId(), user -> vo.setOwnerUserName(user.getNickname()));
|
findAndThen(userMap, vo.getOwnerUserId(), user -> vo.setOwnerUserName(user.getNickname()));
|
||||||
});
|
});
|
||||||
|
|
||||||
return respVoList;
|
return respVoList;
|
||||||
@ -400,6 +405,35 @@ public class CrmStatisticsCustomerServiceImpl implements CrmStatisticsCustomerSe
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<CrmStatisticCustomerAreaRespVO> getCustomerArea(CrmStatisticsCustomerReqVO reqVO) {
|
||||||
|
// 1. 获得用户编号数组
|
||||||
|
List<Long> userIds = getUserIds(reqVO);
|
||||||
|
if (CollUtil.isEmpty(userIds)) {
|
||||||
|
return Collections.emptyList();
|
||||||
|
}
|
||||||
|
reqVO.setUserIds(userIds);
|
||||||
|
// 2. 获取客户地区统计数据
|
||||||
|
List<CrmStatisticCustomerAreaRespVO> list = customerMapper.selectSummaryListByAreaId(reqVO);
|
||||||
|
if (CollUtil.isEmpty(list)) {
|
||||||
|
return Collections.emptyList();
|
||||||
|
}
|
||||||
|
|
||||||
|
// 拼接数据
|
||||||
|
List<Area> areaList = AreaUtils.getByType(AreaTypeEnum.PROVINCE, area -> area);
|
||||||
|
areaList.add(new Area().setId(null).setName("未知"));
|
||||||
|
Map<Integer, Area> areaMap = convertMap(areaList, Area::getId);
|
||||||
|
List<CrmStatisticCustomerAreaRespVO> customerAreaRespVOList = convertList(list, item -> {
|
||||||
|
Integer parentId = AreaUtils.getParentIdByType(item.getAreaId(), AreaTypeEnum.PROVINCE);
|
||||||
|
if (parentId == null) {
|
||||||
|
return item;
|
||||||
|
}
|
||||||
|
findAndThen(areaMap, parentId, area -> item.setAreaId(parentId).setAreaName(area.getName()));
|
||||||
|
return item;
|
||||||
|
});
|
||||||
|
return customerAreaRespVOList;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 拼接用户信息(昵称)
|
* 拼接用户信息(昵称)
|
||||||
*
|
*
|
||||||
@ -408,7 +442,7 @@ public class CrmStatisticsCustomerServiceImpl implements CrmStatisticsCustomerSe
|
|||||||
private <T extends CrmStatisticsCustomerByUserBaseRespVO> void appendUserInfo(List<T> respVoList) {
|
private <T extends CrmStatisticsCustomerByUserBaseRespVO> void appendUserInfo(List<T> respVoList) {
|
||||||
Map<Long, AdminUserRespDTO> userMap = adminUserApi.getUserMap(convertSet(respVoList,
|
Map<Long, AdminUserRespDTO> userMap = adminUserApi.getUserMap(convertSet(respVoList,
|
||||||
CrmStatisticsCustomerByUserBaseRespVO::getOwnerUserId));
|
CrmStatisticsCustomerByUserBaseRespVO::getOwnerUserId));
|
||||||
respVoList.forEach(vo -> MapUtils.findAndThen(userMap, vo.getOwnerUserId(), user -> vo.setOwnerUserName(user.getNickname())));
|
respVoList.forEach(vo -> findAndThen(userMap, vo.getOwnerUserId(), user -> vo.setOwnerUserName(user.getNickname())));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -312,5 +312,26 @@
|
|||||||
GROUP BY
|
GROUP BY
|
||||||
level;
|
level;
|
||||||
</select>
|
</select>
|
||||||
|
<select id="selectSummaryListByAreaId"
|
||||||
|
resultType="cn.iocoder.yudao.module.crm.controller.admin.statistics.vo.customer.analyze.CrmStatisticCustomerAreaRespVO">
|
||||||
|
SELECT
|
||||||
|
area_id,
|
||||||
|
COUNT(*) AS customerCount,
|
||||||
|
SUM(deal_status) AS dealCount,
|
||||||
|
ROUND(COUNT(*) / (SELECT COUNT(*) FROM crm_customer WHERE deleted = 0) * 100, 2) AS areaPortion,
|
||||||
|
ROUND(SUM(deal_status) / NULLIF(COUNT(*), 0) * 100, 2) AS dealPortion
|
||||||
|
FROM
|
||||||
|
crm_customer
|
||||||
|
WHERE
|
||||||
|
deleted = 0 AND area_id IS NOT NULL
|
||||||
|
AND owner_user_id IN
|
||||||
|
<foreach collection="userIds" item="userId" open="(" close=")" separator=",">
|
||||||
|
#{userId}
|
||||||
|
</foreach>
|
||||||
|
AND create_time BETWEEN #{times[0],javaType=java.time.LocalDateTime} AND
|
||||||
|
#{times[1],javaType=java.time.LocalDateTime}
|
||||||
|
GROUP BY
|
||||||
|
area_id;
|
||||||
|
</select>
|
||||||
|
|
||||||
</mapper>
|
</mapper>
|
||||||
|
Loading…
Reference in New Issue
Block a user