跳到主要内容

CRM 客户关系管理系统设计

一、系统概述

1.1 系统简介

CRM(Customer Relationship Management)客户关系管理系统是一个以客户为中心的企业管理系统,帮助企业管理客户信息、销售机会、营销活动、客户服务等,提升客户满意度和企业销售业绩。

1.2 核心价值

价值点说明预期效果
🎯 客户洞察360度客户画像分析客户转化率提升 35%
📊 销售提效销售漏斗自动化管理销售效率提升 40%
🔄 营销自动化智能营销活动管理营销 ROI 提升 50%
📈 数据驱动实时数据分析决策决策效率提升 45%
🚀 服务升级智能工单系统客户满意度提升 30%

1.3 业务需求

核心功能

  • 客户管理:客户信息、联系人、客户标签、客户分级
  • 销售管理:商机管理、销售漏斗、报价单、合同管理
  • 营销管理:营销活动、营销自动化、营销线索
  • 服务管理:工单管理、客户投诉、售后服务
  • 数据分析:销售报表、客户分析、业绩统计
  • 协作管理:任务管理、日程安排、团队协作

非功能需求

  • 高可用性:系统可用性 99.9%
  • 数据安全:客户数据加密存储,权限严格控制
  • 易用性:界面友好,操作简单
  • 移动端支持:支持移动端 APP

二、系统架构

2.1 技术架构

2.2 销售漏斗流程

2.3 微服务划分

1. 客户服务 (crm-customer-service)

java
1- 客户管理 (Customer)
2- 联系人管理 (Contact)
3- 客户标签 (CustomerTag)
4- 客户跟进记录 (FollowUp)
5- 客户分级 (CustomerLevel)

2. 销售服务 (crm-sales-service)

java
1- 商机管理 (Opportunity)
2- 销售线索 (Lead)
3- 报价单管理 (Quotation)
4- 合同管理 (Contract)
5- 订单管理 (Order)

3. 营销服务 (crm-marketing-service)

java
1- 营销活动 (Campaign)
2- 营销自动化 (Marketing Automation)
3- 邮件营销 (Email Marketing)
4- 短信营销 (SMS Marketing)
5- 营销效果分析 (Marketing Analytics)

4. 服务工单 (crm-service-service)

java
1- 工单管理 (Ticket)
2- 客户投诉 (Complaint)
3- 售后服务 (After-sales Service)
4- 知识库 (Knowledge Base)

5. 数据分析服务 (crm-analytics-service)

java
1- 销售报表 (Sales Report)
2- 客户分析 (Customer Analytics)
3- 业绩统计 (Performance Statistics)
4- 漏斗分析 (Funnel Analysis)

数据模型设计

核心表结构

1. 客户表 (customer)

sql
1CREATE TABLE customer (
2 id BIGINT PRIMARY KEY AUTO_INCREMENT,
3 customer_no VARCHAR(50) NOT NULL UNIQUE COMMENT '客户编号',
4 customer_name VARCHAR(200) NOT NULL COMMENT '客户名称',
5 customer_type TINYINT NOT NULL COMMENT '客户类型:1-企业,2-个人',
6 industry VARCHAR(50) COMMENT '所属行业',
7 level TINYINT DEFAULT 1 COMMENT '客户等级:1-A类,2-B类,3-C类',
8 source TINYINT COMMENT '客户来源:1-线上,2-线下,3-转介绍,4-其他',
9 status TINYINT DEFAULT 1 COMMENT '状态:1-潜在客户,2-意向客户,3-成交客户,4-流失客户',
10 province VARCHAR(50) COMMENT '省份',
11 city VARCHAR(50) COMMENT '城市',
12 address VARCHAR(200) COMMENT '详细地址',
13 phone VARCHAR(20) COMMENT '电话',
14 email VARCHAR(100) COMMENT '邮箱',
15 website VARCHAR(200) COMMENT '网站',
16 company_size VARCHAR(20) COMMENT '公司规模',
17 annual_revenue DECIMAL(15,2) COMMENT '年营收',
18 owner_user_id BIGINT COMMENT '负责人ID',
19 create_user_id BIGINT COMMENT '创建人ID',
20 create_time DATETIME DEFAULT CURRENT_TIMESTAMP,
21 update_time DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
22 INDEX idx_customer_no (customer_no),
23 INDEX idx_owner (owner_user_id),
24 INDEX idx_status (status),
25 INDEX idx_level (level)
26) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='客户表';

