datai/datai-scenes/datai-scene-salesforce/docs/decisions/2026-02-03-002-05-ADR-Flow覆盖率技术选型.md

7.7 KiB
Raw Permalink Blame History

ADR-002-05: Flow 覆盖率技术选型

状态

已接受

日期

2026-02-03

背景

Flow 覆盖率功能需要选择合适的技术方案,满足以下要求:

  1. 支持查询和统计 Salesforce Flow 的测试覆盖率数据
  2. 支持按 Flow 名称、类型、命名空间等多维度查询
  3. 提供覆盖率统计和聚合分析能力
  4. 与 002-03测试执行功能的数据模型兼容
  5. 与 002-04代码覆盖率功能保持架构一致性
  6. 确保查询性能和数据一致性

需求约束

  1. 支持分页查询,避免大数据量查询导致性能问题
  2. 支持多条件筛选testResultId、flowName、type、namespace、coverage范围
  3. 提供总体覆盖率统计功能
  4. 提供按类型统计功能
  5. 支持 Flow 覆盖率警告查询
  6. 与现有技术栈保持一致

决策

决策 1数据库表策略

选择方案 1创建独立的 Flow 覆盖率表

  • 创建独立的 datai_apex_flow_coverage 表存储 Flow 覆盖率数据
  • 创建独立的 datai_apex_flow_coverage_warning 表存储 Flow 覆盖率警告
  • 不与代码覆盖率表合并

理由:

  1. 数据模型差异Flow 覆盖率与代码覆盖率的数据模型不同Flow 使用 numElements 而不是 numLocations
  2. 查询独立性:独立的表结构便于针对 Flow 特性进行查询优化
  3. 扩展性:未来 Flow 覆盖率可能有特有的字段需求,独立表更易于扩展
  4. 数据隔离:代码覆盖率和 Flow 覆盖率是不同类型的数据,分开存储更清晰

放弃方案 2复用代码覆盖率表的理由

  1. Flow 覆盖率和代码覆盖率的字段差异较大numElements vs numLocations
  2. 合并会导致表结构复杂,增加空字段
  3. 查询时需要额外的类型区分逻辑
  4. 不利于针对 Flow 特性的查询优化

决策 2Service 层设计策略

选择方案 1独立 Service 层

  • 创建独立的 IApexFlowCoverageService 接口和 ApexFlowCoverageServiceImpl 实现
  • ApexCodeCoverageService 分离,职责更清晰

理由:

  1. 单一职责原则Flow 覆盖率功能与代码覆盖率功能是不同的业务领域
  2. 可维护性:独立的 Service 层便于维护和扩展
  3. 可测试性:独立的 Service 层便于单元测试
  4. 代码清晰度:避免一个 Service 类过于庞大,职责混乱

放弃方案 2合并到 ApexCodeCoverageService的理由

  1. 虽然都是覆盖率功能,但数据模型和查询逻辑差异较大
  2. 合并会导致 Service 类过于庞大,职责不清晰
  3. 不利于针对 Flow 特性的独立扩展
  4. 与代码覆盖率功能的设计理念冲突002-04 也是独立的 Service

决策 3查询性能优化策略

选择方案 1数据库索引 + 分页查询

  • 使用数据库索引test_result_id、name、type、namespace
  • 使用 PageHelper 进行物理分页
  • 对覆盖率范围筛选在内存中进行(数据量可控)

理由:

  1. 查询性能:数据库索引确保查询性能
  2. 内存友好:物理分页避免加载大量数据到内存
  3. 灵活性:覆盖率范围筛选在内存中进行,避免复杂的 SQL 条件
  4. 简单性:实现简单,与 002-04 代码覆盖率功能保持一致
  5. 一致性:与项目其他功能的查询策略保持一致

放弃方案 2使用 Redis 缓存)的理由:

  1. Flow 覆盖率数据相对稳定,但查询条件多样,缓存命中率可能不高
  2. 增加系统复杂度,需要维护缓存一致性
  3. 当前数据量下,数据库查询性能已经足够
  4. 可以后续根据实际性能需求再考虑添加缓存

