CRM Customer Relationship Management
Core Positioning
CRM is the sales team’s “command center.” From a single lead, to converting into a customer, creating an opportunity, signing a contract, and receiving payment — the entire sales funnel is visualized here. Combined with the public pool mechanism, it prevents customer resources from being “hoarded” by individual salespeople.
In one sentence: Help your sales team say goodbye to managing customers in Excel, and make every deal traceable.
Problems Solved
| Pain Point | How CRM Solves It |
|---|---|
| Customer info scattered in salespeople’s personal WeChat/Excel | Unified customer database, no data loss during handover |
| Sales collision, multiple people following the same customer | Customer lock mechanism + public pool rules |
| No visibility into what salespeople do daily | Follow-up records, visit records fully logged |
| Unclear which part of the sales funnel has issues | Lead→Customer→Opportunity→Contract conversion rate visualization |
| Chaotic payment collection management | Contract → Payment Plan → Payment Record full chain |
User Roles
graph LR
subgraph Roles
SALES["Salesperson
Follow up on leads and customers
Create opportunities and contracts
Record follow-ups and payments"] MANAGER["Sales Manager
Assign leads and customers
Approve contracts
View team data"] ADMIN4["Administrator
Configure public pool rules
Manage product catalog
Data statistics and analysis"] end
Follow up on leads and customers
Create opportunities and contracts
Record follow-ups and payments"] MANAGER["Sales Manager
Assign leads and customers
Approve contracts
View team data"] ADMIN4["Administrator
Configure public pool rules
Manage product catalog
Data statistics and analysis"] end
Complete Sales Process
flowchart LR
A["🔍 Lead
Potential customer source"] -->|Convert| B["👤 Customer
Official customer"] B -->|Create| C["💼 Opportunity
Sales opportunity"] C -->|Advance| D["📝 Contract
Signing"] D -->|Collect| E["💰 Payment
Funds received"] A -.->|Invalid| X1["❌ Invalid Lead"] B -.->|Long-term no follow-up| X2["🌊 Falls into Public Pool"] X2 -.->|Claimed by other salesperson| B C -.->|Lost| X3["❌ Close Opportunity"]
Potential customer source"] -->|Convert| B["👤 Customer
Official customer"] B -->|Create| C["💼 Opportunity
Sales opportunity"] C -->|Advance| D["📝 Contract
Signing"] D -->|Collect| E["💰 Payment
Funds received"] A -.->|Invalid| X1["❌ Invalid Lead"] B -.->|Long-term no follow-up| X2["🌊 Falls into Public Pool"] X2 -.->|Claimed by other salesperson| B C -.->|Lost| X3["❌ Close Opportunity"]
Core Table Structure (ER Diagram)
erDiagram
CRM_CLUE ||--o| CRM_CUSTOMER : "Converted to"
CRM_CUSTOMER ||--o{ CRM_CONTACT : "Has"
CRM_CUSTOMER ||--o{ CRM_BUSINESS : "Creates"
CRM_BUSINESS ||--o{ CRM_CONTRACT : "Advances to"
CRM_CONTRACT ||--o{ CRM_RECEIVABLE : "Payment"
CRM_CONTRACT ||--o{ CRM_RECEIVABLE_PLAN : "Payment Plan"
CRM_CLUE {
bigint id PK
varchar name "Lead Name"
varchar mobile "Phone Number"
tinyint status "Status"
bigint owner_user_id FK "Owner"
}
CRM_CUSTOMER {
bigint id PK
varchar name "Customer Name"
tinyint level "Customer Level"
bigint owner_user_id FK "Owner"
}
CRM_CONTACT {
bigint id PK
bigint customer_id FK
varchar name "Contact Name"
varchar mobile "Phone Number"
}
CRM_BUSINESS {
bigint id PK
bigint customer_id FK
varchar name "Opportunity Name"
decimal total_price "Estimated Amount"
tinyint status "Stage"
}
CRM_CONTRACT {
bigint id PK
bigint business_id FK
varchar no "Contract Number"
decimal total_price "Contract Amount"
tinyint status "Status"
}
CRM_RECEIVABLE {
bigint id PK
bigint contract_id FK
decimal price "Payment Amount"
datetime time "Payment Time"
}
Public Pool Mechanism
flowchart TB
CUSTOMER["Customer"] -->|Salesperson following up| PROTECTED["Protection Period
Other salespeople cannot claim"] PROTECTED -->|No follow-up for N days| SEA["Public Pool
Visible to all salespeople"] PROTECTED -->|Deal Closed| DEAL["Locked
Permanently assigned to this salesperson"] SEA -->|Claimed by other salesperson| PROTECTED SEA -->|Reached customer limit| LIMIT["Exceeded personal customer limit
Cannot claim"]
Other salespeople cannot claim"] PROTECTED -->|No follow-up for N days| SEA["Public Pool
Visible to all salespeople"] PROTECTED -->|Deal Closed| DEAL["Locked
Permanently assigned to this salesperson"] SEA -->|Claimed by other salesperson| PROTECTED SEA -->|Reached customer limit| LIMIT["Exceeded personal customer limit
Cannot claim"]
| Rule | Description |
|---|---|
| Auto-Release | If no follow-up for N days, customer automatically falls into public pool |
| Advance Reminder | Remind salesperson to follow up before deadline |
| Lock Protection | Closed-deal customers permanently locked, will not fall into public pool |
| Customer Limit | Each salesperson has a maximum customer count limit to prevent hoarding |
| Scheduled Task | Background scheduled scan and execution of public pool release logic |
Data Permissions
CRM uses an owner mechanism for data isolation:
- Each customer/lead/opportunity/contract has an
owner_user_idfield - Salespeople can only see their own data
- Sales managers can see team data
- Administrators can see all data
- Supports transfer operation: transfer customers to other salespeople
Feature List
| Module | Features |
|---|---|
| Lead Management | Lead entry, assignment, conversion, invalid marking |
| Customer Management | Customer info, contacts, follow-up records, locking |
| Public Pool Customers | Public pool, claiming, release rules |
| Opportunity Management | Opportunity stages, estimated amount, win/loss |
| Contract Management | Contract creation, approval, changes |
| Payment Management | Payment plans, payment records, receivables statistics |
| Product Management | Product catalog, pricing |
| Data Statistics | Funnel analysis, performance statistics |