2. 联系人表 (contact)

sql
1CREATE TABLE contact (
2 id BIGINT PRIMARY KEY AUTO_INCREMENT,
3 customer_id BIGINT NOT NULL COMMENT '客户ID',
4 contact_name VARCHAR(100) NOT NULL COMMENT '联系人姓名',
5 gender TINYINT COMMENT '性别:1-男,2-女',
6 position VARCHAR(50) COMMENT '职位',
7 department VARCHAR(50) COMMENT '部门',
8 mobile VARCHAR(20) COMMENT '手机',
9 phone VARCHAR(20) COMMENT '电话',
10 email VARCHAR(100) COMMENT '邮箱',
11 wechat VARCHAR(50) COMMENT '微信',
12 qq VARCHAR(20) COMMENT 'QQ',
13 is_primary TINYINT DEFAULT 0 COMMENT '是否主联系人:0-否,1-是',
14 birthday DATE COMMENT '生日',
15 remark VARCHAR(500) COMMENT '备注',
16 create_time DATETIME DEFAULT CURRENT_TIMESTAMP,
17 update_time DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
18 INDEX idx_customer (customer_id),
19 INDEX idx_mobile (mobile)
20) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='联系人表';

3. 商机表 (opportunity)

sql
1CREATE TABLE opportunity (
2 id BIGINT PRIMARY KEY AUTO_INCREMENT,
3 opportunity_no VARCHAR(50) NOT NULL UNIQUE COMMENT '商机编号',
4 opportunity_name VARCHAR(200) NOT NULL COMMENT '商机名称',
5 customer_id BIGINT NOT NULL COMMENT '客户ID',
6 contact_id BIGINT COMMENT '联系人ID',
7 amount DECIMAL(15,2) COMMENT '预计金额',
8 stage TINYINT NOT NULL DEFAULT 1 COMMENT '阶段:1-初步接触,2-需求分析,3-方案报价,4-谈判,5-成交,6-失败',
9 probability INT DEFAULT 0 COMMENT '赢单概率(%)',
10 expected_close_date DATE COMMENT '预计成交日期',
11 actual_close_date DATE COMMENT '实际成交日期',
12 source TINYINT COMMENT '商机来源:1-线上,2-线下,3-转介绍,4-其他',
13 competitor VARCHAR(200) COMMENT '竞争对手',
14 priority TINYINT DEFAULT 0 COMMENT '优先级:0-普通,1-重要,2-紧急',
15 status TINYINT DEFAULT 1 COMMENT '状态:1-进行中,2-已成交,3-已失败',
16 owner_user_id BIGINT NOT NULL COMMENT '负责人ID',
17 lose_reason VARCHAR(500) COMMENT '失败原因',
18 remark VARCHAR(500) COMMENT '备注',
19 create_user_id BIGINT COMMENT '创建人ID',
20 create_time DATETIME DEFAULT CURRENT_TIMESTAMP,
21 update_time DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
22 INDEX idx_opportunity_no (opportunity_no),
23 INDEX idx_customer (customer_id),
24 INDEX idx_owner (owner_user_id),
25 INDEX idx_stage (stage),
26 INDEX idx_status (status)
27) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='商机表';

4. 销售线索表 (lead)

