Files
cmroubao/docs/03-tech-stack.md
T

161 lines
9.7 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# 技术栈
> “用什么”的权威速查表。状态为“待验证”的项不能在代码中当作既成事实。
## 技术栈一览
| 维度 | 选型 | 状态 | 说明 |
| --- | --- | --- | --- |
| Android 基础 | Roubao `main` 的 Kotlin 原生 Android 代码,应用版本 1.4.2 | 上游已核实,待接入 | 上游为 `Turbo1123/roubao`,MIT;接入时固定具体 commit。 |
| Android IDE/JDK | Android Studio Hedgehog 2023.1.1 或更高;JDK 17 | 上游已核实 | 首次导入不接受 IDE 自动升级 AGP、Gradle 或 Kotlin。 |
| Android 构建链 | Gradle 8.2;AGP 8.2.0;Kotlin 1.9.20;JVM target 17 | 上游已核实 | 使用仓库内 Gradle Wrapper,不依赖全局 Gradle。 |
| Android SDK | compileSdk/targetSdk 34;minSdk 26;SDK Build Tools 34.0.0 | 上游已核实 | 支持 Android 8.0+;真机自动化优先 Android 11+。 |
| Android UI | Jetpack Compose + Material 3;Compose Compiler 1.5.5 | 上游已核实 | Compose BOM 为 2023.10.01。 |
| Android 自动化 | 项目目标以 `AccessibilityService` 为主,Shizuku 为兼容/增强路径 | 目标已定,待实现 | 上游 `main` 使用 Shizuku 13.1.5;无障碍实现位于独立开发分支,不能把它误认为主分支现状。 |
| 第一层任务源 | UTF-8 四行蝦皮订单文本 + 同订单号 JPEG | 首份样例已核实,待实现 | 使用 Debug/测试专用 `TaskSource`;原始数据和生成物不得提交。 |
| Android 长任务 | 前台服务 + 持续通知 | 计划采用 | 降低执行中被系统挂起的风险,仍需处理进程死亡恢复。 |
| 后端语言 | Go 1.23.0 | MVP 已定 | 与现有本机工具链一致;构建测试必须设置 `GOTOOLCHAIN=local` 防止静默升级。 |
| 后端骨架 | Go Blueprint v0.10.11 生成的最小 Gin + SQLite 工程 | MVP 已定 | 只作为一次性脚手架输入;生成后立即重写版本约束。 |
| 后端框架 | Gin v1.11.0 | MVP 已定 | 这是 `go.mod` 明确支持 Go 1.23.0 的最高已核实 Gin 版本。 |
| 数据访问 | 标准库 `database/sql` | MVP 已定 | 领域层通过仓储接口访问,避免先引入 ORM 和代码生成复杂度。 |
| 数据迁移 | Goose v3,使用 SQL migration | MVP 已定 | 迁移可审核、可排序并支持 SQLite;版本在 T-201 建立 `go.mod` 时锁定。 |
| 管理 Web | Gin + `html/template` + `embed` + 少量原生 JS/CSS | MVP 已定 | 不单独引入 SPA 工程,模板和静态资源随服务构建。 |
| 数据库 | SQLite | MVP 已定 | 单服务、单设备验证足够;多实例或并发提升前迁移 PostgreSQL。 |
| 图片/截图 | 后端受控本地文件目录,数据库存元数据 | MVP 已定 | 禁止把二进制直接塞入日志;生产再评估对象存储。 |
| 管理鉴权 | 单个种子管理账号 + 服务端会话 Cookie | MVP 已定 | 密码只保存哈希;完整 RBAC 为 V2。 |
| App 鉴权 | 采购员登录态 + 设备绑定令牌 | 目标已定,细节待实现 | 人员身份与设备身份分离;令牌只保存哈希。 |
| VLM 接入 | 应用内统一适配器,优先兼容 OpenAI 风格多模态接口 | 接口已定,供应商待定 | 模型输出必须符合本项目 JSON Schema。 |
| 通知 | MVP 不使用推送 | 已定 | 点击“获取任务”调用原子 claim API;V2 再评估厂商推送/WebSocket。 |
| 后端测试 | 标准库 `testing` + `httptest` | MVP 已定 | 覆盖状态机、权限、幂等、SQLite 事务和输入校验。 |
| Android 测试 | JUnit + 现有上游测试工具;真实设备 smoke | 待源码核实 | UI 自动化核心必须在目标设备验证。 |
| 部署 | 单机局域网 Go 服务;容器化后置 | MVP 已定 | Android 测试机必须能通过 HTTPS 或受控测试网络访问。 |
## Roubao 上游版本基线
核实日期:2026-07-25。
| 项目 | 已核实值 |
| --- | --- |
| 上游仓库 | [`Turbo1123/roubao`](https://github.com/Turbo1123/roubao) |
| 许可证 | MIT |
| 默认分支 | `main` |
| 核实时 `main` commit | `c8a6d7f03422eb01744b01f3ee77bf7757741f7e` |
| `main` 应用版本 | 1.4.2(`versionCode 7`) |
| 开发 IDE | Android Studio Hedgehog 2023.1.1 或更高 |
| JDK / JVM target | 17 / 17 |
| Android SDK | compileSdk 34、targetSdk 34、minSdk 26 |
| SDK Build Tools | 34.0.0(AGP 8.2 官方兼容基线) |
| Gradle / AGP | 8.2 / 8.2.0 |
| Kotlin | 1.9.20 |
| Compose | Compose BOM 2023.10.01、Compiler 1.5.5、Material 3 |
| 自动化依赖 | Shizuku API/Provider 13.1.5 |
| 无障碍开发分支 | `roubao2.0+AccessibilityService`,核实时 commit `5b114c0a9476c359b27cfe994743fc7beb0a3554` |
上述值来自上游 README、`build.gradle.kts`、`app/build.gradle.kts` 和
`gradle/wrapper/gradle-wrapper.properties`。它们是接入前的远端核实结果,不代表
本仓库已经构建通过。`T-001` 接入时必须再次确认远端 commit,并把最终采用的 commit
作为可复现基线。
上游启用了 Google Services 4.4.2、Firebase Crashlytics Gradle Plugin 3.0.2 和
Firebase BOM 33.7.0,但 `google-services.json` 被 `.gitignore` 排除。干净构建必须
提供本项目自己的 Firebase 配置,或者在不需要遥测时移除相关插件和依赖;不得提交
真实 Firebase 配置。
## 关键决策
- 统一后端同时服务管理 Web 与 Android App;不是两套业务后端。
- 首版管理页面使用服务端渲染,避免在验证阶段维护独立前端构建链。
- Go Blueprint 只生成起始目录;正式代码必须删除演示逻辑,并按
`04-architecture.md` 的领域边界重组。
- SQLite 只服务单实例验证;出现多服务实例、并发写或正式备份要求时迁移 PostgreSQL。
- VLM 厂商可替换,领域层只接收结构化请求和结果,不传播供应商 SDK 类型。
- 拼多多自动化是独立工作流模块,不能耦合后端数据库实现或管理页面。
## 骨架选择记录
- 来源:[`Melkeydev/go-blueprint`](https://github.com/Melkeydev/go-blueprint)
- 固定版本:`v0.10.11`(MIT)
- 生成目标:`Gin + SQLite`
- 不启用:React、HTMX、WebSocket、Redis、Docker 等高级特性
计划生成命令:
```powershell
go install github.com/melkeydev/go-blueprint@v0.10.11
go-blueprint create --name backend-api --framework gin --driver sqlite --git skip
```
Go Blueprint v0.10.11 当前生成的是 `Go 1.25.0 + Gin 1.12.0`,不能直接作为本项目
的 `go.mod`。2026-07-25 已在临时目录将生成结果调整为以下版本,并在
`GOTOOLCHAIN=local` 下完成 `go mod tidy` 和 `go test ./...`:
```text
go 1.23.0
github.com/gin-gonic/gin v1.11.0
github.com/gin-contrib/cors v1.7.6
github.com/joho/godotenv v1.5.1
github.com/mattn/go-sqlite3 v1.14.48
```
Gin v1.12.0 的 `go.mod` 要求 Go 1.25.0,因此本项目禁止升级到 Gin 1.12.x,除非先
单独批准升级 Go 工具链。正式接入还必须修正:
- 健康检查不得调用 `log.Fatal` 终止进程。
- 删除包级数据库单例和包加载阶段读取环境变量的写法。
- 关闭不需要的默认 CORS,不提交生成的 `.env`。
- 正确关闭数据库和 HTTP Server,注入 config/repository 以便测试。
- `mattn/go-sqlite3` 需要 CGO 和 GCC;构建环境必须显式验证。
不选择 `go-admin-team/go-admin`:Vue、多租户、Casbin RBAC、代码生成和定时任务
超出 MVP。不选择 `evrone/go-clean-template`:当前模板以 Fiber、PostgreSQL、
RabbitMQ、NATS 和 gRPC 为主,不符合最小 Gin + SQLite 边界。
## 计划目录
```text
android-buyer/ # Kotlin Android App
backend-api/
cmd/api/ # 进程入口,只负责装配和生命周期
internal/domain/ # 实体、状态机和确定性规则
internal/usecase/ # 创建、领取、执行和结果归档
internal/transport/http/ # Gin handler、中间件和页面
internal/repository/sqlite/ # database/sql 仓储
internal/platform/ # 配置、日志、文件和 VLM 适配器
migrations/ # Goose SQL migration
web/templates/ # html/template
web/static/ # 少量 CSS/JS
var/ # 本地运行数据,必须忽略
docs/
```
目录在真实骨架建立后以代码为准并同步本文。
## 构建与运行命令
当前没有源码,以下是计划形状而非可运行证据:
| 用途 | 计划命令 | 当前状态 |
| --- | --- | --- |
| Android 构建 | `android-buyer\gradlew.bat assembleDebug` | 待 `T-001` |
| Android 单元测试 | `android-buyer\gradlew.bat test` | 待 `T-001` |
| 后端依赖 | `go mod download`(在 `backend-api/`) | 待 `T-201` |
| 后端测试 | `go test ./...`(在 `backend-api/`) | 待 `T-201` |
| 后端构建 | `go build -o bin/cmroubao-api.exe ./cmd/api` | 待 `T-201` |
| 后端启动 | `go run ./cmd/api` | 待 `T-201` |
| 数据迁移 | `goose -dir migrations sqlite3 ./var/cmroubao.db up` | 待 `T-201` |
任何命令只有实际执行成功后才能写入 `init.ps1`、`init.sh` 和
`current-state.md` 的“当前可运行内容”。
## 依赖纪律
- 接入 Roubao 后优先使用其已有 HTTP、序列化、依赖注入和 UI 方案。
- 扩大 Shizuku 使用范围,或新增 OCR、浏览器自动化和第二套网络库前必须证明已有
能力不足。
- 后端新增库要说明用途;验证版不引入 ORM、消息队列、Redis、微服务或 SPA 框架。
- Go 依赖必须固定到 `go.mod`/`go.sum`;构建和 CI 不使用未固定的 `@latest`。
- `go.mod` 必须声明 `go 1.23.0`;验证使用 `GOTOOLCHAIN=local go test ./...` 或
PowerShell 等价环境变量,确保依赖没有暗中要求更高 Go 版本。
- handler 不直接写 SQL,repository 不依赖 Gin,domain/usecase 不导入具体数据库驱动。
- 密钥和设备令牌通过环境变量或本地忽略配置注入,不进入 Git。