commit 3d013fd0b7bb8a4ec431c733349f74bac0c9a94b Author: 浅念 Date: Tue Sep 15 09:51:36 2026 +0800 docs: 客户行为采集平台设计文档(M1/M2/M3 需求基线) Co-Authored-By: Claude Code diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..a51f6fc --- /dev/null +++ b/.gitignore @@ -0,0 +1,5 @@ +_extract_*.txt +__pycache__/ +*.pyc +node_modules/ +.env diff --git a/docs/superpowers/specs/2026-09-15-customer-behavior-platform-design.md b/docs/superpowers/specs/2026-09-15-customer-behavior-platform-design.md new file mode 100644 index 0000000..686bc4e --- /dev/null +++ b/docs/superpowers/specs/2026-09-15-customer-behavior-platform-design.md @@ -0,0 +1,291 @@ +# 客户行为采集平台 · 设计文档 + +- 日期:2026-09-15 +- 状态:待评审 +- 关联文档:`docs/客户行为数据采集平台完整项目实施方案.docx`、`docs/客户行为数据采集平台方案实施报告.docx`(需求基线,本设计在其基础上按实际约束裁剪落地) + +## 1. 项目目标 + +构建一个**第一方客户行为数据采集平台**:网站引入自研 JS SDK,采集访客行为轨迹与环境信息,写入独立后台数据库;后台基于 Art Design Pro 构建管理控制台,提供访客/客户的跨天行为时间线、来源归因、有效停留统计和客户档案管理。 + +核心业务问题:**"这个客户从哪来、看过什么、哪天来过、每次停多久、在哪儿流失、什么时候变成了线索"**。 + +## 2. 已确认的决策 + +| 维度 | 决策 | +|---|---| +| 形态 | 通用 JS SDK(网站引入)+ 独立后台 | +| 后端 | Python · Django + DRF | +| 数据库 | MySQL 8(复用 1Panel 现有容器),事件表按月分区 | +| 前端 | Art Design Pro(Vue3 + TypeScript + Element Plus + Pinia + ECharts) | +| 部署 | 阿里云 ECS · 1Panel · Docker Compose(Nginx 静态 + 反代 Django) | +| 规模策略 | 先小后大;单组织多站点,表结构带 `site_id` 留多站点扩展位 | +| 实时性 | 准实时(事件分钟内可见,最近 5 分钟活跃作为"在线"口径) | +| 客户识别 | 表单提交(询盘/留言)为主;邮件专属链接识别(M2);登录绑定(P2) | +| 缓存 | M1 不引入 Redis;M2 起可选(限流/缓存加固) | + +### 2.1 与原方案文档的差异 + +| 原文档建议 | 本设计 | 理由 | +|---|---|---| +| Node.js 后端 | Django + DRF | 团队技术选型 | +| PostgreSQL | MySQL 8 | 现有 1Panel 环境;JSON 类型 + 按月分区满足当前量级 | +| React/Next.js 后台 | Art Design Pro | 指定模板,自带权限/菜单/主题体系 | +| 多租户 SaaS 就绪 | 单组织多站点 | 先自用,不为 SaaS 付复杂度 | +| Redis 起步必备 | M2 可选 | 先小后大 | + +**明确砍掉/推迟**(首期不做):多租户组织管理、ClickHouse、同意管理平台(CMP)、Webhook、会话回放、浏览器指纹身份追踪、营销自动化、机器学习评分。 + +**保留的治理底线**(不可裁剪):敏感字段黑名单双重拦截、确定性合并原则、数据保留期限与清理、客户删除流程、隐私告知。 + +## 3. 系统架构 + +``` +┌─────────────────────────────────────────────┐ +│ 网站浏览器 │ +│ JS SDK(自研 ~10KB,异步加载,绝不阻塞页面) │ +└──────────────────┬──────────────────────────┘ + │ HTTPS 批量 JSON 上报 + ▼ +┌─────────────────────────────────────────────┐ +│ 阿里云 ECS · 1Panel · Docker │ +│ Nginx │ +│ ├─ 静态:Art Design Pro 打包产物 │ +│ └─ /api/* ──► Django + DRF │ +│ ├─ 采集接口(公开、域名白名单、限流)│ +│ ├─ 管理接口(JWT 登录) │ +│ └─ 后台任务(会话化/聚合/清理) │ +│ │ │ +│ ▼ │ +│ MySQL 8(events 按月分区) │ +└─────────────────────────────────────────────┘ +``` + +- 开发期:Vite 代理解决跨域;部署期同域无跨域问题。 +- 响应格式适配 Art Design Pro 的 `{code, data, message}` 约定。 +- 升级路径:事件量到瓶颈时把采集接口拆为独立 FastAPI 服务,SDK 协议不变。 + +## 4. JS SDK 设计 + +### 4.1 接入方式(两行) + +```html + + +``` + +### 4.2 身份模型 + +- `visitor_id`:加密安全随机数,存 localStorage(第一方存储,不用 Cookie+localStorage 双恢复对抗用户清除)。 +- `session_id`:30 分钟无活动切新会话;跨天访问 = 新会话、同一 visitor。 +- 首次落地时保存**首触来源**(referrer + UTM + 落地页)到访客档案;每次会话各自记录来源。 + +### 4.3 事件清单 + +| 事件 | 优先级 | 字段要点 | +|---|---|---| +| `page_view` | P0 | path、title、referrer、UTM;SPA 路由变化触发(P1) | +| `page_stay` | P0 | `active_ms` 有效停留:页面可见 + 有鼠标/键盘/滚动活动才累计;`visibilitychange` 停止;`sendBeacon` 兜底上报 | +| `scroll_depth` | P1 | 25/50/75/100% 四档 | +| `click` | P1 | 可配置范围(按钮/导航/外链/下载),`data-track-id` 优先标识 | +| `form_start` / `form_submit` | P1 | 表单标识、字段名清单、成功/失败;字段值**白名单制** | +| `copy` / `download` / `print` | P1 | 意图事件:复制了邮箱/电话、下载报价单 PDF、打印页面 | +| `rage_click` / `dead_click` | P2 | 反复点无反应区域 | +| `first_interaction` | P1 | 进页面后首次互动耗时 | +| `form_field_drop` | P1 | 表单在哪个字段放弃、是否粘贴、是否自动填充 | +| `identify_hit` | P1 | 邮件专属链接 token 命中(见 5.3) | +| `sdk_loaded` | P0 | 诊断事件:SDK 版本、初始化耗时 | + +### 4.4 环境信息(首次访问携带) + +设备类型、OS + 版本、浏览器 + 版本、屏幕分辨率、语言、时区、触屏、CPU 核心数、设备内存(可选开)、Client Hints(设备型号)、网络类型/下行/RTT(`navigator.connection`)、页面性能(Navigation Timing)。 + +### 4.5 传输可靠性 + +- 内存队列 → 批量发送(10 条或 15 秒触发);页面隐藏 `sendBeacon`,需自定义头时 `fetch keepalive`。 +- 每事件 UUID `event_id`,服务端按 `site_id + event_id` 幂等去重。 +- 失败指数退避重试(上限 3 次);4xx 不重试;离线队列超限按最旧丢弃并记本地丢弃计数。 +- 客户端时间仅作排序参考,服务端另存 `received_at` 并标记时钟偏差。 +- SDK 全部逻辑 try/catch 包裹,任何异常不影响宿主网站。 + +### 4.6 隐私与安全红线(SDK 端) + +- 不采集:password/hidden/file/autocomplete 敏感字段值、验证码、银行卡、身份证。 +- URL 清洗:含邮箱/手机号/令牌类查询参数在入库前删除或哈希。 +- 不做:键盘逐键记录、剪贴板读取、摄像头/麦克风、浏览器指纹身份追踪(弱指纹仅用于爬虫识别,不参与身份关联)。 +- 免费文本默认不采集,需逐项白名单。 + +## 5. 身份识别与客户合并 + +### 5.1 身份层级 + +``` +visitor_id(匿名浏览器) + └─ session_id(每次访问) + └─ events +contact(客户档案)── identity 关联表 ── visitor_id / 邮箱哈希 / 手机号哈希 +``` + +### 5.2 表单识别(M2 主路径) + +``` +匿名访客逛了 3 天 → 第 4 天提交询盘表单 +→ 白名单字段值(姓名/邮箱/电话)创建客户档案 +→ 同邮箱/手机号已存在则归并,不建重复档案 +→ 该 visitor_id 全部历史轨迹自动归入客户名下 +→ 后续访问持续追加到同一档案 +``` + +- 表单字段值浏览器端采集(询盘线索场景够用 + 垃圾过滤:粘贴检测/Honeypot/频率)。 +- **订单、支付、注册成功等业务事实必须走服务端签名 API(P2)**,浏览器事件不作事实依据。 + +### 5.3 邮件专属链接识别(M2) + +开发信/WhatsApp/社媒发 `https://site/?ctk_token=<专属token>` 链接;对方点开即触发 `identify_hit`,立即把匿名轨迹归到对应客户档案——比等表单提交更早识别。 + +### 5.4 合并规则 + +- **只做确定性合并**:邮箱/手机号/token/user_id。IP、城市、设备相似**绝不自动合并**,仅作线索提示。 +- 手动认领:后台把匿名访客轨迹认领给客户,支持解除;操作记审计。 +- 多个 visitor_id 绑定同一邮箱 → 汇入同一 contact(跨设备视图)。 +- 每次 merge/认领/解除记录操作者、时间、规则版本。 + +## 6. 来源归因(四层) + +1. **自动 referrer**:提取来路域名(google.com / 合作伙伴站 / 微信内置浏览器 / 直接访问)。 +2. **UTM 参数**:utm_source / medium / campaign / term / content,外投链接统一带参。 +3. **首触 + 会话来源**:访客/客户档案永久记录首触来源;每次会话各自记录(时间线可见"第 N 次访问来自 X")。 +4. **渠道规则映射 + 手动标记**:后台配置 `域名 → 渠道名` 规则表(google.com → 自然搜索等);支持手动改/手动标(线下展会、referrer 丢失场景)。 + +已知边界:referrer 被剥(部分隐私工具/HTTPS→HTTP/微信)记为"直接访问";要 100% 可靠归因用 UTM 链接。 + +## 7. 匿名访客可采集信息全景 + +| 类别 | 内容 | +|---|---| +| 身份标识 | visitor_id、session_id、新/回访、访问次数、首末次访问、活跃天数 | +| 行为轨迹 | 页面浏览及路径、每页有效停留、滚动深度、点击、表单行为(开始/放弃字段/提交)、意图事件(复制/下载/打印) | +| 来源 | referrer 域名、UTM、落地页、部分搜索词 | +| 设备环境 | 设备类型、OS/浏览器及版本、分辨率、语言、时区、触屏、硬件(可选)、Client Hints、网络质量、页面性能 | +| 网络地理(服务端) | IP(保留期限见 9.2)、国家/省/市(ip2region 离线库)、运营商、爬虫识别 | +| 跨站关联 | 同一访客在自有多个域名间串联(首方合法做法) | + +拿不到(诚实边界):匿名阶段真实身份(姓名/邮箱/电话);跨设备同一人(直到提交表单/登录/token 命中);清存储/无痕后重新开始(不对抗)。 + +## 8. 管理控制台(Art Design Pro 页面) + +| # | 页面 | 优先级 | 内容 | +|---|---|---|---| +| C1 | 登录/权限 | P0 | JWT;管理员/普通成员两角色起步(复用模板权限体系) | +| C2 | 总览 Dashboard | P0 | 今日/7日/30日 PV、UV、会话数、新访客比;最近 5 分钟活跃(准实时在线);趋势图 | +| C3 | 访客列表(匿名) | P0 | 访客 ID、首末次访问、会话数、来源、位置、设备 | +| C4 | 访客/会话详情 | P0 | 单访客跨天时间线 + 单会话页面路径(**M1 验收核心**) | +| C5 | 站点管理 | P0 | 站点 CRUD、site_id 签发、域名白名单 | +| C6 | 客户列表 | P1 | 姓名/邮箱/手机号脱敏、首末次访问、访问次数、总停留、最近来源、标签筛选、搜索 | +| C7 | 客户详情 | P1 | 跨天时间线(日期分组)+ 会话列表 + 设备/地理位置 + 首触来源 + 标签备注 | +| C8 | 事件调试流 | P1 | 原始事件流(含拒绝原因、时延),开发调试用 | +| C9 | 标签/备注 | P1 | 客户打标签、跟进备注 | +| C10 | 渠道规则 | P1 | 域名→渠道映射配置 | +| C11 | 专属链接生成 | P1 | 给客户/活动生成带 token 的识别链接 | +| C12 | 数据导出 | P2 | 客户列表/时间线 CSV | +| C13 | 事件字典 | P2 | 事件 schema 登记 | + +客户时间线样式(原样采用文档 8.2): + +``` +09-01 10:20 首次访问产品 A 页面 来源 Google Ads +09-01 10:24 查看价格页 有效停留 2 分 18 秒 +09-02 16:10 再次访问案例页面 +09-02 16:15 询盘提交成功 身份识别为 customer@example.com +``` + +## 9. 数据治理 + +### 9.1 敏感字段黑名单 + +SDK 端 + 服务端**双重拦截**:password/验证码/银行卡/身份证等永不入库;服务端对 properties 做体积/数量/长度/深度校验,未知字段拒绝或隔离并记原因。 + +### 9.2 数据保留(默认值,站点可配) + +| 数据 | 保留期 | +|---|---| +| 原始事件(events 分区) | 180 天,分区清理 | +| 原始 IP | 180 天,到期后台任务截断为 /24 前缀;地理/运营商解析结果长期保留 | +| 客户档案、标签、备注 | 长期(直至客户删除) | +| 审计日志 | 1 年 | + +### 9.3 客户删除 + +删除客户档案 + 关联事件(标记删除 + 异步物理清理),记录审计;导出留档。 + +### 9.4 隐私告知 + +提供隐私政策/Cookie 告知文案模板;SDK 预留 `consent` 开关接口(同意管理模式 P2 完善化);第三方脚本不可绕过同意状态。 + +## 10. 数据库核心表(MySQL 8) + +| 表 | 要点 | +|---|---| +| `site` | 站点、site_id、域名白名单、采样配置 | +| `visitor` | visitor_id、首触来源、首次/最近访问、环境摘要 | +| `session` | session_id、visitor、开始/结束、来源、落地页、会话时长 | +| `events`(按月分区) | event_id(site 内唯一幂等键)、visitor、session、contact(可空)、event_type、occurred_at、received_at、path、properties JSON | +| `contact` | 客户档案:姓名、邮箱(规范化+加盐哈希列)、电话(同)、公司(可由邮箱域名推导)、标签、备注、负责人 | +| `identity_map` | visitor_id / 邮箱哈希 / 电话哈希 / token ↔ contact 关联 + 合并审计字段 | +| `track_token` | 专属链接 token ↔ contact | +| `daily_stats` / `session_rollup` | 聚合派生表(日指标、会话摘要),避免报表扫 events | +| `admin_user` / `audit_log` | 后台账号、审计 | + +索引原则:时间线 `(site_id, visitor_id/contact_id, occurred_at DESC)`;会话 `(site_id, visitor_id, started_at DESC)`;高频筛选字段独立列,长尾属性进 JSON。 + +## 11. API 概览 + +| 接口 | 说明 | +|---|---| +| `POST /api/collect/batch` | 浏览器批量上报:校验站点状态/域名白名单/体积/限流/幂等去重/黑名单 → 入库 | +| `POST /api/collect/identify` | token 命中识别(M2) | +| 管理接口 `/api/admin/*` | JWT;站点、访客、客户、事件调试、标签、渠道规则、导出、Dashboard 聚合 | + +采集接口返回最小响应(成功/失败 + 稳定错误码),不向匿名调用方泄露配置或客户数据。site_id 是公开标识,只用于归属,不赋予任何读取权限。 + +## 12. 非功能需求 + +- SDK 体积 ≤ 15KB(gzip),初始化不阻塞首屏;加载失败对网站零影响。 +- 采集接口:日均 10 万事件内单 Django 实例 + MySQL 从容承载;监控接受率、去重率、拒绝原因分布。 +- 准实时:事件从发生到后台可见 ≤ 60 秒(列表刷新即得,无长连接)。 +- 部署:1Panel Docker Compose(Nginx + Django/uwsgi 或 gunicorn + 复用 MySQL 容器);.env 管理密钥;数据库迁移向前兼容。 +- 备份:MySQL 自动备份 + 恢复演练(复用 1Panel 能力)。 + +## 13. 里程碑 + +### M1 · 最小闭环(端到端技术验证) +- SDK:接入两行代码、visitor/session 身份、page_view、page_stay、批量传输、幂等去重、UTM/referrer 首触记录、环境信息。 +- 后端:采集 API(域名白名单/限流/黑名单校验)、核心表、会话化与日聚合任务。 +- 后台:C1 登录权限、C2 总览、C3 访客列表、C4 访客/会话详情、C5 站点管理。 +- **验收**:一个真实网站接入,后台能看到"某访客今天看了 3 页、每页停多久、昨天来过、首触来源是 Google"。 + +### M2 · 完整产品(客户识别 + 完整后台) +- SDK:click、scroll、SPA 路由、表单事件(含字段放弃/粘贴/自动填充)、意图事件(复制/下载/打印)、first_interaction、URL 清洗、track/identify/reset API。 +- 身份:表单→客户档案创建与归并、邮箱/手机号去重、邮件专属链接识别、手动认领/解除、合并审计。 +- 后台:C6 客户列表、C7 客户详情、C8 事件调试流、C9 标签备注、C10 渠道规则、C11 专属链接生成。 +- 治理:IP 保留期任务、客户删除流程、隐私告知模板。 +- **验收**:询盘表单提交后客户档案自动生成并归并全部历史轨迹;专属链接点开即识别。 + +### M3 · 增强与扩展 +- rage/dead click、远程配置(采样/开关,ETag)、npm 包发布。 +- 服务端签名事件 API(订单/注册事实)、WordPress 连接器插件(注入 SDK + CF7/WPForms 钩子)。 +- IP 企业反查(Leadfeeder 式 B2B 线索提示,可选付费库,只提示不自动合并)、邮箱后缀→公司名补全。 +- 数据导出、事件字典、Redis 限流加固、(独立评估)会话回放。 + +## 14. 风险与开放项 + +| 项 | 状态 | +|---|---| +| 表单字段值浏览器端先行、签名机制 P2 | 已决策 | +| 原始 IP 默认保留 180 天后截断(站点可配) | 已决策(默认值) | +| 微信内置浏览器 referrer 常缺失 | 已知边界,用 UTM 专属链接兜底 | +| 主要访客区域与跨境合规 | 上线前按原方案文档第十章做一次专项确认 | +| 事件量超预期 | 升级路径已定:FastAPI 采集拆分 → 分区细化 → 聚合下沉 |