sql
1CREATE TABLE lead (
2 id BIGINT PRIMARY KEY AUTO_INCREMENT,
3 lead_no VARCHAR(50) NOT NULL UNIQUE COMMENT '线索编号',
4 company_name VARCHAR(200) COMMENT '公司名称',
5 contact_name VARCHAR(100) NOT NULL COMMENT '联系人',
6 mobile VARCHAR(20) COMMENT '手机',
7 email VARCHAR(100) COMMENT '邮箱',
8 province VARCHAR(50) COMMENT '省份',
9 city VARCHAR(50) COMMENT '城市',
10 industry VARCHAR(50) COMMENT '行业',
11 source TINYINT COMMENT '来源:1-网站,2-广告,3-活动,4-转介绍,5-其他',
12 campaign_id BIGINT COMMENT '营销活动ID',
13 status TINYINT DEFAULT 1 COMMENT '状态:1-未处理,2-跟进中,3-已转化,4-无效',
14 score INT DEFAULT 0 COMMENT '线索评分',
15 owner_user_id BIGINT COMMENT '负责人ID',
16 converted_customer_id BIGINT COMMENT '转化客户ID',
17 converted_time DATETIME COMMENT '转化时间',
18 remark VARCHAR(500) COMMENT '备注',
19 create_time DATETIME DEFAULT CURRENT_TIMESTAMP,
20 update_time DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
21 INDEX idx_lead_no (lead_no),
22 INDEX idx_mobile (mobile),
23 INDEX idx_status (status),
24 INDEX idx_owner (owner_user_id)
25) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='销售线索表';

5. 跟进记录表 (follow_up)

sql
1CREATE TABLE follow_up (
2 id BIGINT PRIMARY KEY AUTO_INCREMENT,
3 related_type TINYINT NOT NULL COMMENT '关联类型:1-客户,2-商机,3-线索',
4 related_id BIGINT NOT NULL COMMENT '关联ID',
5 follow_up_type TINYINT NOT NULL COMMENT '跟进方式:1-电话,2-邮件,3-拜访,4-会议,5-其他',
6 follow_up_time DATETIME NOT NULL COMMENT '跟进时间',
7 content TEXT NOT NULL COMMENT '跟进内容',
8 next_follow_up_time DATETIME COMMENT '下次跟进时间',
9 attachment_url VARCHAR(500) COMMENT '附件URL',
10 create_user_id BIGINT NOT NULL COMMENT '创建人ID',
11 create_time DATETIME DEFAULT CURRENT_TIMESTAMP,
12 INDEX idx_related (related_type, related_id),
13 INDEX idx_create_user (create_user_id),
14 INDEX idx_create_time (create_time)
15) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='跟进记录表';

6. 合同表 (contract)

sql
1CREATE TABLE contract (
2 id BIGINT PRIMARY KEY AUTO_INCREMENT,
3 contract_no VARCHAR(50) NOT NULL UNIQUE COMMENT '合同编号',
4 contract_name VARCHAR(200) NOT NULL COMMENT '合同名称',
5 customer_id BIGINT NOT NULL COMMENT '客户ID',
6 opportunity_id BIGINT COMMENT '商机ID',
7 contract_type TINYINT NOT NULL COMMENT '合同类型:1-销售合同,2-服务合同,3-其他',
8 amount DECIMAL(15,2) NOT NULL COMMENT '合同金额',
9 start_date DATE NOT NULL COMMENT '开始日期',
10 end_date DATE NOT NULL COMMENT '结束日期',
11 sign_date DATE COMMENT '签订日期',
12 status TINYINT DEFAULT 1 COMMENT '状态:1-草稿,2-待审批,3-审批中,4-已生效,5-已终止',
13 owner_user_id BIGINT NOT NULL COMMENT '负责人ID',
14 contract_file_url VARCHAR(500) COMMENT '合同文件URL',
15 remark VARCHAR(500) COMMENT '备注',
16 create_user_id BIGINT COMMENT '创建人ID',
17 create_time DATETIME DEFAULT CURRENT_TIMESTAMP,
18 update_time DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
19 INDEX idx_contract_no (contract_no),
20 INDEX idx_customer (customer_id),
21 INDEX idx_status (status)
22) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='合同表';

7. 营销活动表 (campaign)

