|
@@ -0,0 +1,401 @@
|
|
|
|
|
+# Spring Boot 3.x 升级 + Dify 替代 实施计划
|
|
|
|
|
+
|
|
|
|
|
+> 版本: v1.0
|
|
|
|
|
+> 日期: 2026-07-20
|
|
|
|
|
+> 范围: cfc-backend (Spring Boot 2.7.18 + Java 8 → Spring Boot 3.4.x + Java 21)
|
|
|
|
|
+
|
|
|
|
|
+---
|
|
|
|
|
+
|
|
|
|
|
+## 一、目标状态
|
|
|
|
|
+
|
|
|
|
|
+| 维度 | 当前 | 目标 |
|
|
|
|
|
+|------|------|------|
|
|
|
|
|
+| Java | 1.8 (JDK 8) | **21 LTS** |
|
|
|
|
|
+| Spring Boot | 2.7.18 | **3.4.x** (最新稳定) |
|
|
|
|
|
+| AI 框架 | 直调 Dify API | **Spring AI 1.x** |
|
|
|
|
|
+| 知识库 | Dify Datasets | **本地 sqlite-vec** |
|
|
|
|
|
+| 数学引擎 | Nashorn (JDK 15 已移除) | **exp4j / SpEL** |
|
|
|
|
|
+| API 文档 | springdoc-openapi 1.8.0 | **springdoc-openapi 2.7+** |
|
|
|
|
|
+| ORM | MyBatis-Plus 3.5.3.1 | **MyBatis-Plus 3.5.7+** |
|
|
|
|
|
+| JWT | jjwt 0.11.5 | **jjwt 0.12.6** |
|
|
|
|
|
+
|
|
|
|
|
+---
|
|
|
|
|
+
|
|
|
|
|
+## 二、总体路线
|
|
|
|
|
+
|
|
|
|
|
+```
|
|
|
|
|
+5 阶段 / 20 人天 / 可回退 / 每阶段独立验证
|
|
|
|
|
+
|
|
|
|
|
+Phase 0 ─── Phase 1 ─── Phase 2 ─── Phase 3 ─── Phase 4
|
|
|
|
|
+前置准备 javax→ 行为适配 Spring AI 回归验证
|
|
|
|
|
+(3天) jakarta + + +
|
|
|
|
|
+ 迁移 Nashorn Dify 上线
|
|
|
|
|
+ (5天) 替换 替换 (3天)
|
|
|
|
|
+ (4天) (5天)
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+**回退机制**:每阶段结束时有一个 `git tag`,任一阶段失败可退回到上个稳定点。
|
|
|
|
|
+
|
|
|
|
|
+---
|
|
|
|
|
+
|
|
|
|
|
+## 三、各阶段详细任务
|
|
|
|
|
+
|
|
|
|
|
+### Phase 0 — 前置准备(3 天)
|
|
|
|
|
+
|
|
|
|
|
+**目标**:环境就绪,依赖对齐,识别所有需要改动的文件。
|
|
|
|
|
+
|
|
|
|
|
+| 任务 | 产出 | 验证 |
|
|
|
|
|
+|------|------|------|
|
|
|
|
|
+| 0.1 JDK 21 安装 + Maven 3.9+ 升级 | `java -version` → 21 | 开发/CI 环境确认 |
|
|
|
|
|
+| 0.2 pom.xml: parent → spring-boot 3.4.x | BOM 对齐 | `mvn dependency:tree` 无冲突 |
|
|
|
|
|
+| 0.3 依赖版本批量更新 | 见下方依赖表 | 编译无报错 |
|
|
|
|
|
+| 0.4 maven-compiler-plugin source/target → 21 | `java.version=21` | 编译通过 |
|
|
|
|
|
+| 0.5 `mvn compile` 采集完整 javax 报错清单 | javax 影响范围清单 | 确认 482 个文件全部覆盖 |
|
|
|
|
|
+| 0.6 Nashorn 调用栈录制 | WisdomMathService 表达式求值场景 | 确认替换范围 |
|
|
|
|
|
+| 0.7 创建 git tag: `v2.7.18-baseline` | 可回退点 | `git log` 确认 |
|
|
|
|
|
+
|
|
|
|
|
+**依赖版本变更表:**
|
|
|
|
|
+
|
|
|
|
|
+```xml
|
|
|
|
|
+<!-- pom.xml 关键变更 -->
|
|
|
|
|
+<parent>
|
|
|
|
|
+ <groupId>org.springframework.boot</groupId>
|
|
|
|
|
+ <artifactId>spring-boot-starter-parent</artifactId>
|
|
|
|
|
+ <version>3.4.x</version> <!-- 2.7.18 → 3.4.x -->
|
|
|
|
|
+</parent>
|
|
|
|
|
+<properties>
|
|
|
|
|
+ <java.version>21</java.version> <!-- 1.8 → 21 -->
|
|
|
|
|
+ <mybatis-plus.version>3.5.9</mybatis-plus.version> <!-- 3.5.3.1 → 3.5.9 -->
|
|
|
|
|
+</properties>
|
|
|
|
|
+
|
|
|
|
|
+<!-- 替换或新增 -->
|
|
|
|
|
+<dependency>
|
|
|
|
|
+ <!-- springdoc v1 → v2 (包名变更) -->
|
|
|
|
|
+ <groupId>org.springdoc</groupId>
|
|
|
|
|
+ <artifactId>springdoc-openapi-starter-webmvc-ui</artifactId>
|
|
|
|
|
+ <version>2.7.0</version>
|
|
|
|
|
+</dependency>
|
|
|
|
|
+
|
|
|
|
|
+<dependency>
|
|
|
|
|
+ <!-- jjwt 0.11.5 → 0.12.6 -->
|
|
|
|
|
+ <groupId>io.jsonwebtoken</groupId>
|
|
|
|
|
+ <artifactId>jjwt-api</artifactId>
|
|
|
|
|
+ <version>0.12.6</version>
|
|
|
|
|
+</dependency>
|
|
|
|
|
+
|
|
|
|
|
+<!-- 移除:nashorn-core (如果显式引入) -->
|
|
|
|
|
+<!-- 新增:表达式求值替代库 -->
|
|
|
|
|
+<dependency>
|
|
|
|
|
+ <groupId>net.objecthunter</groupId>
|
|
|
|
|
+ <artifactId>exp4j</artifactId>
|
|
|
|
|
+ <version>0.4.8</version>
|
|
|
|
|
+</dependency>
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+---
|
|
|
|
|
+
|
|
|
|
|
+### Phase 1 — javax → jakarta 迁移(5 天)
|
|
|
|
|
+
|
|
|
|
|
+**目标**:482 个文件的 `javax.*` 引用全部替换为 `jakarta.*`,编译通过。
|
|
|
|
|
+
|
|
|
|
|
+**替换规则:**
|
|
|
|
|
+
|
|
|
|
|
+| 原包名 | 目标包名 | 影响模块 |
|
|
|
|
|
+|--------|---------|---------|
|
|
|
|
|
+| `javax.persistence.*` | `jakarta.persistence.*` | 所有 @Entity, @Table, @Column |
|
|
|
|
|
+| `javax.annotation.*` | `jakarta.annotation.*` | @Resource, @PostConstruct, @PreDestroy |
|
|
|
|
|
+| `javax.validation.*` | `jakarta.validation.*` | @Valid, @NotBlank, @Size, DTO |
|
|
|
|
|
+| `javax.servlet.*` | `jakarta.servlet.*` | HttpServletRequest/Response, Filter |
|
|
|
|
|
+| `javax.sql.*` | `jakarta.sql.*` | DataSource (如果直接引用) |
|
|
|
|
|
+
|
|
|
|
|
+**操作方式:**
|
|
|
|
|
+
|
|
|
|
|
+```
|
|
|
|
|
+方式 A:IDE 全局替换(推荐)
|
|
|
|
|
+ IntelliJ: 重构 → 迁移包 → javax→jakarta
|
|
|
|
|
+ 或 sed 逐目录确认
|
|
|
|
|
+
|
|
|
|
|
+方式 B:分批替换
|
|
|
|
|
+ day1: entity 包(~80 个文件)—— 最规则,可批量
|
|
|
|
|
+ day2: dto 包(所有 @NotBlank/@Valid)—— 替换量大但简单
|
|
|
|
|
+ day3: config + task + filter 包 —— @Resource/@PostConstruct
|
|
|
|
|
+ day4: service + controller 包 —— 逐一检查
|
|
|
|
|
+ day5: 全量编译 + 修复残留问题
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+**风险提示**:
|
|
|
|
|
+- `javax.annotation.Resource` 和 `javax.annotation.PostConstruct` 在 Spring Boot 3 中内置了 jakarta 适配,但显式引用仍需改包名
|
|
|
|
|
+- Spring 自己的 `@Autowired` 不受影响
|
|
|
|
|
+- MyBatis-Plus 的注解 (`@TableName` 等) 不受影响(不走 javax)
|
|
|
|
|
+
|
|
|
|
|
+**产出**:`mvn clean compile` 零错误。
|
|
|
|
|
+
|
|
|
|
|
+---
|
|
|
|
|
+
|
|
|
|
|
+### Phase 2 — 行为适配 + Nashorn 替换(4 天)
|
|
|
|
|
+
|
|
|
|
|
+**目标**:Spring Boot 3 行为变更对齐,废弃 API 替换,全量编译通过。
|
|
|
|
|
+
|
|
|
|
|
+#### 2.1 Spring Boot 3 行为变更
|
|
|
|
|
+
|
|
|
|
|
+| 变更项 | 影响 | 处理方式 |
|
|
|
|
|
+|--------|------|---------|
|
|
|
|
|
+| PathPatternParser (默认) | 某些 Ant 风格路径可能不匹配 | 配置 `spring.mvc.pathmatch.matching-strategy=ant-path-matcher` 可回退 |
|
|
|
|
|
+| `spring.config.location` 弃用 | 如果使用了 | 改为 `spring.config.import` |
|
|
|
|
|
+| Spring Security 默认变更 | 如果有 Security 配置 | 检查 CSRF/鉴权默认值 |
|
|
|
|
|
+| `WebMvcConfigurerAdapter` 已删除 | 如果继承了 | 改为实现 `WebMvcConfigurer` |
|
|
|
|
|
+| Health indicator 变更 | actuator 配置 | 确认无需更改 |
|
|
|
|
|
+
|
|
|
|
|
+#### 2.2 Nashorn → exp4j 替换
|
|
|
|
|
+
|
|
|
|
|
+当前代码(WisdomMathService):
|
|
|
|
|
+```java
|
|
|
|
|
+ScriptEngineManager mgr = new ScriptEngineManager();
|
|
|
|
|
+ScriptEngine engine = mgr.getEngineByName("nashorn");
|
|
|
|
|
+engine.eval("12+38*2"); // → 88
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+替换方式:
|
|
|
|
|
+```java
|
|
|
|
|
+// exp4j (轻量,仅数学表达式,推荐)
|
|
|
|
|
+import net.objecthunter.exp4j.ExpressionBuilder;
|
|
|
|
|
+
|
|
|
|
|
+Expression exp = new ExpressionBuilder(expression).build();
|
|
|
|
|
+double result = exp.evaluate();
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+**验证**:
|
|
|
|
|
+- 提取 WisdomMathService 的所有表达式测试用例
|
|
|
|
|
+- 确保 exp4j 覆盖全部运算符(+ - * / ^ % 括号 函数)
|
|
|
|
|
+- 表达式求值精度一致
|
|
|
|
|
+
|
|
|
|
|
+#### 2.3 springdoc-openapi v1 → v2
|
|
|
|
|
+
|
|
|
|
|
+| v1 (当前) | v2 (目标) |
|
|
|
|
|
+|-----------|----------|
|
|
|
|
|
+| `springdoc-openapi-ui` | `springdoc-openapi-starter-webmvc-ui` |
|
|
|
|
|
+| 包名: `org.springdoc` | 包名: `org.springdoc` (同但内部结构变) |
|
|
|
|
|
+| 配置路径: `springdoc.swagger-ui.path` | 同(但需确认) |
|
|
|
|
|
+
|
|
|
|
|
+改动:pom.xml artifactId 变更,配置确认。
|
|
|
|
|
+
|
|
|
|
|
+#### 2.4 jjwt 0.11 → 0.12
|
|
|
|
|
+
|
|
|
|
|
+主要 API 变化:
|
|
|
|
|
+- `Jwts.builder()` → 签名方法参数类型变化
|
|
|
|
|
+- `Keys.secretKeyFor()` → 返回类型变更为 `SecretKey`
|
|
|
|
|
+- `Jwts.parserBuilder()` → `Jwts.parser()` (不再需要 .builder())
|
|
|
|
|
+
|
|
|
|
|
+需检查 `JwtUtil.java` / 任何使用 jjwt 的地方,逐一适配。
|
|
|
|
|
+
|
|
|
|
|
+#### 2.5 编译验证
|
|
|
|
|
+
|
|
|
|
|
+`mvn clean compile` 零错误。
|
|
|
|
|
+
|
|
|
|
|
+---
|
|
|
|
|
+
|
|
|
|
|
+### Phase 3 — Spring AI 集成 + Dify 替换(5 天)
|
|
|
|
|
+
|
|
|
|
|
+**目标**:用 Spring AI 替换 Dify 的全部调用,本地知识库就位。
|
|
|
|
|
+
|
|
|
|
|
+#### 3.1 Spring AI 依赖
|
|
|
|
|
+
|
|
|
|
|
+```xml
|
|
|
|
|
+<!-- Spring AI - BOM -->
|
|
|
|
|
+<dependencyManagement>
|
|
|
|
|
+ <dependencies>
|
|
|
|
|
+ <dependency>
|
|
|
|
|
+ <groupId>org.springframework.ai</groupId>
|
|
|
|
|
+ <artifactId>spring-ai-bom</artifactId>
|
|
|
|
|
+ <version>1.x.x</version>
|
|
|
|
|
+ <type>pom</type>
|
|
|
|
|
+ <scope>import</scope>
|
|
|
|
|
+ </dependency>
|
|
|
|
|
+ </dependencies>
|
|
|
|
|
+</dependencyManagement>
|
|
|
|
|
+
|
|
|
|
|
+<dependencies>
|
|
|
|
|
+ <!-- OpenAI 兼容协议 (覆盖 DeepSeek, Ollama) -->
|
|
|
|
|
+ <dependency>
|
|
|
|
|
+ <groupId>org.springframework.ai</groupId>
|
|
|
|
|
+ <artifactId>spring-ai-openai-spring-boot-starter</artifactId>
|
|
|
|
|
+ </dependency>
|
|
|
|
|
+ <!-- 如果用 Qwen, 加 dashscope starter -->
|
|
|
|
|
+</dependencies>
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+#### 3.2 ChatClient 封装(替代 AIService)
|
|
|
|
|
+
|
|
|
|
|
+```java
|
|
|
|
|
+// 核心抽象 — 替代原来的 AIService + OkHttp 直调
|
|
|
|
|
+@Service
|
|
|
|
|
+public class LLMService {
|
|
|
|
|
+
|
|
|
|
|
+ @Resource
|
|
|
|
|
+ private ChatClient.Builder chatClientBuilder;
|
|
|
|
|
+
|
|
|
|
|
+ // 聊天(带 System Prompt + 会话记忆)
|
|
|
|
|
+ public String chat(String query, String systemPrompt, String conversationId) {
|
|
|
|
|
+ return chatClientBuilder.build()
|
|
|
|
|
+ .prompt()
|
|
|
|
|
+ .system(systemPrompt)
|
|
|
|
|
+ .user(query)
|
|
|
|
|
+ .advisors(new MessageChatMemoryAdvisor(chatMemory, conversationId, 10))
|
|
|
|
|
+ .call()
|
|
|
|
|
+ .content();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 流式
|
|
|
|
|
+ public Flux<String> stream(String query, String systemPrompt, String conversationId) {
|
|
|
|
|
+ return chatClientBuilder.build()
|
|
|
|
|
+ .prompt()
|
|
|
|
|
+ .system(systemPrompt)
|
|
|
|
|
+ .user(query)
|
|
|
|
|
+ .advisors(new MessageChatMemoryAdvisor(chatMemory, conversationId, 10))
|
|
|
|
|
+ .stream()
|
|
|
|
|
+ .content();
|
|
|
|
|
+ }
|
|
|
|
|
+}
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+#### 3.3 8 个 Service 逐一替换
|
|
|
|
|
+
|
|
|
|
|
+参考 `docs/architecture/Dify替代迁移可行性分析.md` 第 4.2 节的 `LLMService` 接口映射:
|
|
|
|
|
+
|
|
|
|
|
+| Service | Dify API | Spring AI 替代 | 工作量 |
|
|
|
|
|
+|---------|----------|---------------|--------|
|
|
|
|
|
+| AIService | chat-messages POST | ChatClient | ⭐ 小 |
|
|
|
|
|
+| DifySyncService | datasets | VectorStore + 本地管理 | ⭐⭐⭐ 中 |
|
|
|
|
|
+| AiConversationSummaryService | conversations | MemoryAdvisor | ⭐ 小 |
|
|
|
|
|
+| AiUserFactService | /workflows | ChatClient + @Tool | ⭐⭐ 中 |
|
|
|
|
|
+| ChatMirrorService | 日志镜像 | 转正为缓存层 | ⭐ 小 |
|
|
|
|
|
+| 其余 3 个 Service | 各异 | 具体分析 | ⭐⭐ 中 |
|
|
|
|
|
+
|
|
|
|
|
+#### 3.4 知识库本地化
|
|
|
|
|
+
|
|
|
|
|
+Dify Datasets 替代方案:
|
|
|
|
|
+
|
|
|
|
|
+```yaml
|
|
|
|
|
+# 方案投票:pgvector vs sqlite-vec
|
|
|
|
|
+# PostgreSQL 扩展 — 如果主库是 MySQL 则需要额外 PG 实例,引入成本高
|
|
|
|
|
+# sqlite-vec — 嵌入式,零运维,适合知识库 < 10万条
|
|
|
|
|
+
|
|
|
|
|
+# 选型:sqlite-vec(嵌入式,匹配项目规模)
|
|
|
|
|
+spring:
|
|
|
|
|
+ ai:
|
|
|
|
|
+ vectorstore:
|
|
|
|
|
+ sqlite:
|
|
|
|
|
+ path: ${data.dir}/knowledge.db
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+#### 3.5 System Prompt 外部化
|
|
|
|
|
+
|
|
|
|
|
+```
|
|
|
|
|
+不再依赖 Dify 的 Prompt 编辑器 →
|
|
|
|
|
+改为 YAML 文件或数据库表管理:
|
|
|
|
|
+
|
|
|
|
|
+resources/prompts/
|
|
|
|
|
+├── family-advisor.yaml
|
|
|
|
|
+├── growth-plan.yaml
|
|
|
|
|
+├── diet-recommend.yaml
|
|
|
|
|
+└── math-tutor.yaml
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+#### 3.6 Dify 数据归档
|
|
|
|
|
+
|
|
|
|
|
+Dify 替代表(原 6 张表):
|
|
|
|
|
+- `dify_*` 表 → 上游 Dify 不再写入后,保留 30 天观察期 → 归档/删除
|
|
|
|
|
+
|
|
|
|
|
+#### 3.7 验证标准
|
|
|
|
|
+
|
|
|
|
|
+- 原 Dify API 调用的 8 个 Service 全部改用 Spring AI
|
|
|
|
|
+- 流式聊天正常
|
|
|
|
|
+- 知识库检索准确率 >= Dify 时期
|
|
|
|
|
+- 对话记忆正常
|
|
|
|
|
+
|
|
|
|
|
+---
|
|
|
|
|
+
|
|
|
|
|
+### Phase 4 — 回归验证 + 上线(3 天)
|
|
|
|
|
+
|
|
|
|
|
+**目标**:全量回归通过,灰度上线。
|
|
|
|
|
+
|
|
|
|
|
+#### 4.1 回归范围
|
|
|
|
|
+
|
|
|
|
|
+| 测试范围 | 方法 | 负责人 |
|
|
|
|
|
+|---------|------|--------|
|
|
|
|
|
+| 所有 48 个 Controller API | 手动 + Postman 用例集 | 后端 |
|
|
|
|
|
+| 小程序端主流程 | 真机/开发者工具 | 前端联调 |
|
|
|
|
|
+| Web 管理端主流程 | 浏览器 | 前端联调 |
|
|
|
|
|
+| AI 聊天流程 | 对比测试(原 Dify vs Spring AI) | 后端 |
|
|
|
|
|
+| 数学表达式求值 | 用例集 + 精度对比 | 后端 |
|
|
|
|
|
+| 文件上传/PDF 解析 | 功能测试 | 后端 |
|
|
|
|
|
+
|
|
|
|
|
+#### 4.2 性能对比
|
|
|
|
|
+
|
|
|
|
|
+| 指标 | Dify 链路 | Spring AI 链路 | 目标 |
|
|
|
|
|
+|------|-----------|---------------|------|
|
|
|
|
|
+| 非流式首 Token 延迟 | ~2-3s | ~1-2s | 不劣化 |
|
|
|
|
|
+| 流式响应 TTFB | ~1.5s | ~0.8s | -30% |
|
|
|
|
|
+| 并发 50 用户 CPU | 待测 | 待测 | 不劣化 |
|
|
|
|
|
+| 内存使用 | 待测 | 待测 | 不劣化 |
|
|
|
|
|
+
|
|
|
|
|
+#### 4.3 上线方案
|
|
|
|
|
+
|
|
|
|
|
+```
|
|
|
|
|
+Step 1: 灰度 10% 流量(1 天) → 监控错误率
|
|
|
|
|
+Step 2: 灰度 50% 流量(1 天) → 监控延迟/错误率
|
|
|
|
|
+Step 3: 全量上线 → 观察 48h
|
|
|
|
|
+Step 4: Dify 实例下线 → 保留数据 30 天后清理
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+#### 4.4 回滚条件
|
|
|
|
|
+
|
|
|
|
|
+任一触发立即回滚:
|
|
|
|
|
+- API 错误率 > 1%
|
|
|
|
|
+- AI 响应可用率 < 99%
|
|
|
|
|
+- 核心接口延迟翻倍
|
|
|
|
|
+
|
|
|
|
|
+---
|
|
|
|
|
+
|
|
|
|
|
+## 四、风险评估
|
|
|
|
|
+
|
|
|
|
|
+| 风险 | 概率 | 影响 | 缓解措施 |
|
|
|
|
|
+|------|------|------|---------|
|
|
|
|
|
+| 三方库不兼容 Spring Boot 3 | 低 | 高 | Phase 0 先行验证,确认全部依赖兼容 |
|
|
|
|
|
+| javax→jakarta 遗漏某些深层引用 | 中 | 中 | Phase 1 分步替换,逐包编译验证 |
|
|
|
|
|
+| Spring AI 对 DeepSeek 的支持缺陷 | 低 | 中 | 降级方案:直调 OKHttp(方案 D) |
|
|
|
|
|
+| 知识库检索质量下降 | 中 | 中 | Phase 3 做对比测试,保留 Dify 数据 30 天 |
|
|
|
|
|
+| Nashorn 替换导致数学结果偏差 | 低 | 高 | Phase 2 提取全部测试用例,逐条验证 |
|
|
|
|
|
+
|
|
|
|
|
+---
|
|
|
|
|
+
|
|
|
|
|
+## 五、回退点
|
|
|
|
|
+
|
|
|
|
|
+| 阶段 | 回退点 | 回退方式 |
|
|
|
|
|
+|------|--------|---------|
|
|
|
|
|
+| Phase 0 完成 | `git tag v2.7.18-baseline` | `git checkout` |
|
|
|
|
|
+| Phase 1 完成 | `git tag v3.0-javax-migrated` | `git reset --hard` |
|
|
|
|
|
+| Phase 2 完成 | `git tag v3.0-build-ready` | `git reset --hard` |
|
|
|
|
|
+| Phase 3 完成 | `git tag v3.0-spring-ai` | `git reset --hard` + 切回 Dify 数据源 |
|
|
|
|
|
+
|
|
|
|
|
+每阶段可独立回退,不会影响其他阶段的工作。
|
|
|
|
|
+
|
|
|
|
|
+---
|
|
|
|
|
+
|
|
|
|
|
+## 六、资源估算
|
|
|
|
|
+
|
|
|
|
|
+```
|
|
|
|
|
+Phase 0 前置准备 3 天 × 1 人
|
|
|
|
|
+Phase 1 javax→jkt 5 天 × 1 人
|
|
|
|
|
+Phase 2 行为适配 4 天 × 1 人
|
|
|
|
|
+Phase 3 Spring AI 5 天 × 1 人
|
|
|
|
|
+Phase 4 回归+上线 3 天 × 1 人
|
|
|
|
|
+──────────────────────────────
|
|
|
|
|
+总计 20 人天
|
|
|
|
|
+
|
|
|
|
|
+建议 2 人并行(后端 1 + 后端 2):
|
|
|
|
|
+Phase 0-2 可 2 人并行(一人改包名,一人适配行为)
|
|
|
|
|
+Phase 3 集中 1 人(Spring AI 集成需连续上下文)
|
|
|
|
|
+Phase 4 2 人并行回归
|
|
|
|
|
+→ 日历时间约 2 周
|
|
|
|
|
+```
|