决策 4覆盖率计算策略

选择方案 1元素数量加权平均法

  • 总体覆盖率 = Σ(numElementsCovered) / Σ(numElements) × 100%
  • 按类型统计时,分别计算每种类型的加权平均覆盖率

理由:

  1. 准确性:基于元素数量的加权平均能准确反映整体覆盖情况
  2. 公平性:大 Flow元素多对总体覆盖率的影响更大符合实际情况
  3. 简单性:计算逻辑简单,易于理解和维护
  4. 一致性:与 Salesforce 官方覆盖率计算逻辑保持一致

放弃方案 2简单平均法的理由

  1. 简单平均不考虑 Flow 大小差异,可能导致小 Flow 对总体覆盖率影响过大
  2. 不能准确反映实际测试覆盖情况
  3. 与 Salesforce 官方计算逻辑不一致

决策 5权限控制策略

选择方案 1独立权限标识

  • 使用独立的权限标识 apex:flow-coverage:query
  • 与代码覆盖率权限分离

理由:

  1. 细粒度控制:支持对 Flow 覆盖率查询和代码覆盖率查询分别授权
  2. 安全性:某些用户可能只需要查看代码覆盖率,不需要查看 Flow 覆盖率
  3. 灵活性:便于后续的权限管理扩展
  4. 符合规范:与若依的权限管理规范一致

放弃方案 2复用代码覆盖率权限的理由

  1. 权限粒度太粗,无法满足细粒度控制需求
  2. 不符合最小权限原则
  3. 不利于后续的权限管理

决策 6API 设计策略

选择方案 1独立的 RESTful API 端点

  • 提供独立的 /api/apex/flow-coverage 端点
  • 与代码覆盖率 API 分离

理由:

  1. 接口清晰:独立的端点使接口职责更清晰
  2. 版本控制:便于独立版本控制和演进
  3. 文档清晰:独立的 API 便于文档化和理解
  4. 权限控制:独立的端点便于权限控制

放弃方案 2合并到代码覆盖率 API的理由

  1. 合并会导致接口复杂,需要额外的类型参数
  2. 不利于接口文档化
  3. 与代码覆盖率的 API 设计理念冲突

后果

正面影响

  1. 开发效率高:与 002-04 代码覆盖率功能保持一致的架构,减少设计成本
  2. 维护成本低:独立的 Service 层和数据库表,职责清晰
  3. 查询性能好:数据库索引 + 分页查询确保性能
  4. 权限控制灵活:独立的权限标识支持细粒度控制
  5. 扩展性好:独立的表结构和 Service 层便于后续扩展
  6. 架构一致性:与代码覆盖率功能保持一致的架构风格

负面影响

  1. 表数量增加:需要创建 2 张新表datai_apex_flow_coverage、datai_apex_flow_coverage_warning
  2. 代码量增加:需要创建独立的 Service、Controller、Mapper 等类
  3. 权限配置增加:需要配置独立的权限标识

替代方案

方案 A与代码覆盖率功能完全复用

  • 描述:复用代码覆盖率的数据库表和 Service 层,通过类型字段区分
  • 优点:表数量少,代码量少
  • 缺点:数据模型不匹配,查询逻辑复杂,不利于扩展
  • 适用场景:数据模型高度相似的功能

方案 B使用 MongoDB 存储

  • 描述:使用 MongoDB 存储 Flow 覆盖率数据
  • 优点Schema 灵活,适合非结构化数据
  • 缺点:增加系统复杂度,与现有技术栈不一致
  • 适用场景:数据结构变化频繁,需要高度灵活性的场景

方案 C实时查询 Salesforce API

  • 描述:不存储数据到本地数据库,每次查询都调用 Salesforce API
  • 优点:无数据同步问题,数据始终最新
  • 缺点:查询性能差,依赖 Salesforce API 可用性,无法支持复杂统计
  • 适用场景:数据量小,实时性要求高的场景

相关文档