sql
1CREATE TABLE campaign (
2 id BIGINT PRIMARY KEY AUTO_INCREMENT,
3 campaign_no VARCHAR(50) NOT NULL UNIQUE COMMENT '活动编号',
4 campaign_name VARCHAR(200) NOT NULL COMMENT '活动名称',
5 campaign_type TINYINT NOT NULL COMMENT '活动类型:1-线上活动,2-线下活动,3-邮件营销,4-短信营销',
6 channel VARCHAR(50) COMMENT '营销渠道',
7 budget DECIMAL(15,2) COMMENT '预算',
8 actual_cost DECIMAL(15,2) COMMENT '实际花费',
9 start_time DATETIME NOT NULL COMMENT '开始时间',
10 end_time DATETIME NOT NULL COMMENT '结束时间',
11 target_audience VARCHAR(500) COMMENT '目标受众',
12 target_count INT COMMENT '目标人数',
13 actual_count INT DEFAULT 0 COMMENT '实际触达人数',
14 lead_count INT DEFAULT 0 COMMENT '产生线索数',
15 conversion_count INT DEFAULT 0 COMMENT '转化数',
16 status TINYINT DEFAULT 1 COMMENT '状态:1-计划中,2-进行中,3-已结束,4-已取消',
17 owner_user_id BIGINT NOT NULL COMMENT '负责人ID',
18 description TEXT COMMENT '活动描述',
19 create_user_id BIGINT COMMENT '创建人ID',
20 create_time DATETIME DEFAULT CURRENT_TIMESTAMP,
21 update_time DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
22 INDEX idx_campaign_no (campaign_no),
23 INDEX idx_status (status),
24 INDEX idx_time (start_time, end_time)
25) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='营销活动表';

8. 工单表 (ticket)

sql
1CREATE TABLE ticket (
2 id BIGINT PRIMARY KEY AUTO_INCREMENT,
3 ticket_no VARCHAR(50) NOT NULL UNIQUE COMMENT '工单编号',
4 title VARCHAR(200) NOT NULL COMMENT '标题',
5 customer_id BIGINT NOT NULL COMMENT '客户ID',
6 contact_id BIGINT COMMENT '联系人ID',
7 ticket_type TINYINT NOT NULL COMMENT '工单类型:1-咨询,2-投诉,3-售后,4-其他',
8 priority TINYINT DEFAULT 0 COMMENT '优先级:0-普通,1-重要,2-紧急',
9 status TINYINT DEFAULT 1 COMMENT '状态:1-待处理,2-处理中,3-待回复,4-已解决,5-已关闭',
10 channel TINYINT COMMENT '渠道:1-电话,2-邮件,3-在线客服,4-其他',
11 description TEXT COMMENT '问题描述',
12 solution TEXT COMMENT '解决方案',
13 assign_user_id BIGINT COMMENT '处理人ID',
14 create_user_id BIGINT COMMENT '创建人ID',
15 close_time DATETIME COMMENT '关闭时间',
16 satisfaction TINYINT COMMENT '满意度:1-5分',
17 create_time DATETIME DEFAULT CURRENT_TIMESTAMP,
18 update_time DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
19 INDEX idx_ticket_no (ticket_no),
20 INDEX idx_customer (customer_id),
21 INDEX idx_status (status),
22 INDEX idx_assign_user (assign_user_id)
23) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='工单表';

核心业务流程

1. 销售线索转化流程

1线索获取 → 线索评分 → 线索分配 → 跟进 → 线索转化 → 创建客户/商机
2 ↓ ↓ ↓ ↓ ↓
3(未处理) (评分完成) (跟进中) (持续跟进) (已转化)

关键步骤

  1. 获取线索(网站表单、营销活动、广告等)
  2. 线索评分(根据行业、职位、公司规模等打分)
  3. 线索分配(自动/手动分配给销售人员)
  4. 销售跟进(电话、邮件、拜访等)
  5. 线索转化(创建客户和商机)

2. 销售商机管理流程

1创建商机 → 需求分析 → 方案报价 → 谈判签约 → 成交/失败
2 ↓ ↓ ↓ ↓ ↓
3(初步接触) (需求分析) (方案报价) (谈判) (结束)

关键步骤

  1. 创建商机(从线索转化或直接创建)
  2. 需求分析(了解客户需求,评估商机价值)
  3. 方案报价(制定解决方案,提供报价)
  4. 谈判签约(商务谈判,签订合同)
  5. 成交或失败(记录结果和原因)

