# Backend Design: ECR-007 运营行为分析 Ops-B > Architect 产出;Engineer 只消费本文件。 > 实现纪律:`$ESS_ROOT/technology-governance/BACKEND_STANDARD.md` > 项目分层权威:`.ai/architecture.md` · Handler → Service → Repository | Field | Value | |-------|-------| | ID | BD-2026-007 | | ECR | ECR-007 | | Change Level | L2 | | Status | Approved(2026-08-07 Human) | | Author | Architect | | Date | 2026-08-07 | | Risk | Medium | --- ## Context - 问题 / 目标:缺自有行为数据与运营看板;需页停留、退出页、点击、会话级指标。 - 非目标:CMS/RBAC/OLAP/热力图;见 ECR Forbidden。 - 相关 Spec:`ops-analytics.md`;无新 ADR(Postgres 足够,栈不变)。 ## Architecture Change - 是否改变分层边界:No - 受影响层:API · Application(`service/analytics` + admin 扩展)· Infrastructure(repo + migration)· UI(user-h5 analytics · admin-h5 数据页) ## Module Changes | Module | Layer | Change | Must NOT | |--------|-------|--------|----------| | `handler` analytics ingest | API | bind、DeviceAuth、调 service | SQL;业务规则堆 handler | | `service/analytics` | Application | 校验批量、截断、写 session/event | 直连 gin | | `repository/analytics_repo.go` | Infrastructure | SQL ingest + 聚合 | 泄漏到 UI | | `handler/admin` analytics GET | API | AdminAuth | Device 用户可访问 | | `user-h5/lib/analytics.ts` | UI | 队列上报 | 直打 DB;传 PII | | `admin-h5` 数据页 | UI | 展示聚合 | 裸拼绝对 API URL | ## Data Flow ```text user-h5 analytics queue → POST /api/v1/analytics/events (X-Device-Key [+ Bearer]) → service/analytics → AnalyticsRepo → analytics_events / analytics_sessions admin-h5 「数据」 → GET /api/v1/admin/analytics/* (Admin Bearer) → service/admin 或 service/analytics 只读聚合 → SQL group by day / page_path / element_id / funnel names ``` ## API Changes - 契约:`proto/openapi.yaml` 增补 - 兼容:纯新增路径 - 信封:`{code,message,data}` ### Ingest(示意) `POST /api/v1/analytics/events` Body: `{ items: [{ name, session_id, page_path?, client_ts, props? }] }` 上限:≤100/请求;超限 400。 ### Admin 聚合 | Path | data 要点 | |------|-----------| | `/admin/analytics/overview?from&to` | dau, new_users, sessions, avg_session_ms | | `/admin/analytics/pages` | page_path, pv, uv, avg_dwell_ms, exit_count | | `/admin/analytics/exits` | exit_page, count | | `/admin/analytics/clicks` | element_id, count | | `/admin/analytics/funnel` | steps[] name+count | ## Database Changes - `analytics_sessions` · `analytics_events` - 可选 `analytics_daily_page`(实现期若查询慢再加,仍属本 ECR 允许) - Migration:`000013_analytics_ops.up.sql` / `.down.sql` - Immutable:events 只追加;不提供删除 API ## Migration Plan - Required:YES - 步骤:expand 建表 → 部署 API → 开 H5 上报 → admin 看板 - 回滚:关上报 + 下线路由 + down migration(非生产可) ## Failure Handling - ingest 部分非法条目:整批 400 或跳过非法并计 dropped(选定一种写进实现注释,默认整批 400) - 未鉴权 Device:401 - Admin 无 token:401 - DB 错:500;客户端 track 吞错 ## Test Plan - Unit:props 截断、dwell 非负 - Integration:login device → post events → admin overview/pages/exits - H5:analytics 队列 flush mock ## Rollback Plan 见 ECR Rollback。 --- ## Backend Change Boundary(mandatory) ```text Change Level: L2 Change: 自有 analytics ingest + admin 聚合看板 Affected: Domain: - AnalyticsSession / AnalyticsEvent Application: - service/analytics · admin analytics reads Infrastructure: - AnalyticsRepo · migration 000013 API: - POST /api/v1/analytics/events - GET /api/v1/admin/analytics/* Migration: Required Tests: - ingest + admin aggregate path Risk: Medium ``` ## Architecture Regression Check - [ ] 无 Handler 直连 DB - [ ] 无绕过 Service - [ ] Admin / Device 鉴权面隔离 - [ ] 未引入非默认中间件 - [ ] 未简化分层