第1章:模块与埋点状态的定义

1.1 模块边界划分

在Android大型工程中,模块间埋点状态流转的核心问题是边界定义。没有清晰的模块边界,状态就会混乱、重复、丢失。

边界类型 定义 示例
物理边界 Gradle模块(api/implementation依赖) :feature:login、:core:tracking
逻辑边界 业务领域上下文 登录域、支付域、搜索域
运行时边界 进程/线程/生命周期边界 主进程与推送进程分离
关键原则:物理边界决定编译时依赖,逻辑边界决定状态名称空间,运行时边界决定状态同步方式。三个边界必须对齐,否则会出现跨模块状态穿透问题。

1.2 埋点事件类型

每个模块产生的埋点事件可以按职责分为四类,这四类是状态流转的基本单元:

  1. 行为事件(Action Event):用户或系统的显式操作,如点击、滑动、网络请求完成。
  2. 状态事件(State Event):某个模块内部状态发生变化,如登录态从“未登录”变为“已登录”。
  3. 边界事件(Boundary Event):跨模块的入口/出口事件,如从主页模块进入详情模块。
  4. 元事件(Meta Event):描述埋点系统自身行为的控制事件,如初始化完成、缓存命中失败。

在架构上,状态事件和边界事件是需要跨模块流转的核心类型,其余两类一般只在模块内部消费。

1.3 状态实体定义

状态实体是埋点状态流转中携带的数据载体。一个完整的状态实体必须包含以下字段:

// 伪代码:埋点状态实体定义
class TrackState {
    String eventId;          // 全局唯一事件ID
    String moduleId;         // 产生模块标识
    String eventType;        // 事件类型枚举
    long timestamp;          // 事件发生时间戳
    String stateKey;         // 状态键,如 "login_status"
    String stateValue;       // 状态值,如 "logged_in"
    Map<String, String> metadata;  // 扩展元数据
    String traceId;         // 全局追踪链路ID
}
核心约定:所有模块必须使用统一的状态实体格式进行跨模块传递,禁止自定义结构。通过强制 eventId 全局唯一和 traceId 链路追踪,可以解决埋点数据丢失后难以定位的问题。

1.4 模块间埋点状态流转结构

下图展示了在一个多模块Android工程中,埋点状态从产生到消费的完整流转路径:

模块间埋点状态流转结构图 业务模块A 登录/注册 行为事件, 状态事件 业务模块B 支付/订单 状态事件, 边界事件 业务模块C 搜索/推荐 埋点SDK 事件校验 状态缓存 序列化/反序列化 信任验证 状态总线 事件订阅/发布 跨模块状态同步 事件路由 信任链路: 埋点SDK校验→状态总线分发 →消费者模块回溯验证
常见风险:模块在没有通过埋点SDK的情况下直接操作状态总线,会导致信任链路断裂。所有埋点事件必须经过埋点SDK的校验和封装,才能发布到状态总线。

1.5 落地第一阶段的验收标准

验收项 标准 验证方式
模块边界清单 所有参与流转的模块已列出物理边界与逻辑边界 架构评审文档
事件类型定义 四类事件已明确区分,且跨模块事件已标识 代码扫描(检查事件类型枚举)
状态实体格式 所有模块使用统一的TrackState结构 Lint规则 + Code Review
信任链路 埋点SDK作为唯一入口,状态总线不可被模块直接调用 架构约束验证测试

1.6 选型权衡:统一SDK vs 分散上报

维度 统一埋点SDK(推荐) 分散上报
维护成本 低(集中管理) 高(各模块自建)
信任链路 强(中心校验) 弱(难以统一验证)
灵活性 中(需遵守SDK规范) 高(可自定格式)
跨模块流转 原生支持 需要额外适配
适合规模 大型工程(模块 > 20) 小型工程或实验性项目

在第一章节中,我们通过定义清晰的模块边界、事件类型和状态实体格式,为后续的跨模块状态流转打下基础。下一步将进入“分层职责”的讨论,确立各层在状态流转中的具体角色。