3. 客户服务工单流程

1创建工单 → 工单分配 → 处理中 → 待回复 → 已解决 → 关闭 → 满意度评价
2 ↓ ↓ ↓ ↓ ↓ ↓
3(待处理) (已分配) (处理中) (待回复) (已解决) (已关闭)

技术实现方案

1. 客户搜索(Elasticsearch)

使用 Elasticsearch 实现客户全文搜索:

java
1@Service
2public class CustomerSearchService {
3
4 @Autowired
5 private ElasticsearchRestTemplate elasticsearchTemplate;
6
7 /**
8 * 搜索客户
9 */
10 public PageResult<CustomerVO> searchCustomers(String keyword, int pageNum, int pageSize) {
11 // 构建搜索条件
12 NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
13
14 // 多字段搜索
15 BoolQueryBuilder boolQuery = QueryBuilders.boolQuery();
16 boolQuery.should(QueryBuilders.matchQuery("customerName", keyword))
17 .should(QueryBuilders.matchQuery("phone", keyword))
18 .should(QueryBuilders.matchQuery("email", keyword))
19 .should(QueryBuilders.matchQuery("address", keyword));
20
21 queryBuilder.withQuery(boolQuery);
22 queryBuilder.withPageable(PageRequest.of(pageNum - 1, pageSize));
23
24 // 执行搜索
25 SearchHits<CustomerDocument> searchHits = elasticsearchTemplate.search(
26 queryBuilder.build(),
27 CustomerDocument.class
28 );
29
30 // 转换结果
31 List<CustomerVO> customers = searchHits.stream()
32 .map(hit -> convertToVO(hit.getContent()))
33 .collect(Collectors.toList());
34
35 return new PageResult<>(customers, searchHits.getTotalHits(), pageNum, pageSize);
36 }
37}

2. 线索评分系统

使用 规则引擎 实现线索自动评分:

java
1@Service
2public class LeadScoringService {
3
4 /**
5 * 计算线索评分
6 */
7 public int calculateLeadScore(Lead lead) {
8 int score = 0;
9
10 // 行业评分
11 score += getIndustryScore(lead.getIndustry());
12
13 // 公司规模评分
14 score += getCompanySizeScore(lead.getCompanySize());
15
16 // 职位评分
17 score += getPositionScore(lead.getPosition());
18
19 // 来源评分
20 score += getSourceScore(lead.getSource());
21
22 // 行为评分(访问页面、下载资料等)
23 score += getBehaviorScore(lead.getId());
24
25 return Math.min(score, 100); // 最高100分
26 }
27
28 /**
29 * 行业评分
30 */
31 private int getIndustryScore(String industry) {
32 // 根据目标行业打分
33 Map<String, Integer> industryScores = Map.of(
34 "互联网", 30,
35 "金融", 25,
36 "制造业", 20,
37 "其他", 10
38 );
39 return industryScores.getOrDefault(industry, 10);
40 }
41
42 /**
43 * 公司规模评分
44 */
45 private int getCompanySizeScore(String companySize) {
46 Map<String, Integer> sizeScores = Map.of(
47 "1000人以上", 30,
48 "500-1000人", 25,
49 "100-500人", 20,
50 "100人以下", 10
51 );
52 return sizeScores.getOrDefault(companySize, 10);
53 }
54}

3. 销售漏斗分析

