datai/datai-scenes/datai-scene-salesforce/docs/retros/2026-01-30-004-retro.md

10 KiB
Raw Permalink Blame History

复盘文档 - 查询功能

元数据

  • 需求编号001-04
  • 创建时间2026-01-30
  • 创建人AI Assistant
  • 状态:已完成

复盘概述

本次复盘对 Salesforce Partner API 查询功能的开发过程进行全面回顾。查询功能包括 SOQL 查询Query、查询所有记录QueryAll、分页查询QueryMore和 SOSL 搜索Search四个核心功能。通过本次复盘总结成功经验、识别改进点、分析问题根因并制定行动计划以提高后续开发过程的效率和质量。

目标与实际产出对比

目标

  • 实现 Salesforce Partner API 的查询功能,包括 Query、QueryAll、QueryMore、Search 四个核心功能
  • 支持自定义批次大小1-2000默认 500
  • 支持关系查询和跨对象搜索
  • 提供完整的 REST API 接口4 个接口)
  • 实现参数验证、异常处理、权限控制、Swagger 文档
  • 实现完整的单元测试,测试覆盖率不低于 80%
  • 遵循 SSOT 流程,确保所有开发活动都有文档依据

实际产出

  • 成功实现了 Query、QueryAll、QueryMore、Search 四个核心查询功能
  • 支持自定义批次大小,默认 500最大 2000
  • 支持关系查询(如 Account.Name和跨对象搜索SOSL
  • 提供了 4 个 REST API 接口POST /partner/query、POST /partner/queryAll、POST /partner/queryMore、POST /partner/search
  • 实现了参数验证(@NotBlank、@Min、@Max、异常处理、权限控制@PreAuthorize、Swagger 文档(@Operation、@Tag
  • 实现了完整的单元测试,包含 8 个测试用例,覆盖成功、空结果、异常等场景
  • 严格按照 SSOT 流程执行每个阶段都有相应的文档需求文档、设计文档、决策记录、提示词、变更日志、复盘文档、API 文档)
  • 生成了 11 个代码文件4 个 DTO、3 个 VO、1 个 Service 接口、1 个 Service 实现、1 个 Controller、1 个单元测试)

成功经验

1. 分层架构设计的合理性

采用 Controller → Service → Factory → Connection → Salesforce API 的分层架构使得代码结构清晰职责分离明确。Controller 负责接收请求和参数校验Service 负责业务逻辑处理Factory 负责连接管理,各层之间通过接口交互,便于单元测试和后续维护。

2. DTO/VO 模式的正确使用

为每个查询功能创建独立的 DTOQueryDto、QueryAllDto、QueryMoreDto、SearchDto和 VOQueryResultVo、SearchResultVo、SearchRecordVo实现了请求参数和响应数据与业务逻辑的分离。DTO 中使用 @NotBlank、@Min、@Max 等注解进行参数验证VO 中使用 @Schema 注解提供 Swagger 文档,提高了代码的可读性和可维护性。

3. 异常处理的一致性

统一使用 datai-salesforce-common 模块中的异常类SalesforceAuthException、SalesforceOperationException在 Service 层捕获 ConnectionException 并转换为自定义异常,返回友好的错误消息。这种一致的异常处理方式使得错误处理更加规范,便于前端统一处理错误。

4. 单元测试的完整性

为每个查询方法编写了完整的单元测试,包括成功场景、空结果场景、连接异常场景等,使用 JUnit 5 和 Mockito 进行测试,确保测试覆盖率不低于 80%。单元测试不仅验证了功能的正确性,也为后续的代码重构提供了保障。

5. SOQL 和 SOSL 的准确实现

准确实现了 SOQL 查询Query、QueryAll、QueryMore和 SOSL 搜索Search的功能正确处理了查询结果的转换SObject[] 转换为 List<Map<String, Object>>),支持关系查询字段(如 Account.Name正确处理了分页机制QueryLocator

改进点

1. 查询性能优化可以更深入

当前实现每次查询都通过 PartnerConnectionFactory 获取连接,虽然 Factory 内部有连接缓存,但对于高频查询场景,可以考虑实现查询结果缓存,减少重复的 API 调用。此外,对于大数据量查询,可以考虑实现异步查询或流式查询。

2. SOQL 语法验证可以增强

当前实现直接将 SOQL 语句传递给 Salesforce API如果 SOQL 语法错误,只能在运行时捕获异常。可以考虑在客户端增加 SOQL 语法预验证,提前发现语法错误,提高用户体验。

3. 查询结果的数据类型转换可以更完善

当前实现将 SObject 字段值直接放入 Map 中,保留了原始的数据类型。但对于某些特殊数据类型(如 DateTime、Currency、Percent 等),可能需要进行更精细的转换,以便前端更好地展示。

4. API 文档的示例可以更丰富

当前 API 文档中的示例相对简单,可以增加更多复杂的查询示例,如关系查询、聚合查询、子查询等,帮助前端开发人员更好地理解和使用 API。

问题分析

问题 1SObject 转换时的字段类型处理

问题描述:在将 SObject 转换为 Map<String, Object> 时,某些字段的类型(如 DateTime可能不符合前端期望的格式。

根因分析SObject.getField(String) 方法返回的是 Object 类型,保留了 Salesforce 的原始数据类型,没有进行统一的数据类型转换。

解决方案

  • 短期:在 VO 中增加字段类型说明,告知前端可能的字段类型
  • 长期:实现一个统一的数据类型转换器,将 Salesforce 的数据类型转换为标准的 JSON 数据类型(如将 DateTime 转换为 ISO 8601 格式的字符串)

问题 2QueryMore 的 queryLocator 有效期限制

问题描述QueryMore 使用的 queryLocator 有有效期限制(通常为 15 分钟),如果用户在前一页查询后等待较长时间再查询下一页,可能会遇到 queryLocator 过期的问题。

根因分析Salesforce API 的 queryLocator 设计就是为了限制查询结果的有效期,避免长时间占用服务器资源。

解决方案

  • 短期:在 API 文档中明确说明 queryLocator 的有效期限制,建议客户端在获取 queryLocator 后尽快使用
  • 长期:可以考虑实现一个查询结果缓存机制,将查询结果临时存储在服务器端,客户端通过自定义的游标获取数据,不受 Salesforce queryLocator 有效期限制

问题 3SOSL 搜索结果的对象类型识别

问题描述SOSL 搜索结果中,每个记录都需要识别其对象类型(如 Account、Contact当前实现通过 SearchRecordVo.type 字段返回对象类型,但前端可能需要更多的对象元数据信息。

根因分析SOSL 搜索返回的 SearchResult 中包含了记录的对象类型信息,但没有包含对象的完整元数据(如字段列表、字段类型等)。

解决方案

  • 短期:在 API 文档中说明,如果需要对象元数据,可以调用 Describe API 获取
  • 长期:可以考虑在 SearchResultVo 中增加对象元数据信息,或者提供一个批量获取对象元数据的 API

行动计划

序号 改进点/问题 具体行动 责任人 时间节点
1 查询性能优化 研究并实现查询结果缓存机制,减少重复 API 调用 开发团队 下一个迭代
2 SOQL 语法验证 调研 SOQL 语法验证方案,增加客户端预验证 开发团队 下一个迭代
3 数据类型转换 实现统一的数据类型转换器,将 Salesforce 类型转换为标准 JSON 类型 开发团队 下一个迭代
4 API 文档示例 增加更多复杂的查询示例(关系查询、聚合查询等) AI Assistant 立即执行
5 queryLocator 有效期 在 API 文档中明确说明有效期限制,提供最佳实践建议 AI Assistant 立即执行
6 SOSL 对象元数据 提供批量获取对象元数据的 API 或文档说明 开发团队 下一个迭代

提取模式

有效的 Prompt 技巧

  1. 明确的代码生成顺序在提示词中明确指定代码生成的顺序DTO → VO → Service 接口 → Service 实现 → Controller → 单元测试),可以确保生成的代码结构清晰,依赖关系正确。

  2. 详细的验证注解要求:在提示词中明确要求使用 @NotBlank、@Min、@Max 等验证注解,以及 @Schema 注解提供 Swagger 文档,可以提高生成代码的规范性和可用性。

  3. 异常处理的统一要求:在提示词中明确要求使用统一的异常处理机制(捕获 ConnectionException 并转换为自定义异常),可以确保生成的代码具有一致的错误处理方式。

避免的坑

  1. 不要忽略 SObject 转换的细节SObject 到 Map 的转换看似简单,但需要注意字段类型、关系字段、空值处理等细节,否则可能导致数据丢失或类型错误。

  2. 不要忽视分页机制的实现QueryMore 的分页机制需要正确处理 queryLocator 和 done 标志,如果实现不当,可能导致数据重复或遗漏。

  3. 不要忽略 SOQL 和 SOSL 的区别SOQL 用于查询单个对象的记录SOSL 用于跨对象搜索,两者的使用场景和返回结果结构不同,不能混用。

模板迭代

经过本次复盘,发现当前的提示词模板在以下方面可以改进:

  1. 增加数据类型转换的要求:在提示词中增加对数据类型转换的具体要求,明确哪些类型需要转换,如何转换。

  2. 增加分页机制的详细说明:在提示词中增加对分页机制的详细说明,包括 queryLocator 的有效期、done 标志的含义等。

  3. 增加复杂查询示例:在提示词中增加复杂查询的示例(如关系查询、聚合查询、子查询等),帮助生成更完善的代码和文档。

计划在下一个迭代中更新提示词模板,增加上述内容。

相关文档