java
1@Service
2public class SalesFunnelService {
3
4 @Autowired
5 private OpportunityMapper opportunityMapper;
6
7 /**
8 * 获取销售漏斗数据
9 */
10 public SalesFunnelVO getSalesFunnel(Long userId, LocalDate startDate, LocalDate endDate) {
11 // 查询各阶段的商机数量和金额
12 List<OpportunityStageStats> stageStats = opportunityMapper.countByStage(
13 userId, startDate, endDate
14 );
15
16 SalesFunnelVO funnel = new SalesFunnelVO();
17
18 for (OpportunityStageStats stats : stageStats) {
19 switch (stats.getStage()) {
20 case 1: // 初步接触
21 funnel.setInitialContactCount(stats.getCount());
22 funnel.setInitialContactAmount(stats.getAmount());
23 break;
24 case 2: // 需求分析
25 funnel.setNeedsAnalysisCount(stats.getCount());
26 funnel.setNeedsAnalysisAmount(stats.getAmount());
27 break;
28 case 3: // 方案报价
29 funnel.setProposalCount(stats.getCount());
30 funnel.setProposalAmount(stats.getAmount());
31 break;
32 case 4: // 谈判
33 funnel.setNegotiationCount(stats.getCount());
34 funnel.setNegotiationAmount(stats.getAmount());
35 break;
36 case 5: // 成交
37 funnel.setWonCount(stats.getCount());
38 funnel.setWonAmount(stats.getAmount());
39 break;
40 }
41 }
42
43 // 计算转化率
44 funnel.calculateConversionRates();
45
46 return funnel;
47 }
48}

4. 营销自动化

使用 定时任务 + 消息队列 实现营销自动化:

java
1@Component
2public class MarketingAutomationTask {
3
4 @Autowired
5 private LeadService leadService;
6
7 @Autowired
8 private EmailService emailService;
9
10 @Autowired
11 private RabbitTemplate rabbitTemplate;
12
13 /**
14 * 自动跟进未处理的线索
15 */
16 @Scheduled(cron = "0 0 9 * * ?") // 每天9点执行
17 public void autoFollowUpLeads() {
18 // 查询未处理的线索(创建时间超过24小时)
19 LocalDateTime yesterday = LocalDateTime.now().minusDays(1);
20 List<Lead> unprocessedLeads = leadService.findUnprocessedLeads(yesterday);
21
22 for (Lead lead : unprocessedLeads) {
23 // 发送提醒邮件给负责人
24 rabbitTemplate.convertAndSend(
25 "crm.marketing.exchange",
26 "lead.follow.up.reminder",
27 new LeadFollowUpEvent(lead.getId(), lead.getOwnerUserId())
28 );
29 }
30 }
31
32 /**
33 * 自动发送生日祝福
34 */
35 @Scheduled(cron = "0 0 8 * * ?") // 每天8点执行
36 public void sendBirthdayGreetings() {
37 // 查询今天生日的联系人
38 List<Contact> birthdayContacts = leadService.findBirthdayContacts(LocalDate.now());
39
40 for (Contact contact : birthdayContacts) {
41 // 发送生日祝福邮件
42 emailService.sendBirthdayEmail(contact);
43 }
44 }
45}

5. 客户标签系统

java
1@Service
2public class CustomerTagService {
3
4 @Autowired
5 private CustomerMapper customerMapper;
6
7 @Autowired
8 private CustomerTagMapper customerTagMapper;
9
10 /**
11 * 自动打标签
12 */
13 @Transactional
14 public void autoTagCustomer(Long customerId) {
15 Customer customer = customerMapper.selectById(customerId);
16
17 List<String> tags = new ArrayList<>();
18
19 // 根据行业打标签
20 if ("互联网".equals(customer.getIndustry())) {
21 tags.add("互联网行业");
22 }
23
24 // 根据客户等级打标签
25 if (customer.getLevel() == 1) {
26 tags.add("重点客户");
27 }
28
29 // 根据成交金额打标签
30 BigDecimal totalAmount = customerMapper.getTotalOrderAmount(customerId);
31 if (totalAmount.compareTo(new BigDecimal("100000")) > 0) {
32 tags.add("大客户");
33 }
34
35 // 根据购买频率打标签
36 int orderCount = customerMapper.getOrderCount(customerId);
37 if (orderCount > 10) {
38 tags.add("老客户");
39 }
40
41 // 保存标签
42 for (String tagName : tags) {
43 customerTagMapper.addTag(customerId, tagName);
44 }
45 }
46}

6. 权限控制(数据权限)

java
1@Service
2public class CustomerPermissionService {
3
4 /**
5 * 检查用户是否有权限访问客户
6 */
7 public boolean hasPermission(Long userId, Long customerId) {
8 Customer customer = customerMapper.selectById(customerId);
9
10 if (customer == null) {
11 return false;
12 }
13
14 // 负责人有权限
15 if (customer.getOwnerUserId().equals(userId)) {
16 return true;
17 }
18
19 // 管理员有权限
20 if (isAdmin(userId)) {
21 return true;
22 }
23
24 // 同部门有权限(根据配置)
25 if (isSameDepartment(userId, customer.getOwnerUserId())) {
26 return true;
27 }
28
29 return false;
30 }
31}

API 接口设计

1. 客户接口

java
1@RestController
2@RequestMapping("/api/crm/customer")
3public class CustomerController {
4
5 @Autowired
6 private CustomerService customerService;
7
8 /**
9 * 创建客户
10 */
11 @PostMapping("")
12 public Result<Long> createCustomer(@RequestBody @Valid CustomerDTO dto) {
13 Long customerId = customerService.createCustomer(dto);
14 return Result.success(customerId);
15 }
16
17 /**
18 * 客户列表
19 */
20 @GetMapping("")
21 public Result<PageResult<CustomerVO>> listCustomers(
22 @RequestParam(required = false) String keyword,
23 @RequestParam(required = false) Integer level,
24 @RequestParam(required = false) Integer status,
25 @RequestParam(defaultValue = "1") Integer pageNum,
26 @RequestParam(defaultValue = "20") Integer pageSize) {
27
28 PageResult<CustomerVO> result = customerService.listCustomers(
29 keyword, level, status, pageNum, pageSize
30 );
31 return Result.success(result);
32 }
33
34 /**
35 * 客户详情
36 */
37 @GetMapping("/{customerId}")
38 public Result<CustomerDetailVO> getCustomerDetail(@PathVariable Long customerId) {
39 CustomerDetailVO vo = customerService.getCustomerDetail(customerId);
40 return Result.success(vo);
41 }
42
43 /**
44 * 添加跟进记录
45 */
46 @PostMapping("/{customerId}/follow-up")
47 public Result<Void> addFollowUp(
48 @PathVariable Long customerId,
49 @RequestBody @Valid FollowUpDTO dto) {
50
51 customerService.addFollowUp(customerId, dto);
52 return Result.success();
53 }
54}

2. 商机接口

java
1@RestController
2@RequestMapping("/api/crm/opportunity")
3public class OpportunityController {
4
5 @Autowired
6 private OpportunityService opportunityService;
7
8 /**
9 * 创建商机
10 */
11 @PostMapping("")
12 public Result<Long> createOpportunity(@RequestBody @Valid OpportunityDTO dto) {
13 Long opportunityId = opportunityService.createOpportunity(dto);
14 return Result.success(opportunityId);
15 }
16
17 /**
18 * 更新商机阶段
19 */
20 @PutMapping("/{opportunityId}/stage")
21 public Result<Void> updateStage(
22 @PathVariable Long opportunityId,
23 @RequestParam Integer stage) {
24
25 opportunityService.updateStage(opportunityId, stage);
26 return Result.success();
27 }
28
29 /**
30 * 商机成交
31 */
32 @PostMapping("/{opportunityId}/win")
33 public Result<Void> winOpportunity(
34 @PathVariable Long opportunityId,
35 @RequestBody @Valid WinOpportunityDTO dto) {
36
37 opportunityService.winOpportunity(opportunityId, dto);
38 return Result.success();
39 }
40
41 /**
42 * 商机失败
43 */
44 @PostMapping("/{opportunityId}/lose")
45 public Result<Void> loseOpportunity(
46 @PathVariable Long opportunityId,
47 @RequestParam String loseReason) {
48
49 opportunityService.loseOpportunity(opportunityId, loseReason);
50 return Result.success();
51 }
52
53 /**
54 * 销售漏斗
55 */
56 @GetMapping("/funnel")
57 public Result<SalesFunnelVO> getSalesFunnel(
58 @RequestParam(required = false) Long userId,
59 @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate startDate,
60 @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate endDate) {
61
62 SalesFunnelVO vo = opportunityService.getSalesFunnel(userId, startDate, endDate);
63 return Result.success(vo);
64 }
65}

3. 销售线索接口

java
1@RestController
2@RequestMapping("/api/crm/lead")
3public class LeadController {
4
5 @Autowired
6 private LeadService leadService;
7
8 /**
9 * 创建线索
10 */
11 @PostMapping("")
12 public Result<Long> createLead(@RequestBody @Valid LeadDTO dto) {
13 Long leadId = leadService.createLead(dto);
14 return Result.success(leadId);
15 }
16
17 /**
18 * 线索转化
19 */
20 @PostMapping("/{leadId}/convert")
21 public Result<ConvertResultVO> convertLead(
22 @PathVariable Long leadId,
23 @RequestBody @Valid LeadConvertDTO dto) {
24
25 ConvertResultVO result = leadService.convertLead(leadId, dto);
26 return Result.success(result);
27 }
28
29 /**
30 * 批量分配线索
31 */
32 @PostMapping("/batch-assign")
33 public Result<Void> batchAssignLeads(
34 @RequestBody @Valid BatchAssignDTO dto) {
35
36 leadService.batchAssignLeads(dto.getLeadIds(), dto.getUserId());
37 return Result.success();
38 }
39}

4. 数据分析接口

java
1@RestController
2@RequestMapping("/api/crm/analytics")
3public class AnalyticsController {
4
5 @Autowired
6 private AnalyticsService analyticsService;
7
8 /**
9 * 销售报表
10 */
11 @GetMapping("/sales-report")
12 public Result<SalesReportVO> getSalesReport(
13 @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate startDate,
14 @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate endDate,
15 @RequestParam(required = false) Long userId) {
16
17 SalesReportVO report = analyticsService.getSalesReport(startDate, endDate, userId);
18 return Result.success(report);
19 }
20
21 /**
22 * 客户分析
23 */
24 @GetMapping("/customer-analytics")
25 public Result<CustomerAnalyticsVO> getCustomerAnalytics() {
26 CustomerAnalyticsVO analytics = analyticsService.getCustomerAnalytics();
27 return Result.success(analytics);
28 }
29
30 /**
31 * 销售业绩排行
32 */
33 @GetMapping("/sales-ranking")
34 public Result<List<SalesRankingVO>> getSalesRanking(
35 @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate startDate,
36 @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate endDate) {
37
38 List<SalesRankingVO> ranking = analyticsService.getSalesRanking(startDate, endDate);
39 return Result.success(ranking);
40 }
41}

性能优化方案

1. 数据库优化

  • 合理建立索引(客户编号、负责人、状态等)
  • 使用读写分离
  • 对历史数据进行分区
  • 定期归档历史数据

2. 缓存优化

  • 缓存客户基础信息
  • 缓存用户权限数据
  • 缓存统计数据(短时缓存)

3. 搜索优化

  • 使用 Elasticsearch 实现全文搜索
  • 异步更新搜索索引

4. 大数据分析

  • 使用 ClickHouse 存储分析数据
  • 定时同步数据到 ClickHouse
  • 复杂报表查询走 ClickHouse

扩展功能

1. AI 智能推荐

  • 智能线索分配(根据销售特长、历史成交率等)
  • 智能商机预测(预测成交概率)
  • 智能客户画像

2. 移动端支持

  • 移动端 APP(React Native / Flutter)
  • 外勤签到
  • 移动审批

3. 集成第三方系统

  • 邮件系统集成(发送/接收邮件)
  • 短信平台集成
  • 企业微信/钉钉集成
  • 财务系统集成

4. 高级分析

  • 客户流失预警
  • RFM 客户分析
  • 客户生命周期价值分析
  • 销售预测

总结

CRM 系统的核心在于:

  1. 以客户为中心:所有功能围绕客户展开
  2. 销售流程规范化:通过系统规范销售流程,提高销售效率
  3. 数据驱动决策:通过数据分析为决策提供支持
  4. 营销自动化:提高营销效率,降低营销成本
  5. 客户满意度提升:通过优质服务提升客户满意度

本设计方案基于 Spring Cloud 微服务架构,采用主流技术栈,可满足中大型企业的客户关系管理需求。

评论