feat: complete Phase 1 infrastructure
- erp-core: error types, shared types, event bus, ErpModule trait - erp-server: config loading, database/Redis connections, migrations - erp-server/migration: tenants table with SeaORM - apps/web: Vite + React 18 + TypeScript + Ant Design 5 + TailwindCSS - Web frontend: main layout with sidebar, header, routing - Docker: PostgreSQL 16 + Redis 7 development environment - All workspace crates compile successfully (cargo check passes)
This commit is contained in:
84
wiki/architecture.md
Normal file
84
wiki/architecture.md
Normal file
@@ -0,0 +1,84 @@
|
||||
# architecture (架构决策记录)
|
||||
|
||||
## 设计思想
|
||||
|
||||
ERP 平台采用 **模块化单体 + 渐进式拆分** 架构。核心原则:模块间零直接依赖,所有跨模块通信通过事件总线和 trait 接口。
|
||||
|
||||
## 关键架构决策
|
||||
|
||||
### Q: 为什么用模块化单体而非微服务?
|
||||
|
||||
**A:** ERP 系统的模块间数据一致性要求高,分布式事务成本大。单体起步,模块边界清晰,未来需要时可按模块拆分为微服务。`ErpModule` trait 天然支持这种渐进式迁移。
|
||||
|
||||
### Q: 为什么用 UUIDv7 而不是自增 ID?
|
||||
|
||||
**A:** UUIDv7 是时间排序的,既有 UUID 的分布式唯一性,又有接近自增 ID 的索引性能。对多租户 SaaS 尤其重要——不同租户的数据不会因为 ID 冲突而互相影响。
|
||||
|
||||
### Q: 为什么用 broadcast channel 做事件总线?
|
||||
|
||||
**A:** `tokio::sync::broadcast` 提供多消费者发布/订阅,语义匹配模块间事件通知。设计规格要求 outbox 模式(持久化到 domain_events 表),但当前 Phase 1 先用内存 broadcast,后续再补持久化。
|
||||
|
||||
### Q: 为什么错误类型跨 crate 边界必须用 thiserror?
|
||||
|
||||
**A:** `anyhow` 的错误没有类型信息,无法在 API 层做精确的 HTTP 状态码映射。`thiserror` 定义明确的错误变体,`AppError` 可以精确映射到 400/401/403/404/409/500。crate 内部可以用 `anyhow` 简化,但对外必须转 `AppError`。
|
||||
|
||||
### Q: 为什么 tenant_id 不在 API 路径中?
|
||||
|
||||
**A:** 从 JWT token 中提取 tenant_id,通过中间件注入 `TenantContext`。这防止了:
|
||||
- 用户手动修改 URL 访问其他租户数据
|
||||
- API 路径暴露租户信息
|
||||
- 开发者忘记检查租户权限
|
||||
|
||||
管理员接口例外,可以通过路径指定 tenant_id。
|
||||
|
||||
### Q: 为什么前端用 HashRouter 而非 BrowserRouter?
|
||||
|
||||
**A:** 部署时可能不在根路径下,HashRouter 不需要服务端配置 fallback 路由。对 SPA 来说更稳健。
|
||||
|
||||
## 模块依赖铁律
|
||||
|
||||
```
|
||||
erp-core (L1)
|
||||
erp-common (L1)
|
||||
|
|
||||
+--------------+--------------+--------------+
|
||||
| | | |
|
||||
erp-auth erp-config erp-workflow erp-message (L2)
|
||||
| | | |
|
||||
+--------------+--------------+--------------+
|
||||
|
|
||||
erp-server (L3: 唯一组装点)
|
||||
```
|
||||
|
||||
**禁止:**
|
||||
- L2 模块之间直接依赖
|
||||
- L1 模块依赖任何业务模块
|
||||
- 绕过事件总线直接调用其他模块
|
||||
|
||||
## 多租户隔离策略
|
||||
|
||||
**当前策略:共享数据库 + tenant_id 列过滤**
|
||||
|
||||
所有业务表包含 `tenant_id` 列,查询时通过中间件自动注入过滤条件。这是最简单的 SaaS 多租户方案,未来可扩展为:
|
||||
- Schema 隔离 — 每个租户独立 schema
|
||||
- 数据库隔离 — 每个租户独立数据库(私有化部署)
|
||||
|
||||
`ErpModule::on_tenant_created()` 和 `on_tenant_deleted()` 钩子确保模块能在租户创建/删除时初始化/清理数据。
|
||||
|
||||
## 技术选型理由
|
||||
|
||||
| 选择 | 理由 |
|
||||
|------|------|
|
||||
| Axum 0.8 | Tokio 团队维护,与 tower 生态无缝集成,类型安全路由 |
|
||||
| SeaORM 1.1 | 异步、类型安全、Rust 原生 ORM,迁移工具完善 |
|
||||
| PostgreSQL 16 | 企业级关系型数据库,JSON 支持好,扩展丰富 |
|
||||
| Redis 7 | 高性能缓存,会话存储,限流 token bucket |
|
||||
| React 19 + Ant Design 6 | 成熟的组件库,企业后台 UI 标配 |
|
||||
| Zustand | 极简状态管理,无 boilerplate |
|
||||
| utoipa | Rust 代码生成 OpenAPI 文档,零额外维护 |
|
||||
|
||||
## 关联模块
|
||||
|
||||
- **[[erp-core]]** — 架构契约的定义者
|
||||
- **[[erp-server]]** — 架构的组装执行者
|
||||
- **[[database]]** — 多租户隔离的物理实现
|
||||
73
wiki/database.md
Normal file
73
wiki/database.md
Normal file
@@ -0,0 +1,73 @@
|
||||
# database (数据库迁移与模式)
|
||||
|
||||
## 设计思想
|
||||
|
||||
数据库迁移使用 SeaORM Migration 框架,遵循以下原则:
|
||||
|
||||
- **所有表必须包含标准字段** — `id`(UUIDv7), `tenant_id`, `created_at`, `updated_at`, `created_by`, `updated_by`, `deleted_at`, `version`
|
||||
- **软删除** — 不执行硬删除,设置 `deleted_at` 时间戳
|
||||
- **乐观锁** — 更新时检查 `version` 字段
|
||||
- **多租户隔离** — 所有业务表必须含 `tenant_id`,查询时自动过滤
|
||||
- **幂等迁移** — 使用 `if_not_exists` 确保可重复执行
|
||||
- **可回滚** — 每个迁移必须实现 `down()` 方法
|
||||
|
||||
## 代码逻辑
|
||||
|
||||
### 迁移文件命名规则
|
||||
```
|
||||
m{YYYYMMDD}_{6位序号}_{描述}.rs
|
||||
例: m20260410_000001_create_tenant.rs
|
||||
```
|
||||
|
||||
### 当前表结构
|
||||
|
||||
**tenant 表** (唯一已实现的表):
|
||||
| 列名 | 类型 | 约束 |
|
||||
|------|------|------|
|
||||
| id | UUID | PK, NOT NULL |
|
||||
| name | STRING | NOT NULL |
|
||||
| code | STRING | NOT NULL, UNIQUE |
|
||||
| status | STRING | NOT NULL, DEFAULT 'active' |
|
||||
| settings | JSON | NULLABLE |
|
||||
| created_at | TIMESTAMPTZ | NOT NULL, DEFAULT now() |
|
||||
| updated_at | TIMESTAMPTZ | NOT NULL, DEFAULT now() |
|
||||
| deleted_at | TIMESTAMPTZ | NULLABLE |
|
||||
|
||||
### 已知缺失字段
|
||||
tenant 表缺少 `BaseFields` 要求的:
|
||||
- `created_by` — 创建人
|
||||
- `updated_by` — 最后修改人
|
||||
- `version` — 乐观锁版本号
|
||||
|
||||
### 迁移执行
|
||||
```
|
||||
erp-server 启动 → Migrator::up(&db_conn) → 自动运行所有 pending 迁移
|
||||
```
|
||||
|
||||
## 关联模块
|
||||
|
||||
- **[[erp-core]]** — `BaseFields` 定义了标准字段规范,迁移表结构必须对齐
|
||||
- **[[erp-server]]** — 启动时自动运行迁移
|
||||
- **[[erp-auth]]** — Phase 2 将创建 users, roles, permissions 表
|
||||
- **[[erp-config]]** — Phase 3 将创建 system_configs 表
|
||||
- **[[erp-workflow]]** — Phase 4 将创建 workflow_definitions, workflow_instances 表
|
||||
- **[[erp-message]]** — Phase 5 将创建 messages, notification_settings 表
|
||||
|
||||
## 关键文件
|
||||
|
||||
| 文件 | 职责 |
|
||||
|------|------|
|
||||
| `crates/erp-server/migration/src/lib.rs` | Migrator 注册所有迁移 |
|
||||
| `crates/erp-server/migration/src/m20260410_000001_create_tenant.rs` | tenant 表迁移 |
|
||||
| `crates/erp-core/src/types.rs` | BaseFields 标准字段定义 |
|
||||
| `docker/docker-compose.yml` | PostgreSQL 16 服务定义 |
|
||||
|
||||
## 未来迁移计划 (按 Phase)
|
||||
|
||||
| Phase | 表 | 说明 |
|
||||
|-------|-----|------|
|
||||
| Phase 2 | users, roles, permissions, user_roles, role_permissions | RBAC + ABAC |
|
||||
| Phase 3 | system_configs, config_histories | 层级配置 |
|
||||
| Phase 4 | workflow_definitions, workflow_instances, workflow_tasks | BPMN 工作流 |
|
||||
| Phase 5 | messages, notification_settings, message_templates | 多渠道消息 |
|
||||
| 持续 | domain_events | 事件 outbox 表 |
|
||||
68
wiki/erp-core.md
Normal file
68
wiki/erp-core.md
Normal file
@@ -0,0 +1,68 @@
|
||||
# erp-core
|
||||
|
||||
## 设计思想
|
||||
|
||||
`erp-core` 是整个 ERP 平台的 L1 基础层,所有业务模块的唯一共同依赖。它的职责是定义**跨模块共享的契约**,而非实现业务逻辑。
|
||||
|
||||
核心设计决策:
|
||||
- **AppError 统一错误体系** — 6 种错误变体映射到 HTTP 状态码,业务 crate 只需 `?` 传播错误,由 Axum `IntoResponse` 自动转换
|
||||
- **EventBus 进程内广播** — 用 `tokio::sync::broadcast` 实现发布/订阅,模块间零耦合通信
|
||||
- **ErpModule 插件 trait** — 每个业务模块实现此 trait,由 `ModuleRegistry` 统一注册路由和事件处理器
|
||||
- **BaseFields 强制多租户** — 所有实体的基础字段模板,确保 `tenant_id` 从第一天就存在
|
||||
|
||||
## 代码逻辑
|
||||
|
||||
### 错误处理链
|
||||
```
|
||||
业务 crate (thiserror) → AppError → IntoResponse → HTTP JSON 响应
|
||||
数据库 (sea_orm::DbErr) → From 转换 → AppError (自动识别 duplicate key → Conflict)
|
||||
```
|
||||
|
||||
错误响应统一格式:`{ "error": "not_found", "message": "资源不存在", "details": null }`
|
||||
|
||||
### 事件总线
|
||||
```
|
||||
发布者: EventBus::publish(DomainEvent) → broadcast channel
|
||||
订阅者: EventBus::subscribe() → Receiver<DomainEvent>
|
||||
事件字段: id(UUIDv7), event_type("user.created"), tenant_id, payload(JSON), timestamp, correlation_id
|
||||
```
|
||||
|
||||
事件类型命名规则:`{模块}.{动作}` 如 `user.created`, `workflow.task.completed`
|
||||
|
||||
### 模块注册
|
||||
```
|
||||
业务模块实现 ErpModule trait → ModuleRegistry::register() →
|
||||
build_router(): 折叠所有模块的 register_routes() → Axum Router
|
||||
register_handlers(): 注册所有模块的事件处理器 → EventBus
|
||||
```
|
||||
|
||||
### 共享类型
|
||||
- `TenantContext` — 中间件注入的租户上下文(tenant_id, user_id, roles, permissions)
|
||||
- `Pagination` / `PaginatedResponse<T>` — 分页查询标准化(每页上限 100)
|
||||
- `ApiResponse<T>` — API 统一信封 `{ success, data, message }`
|
||||
|
||||
## 关联模块
|
||||
|
||||
- **[[erp-server]]** — 消费所有 erp-core 类型和 trait,是唯一组装点
|
||||
- **[[erp-auth]]** — 实现 `ErpModule` trait,发布认证事件
|
||||
- **[[erp-workflow]]** — 实现 `ErpModule` trait,订阅业务事件
|
||||
- **[[erp-message]]** — 实现 `ErpModule` trait,订阅通知事件
|
||||
- **[[erp-config]]** — 实现 `ErpModule` trait
|
||||
- **[[database]]** — 迁移表结构必须与 `BaseFields` 对齐
|
||||
|
||||
## 关键文件
|
||||
|
||||
| 文件 | 职责 |
|
||||
|------|------|
|
||||
| `crates/erp-core/src/error.rs` | AppError 定义、HTTP 映射、From 转换 |
|
||||
| `crates/erp-core/src/events.rs` | DomainEvent、EventBus、EventHandler trait |
|
||||
| `crates/erp-core/src/module.rs` | ErpModule trait、ModuleRegistry |
|
||||
| `crates/erp-core/src/types.rs` | BaseFields、Pagination、ApiResponse、TenantContext |
|
||||
| `crates/erp-core/src/lib.rs` | 模块导出入口 |
|
||||
|
||||
## 当前状态
|
||||
|
||||
**已实现,Phase 1 可用。** 但以下部分尚未被 erp-server 集成:
|
||||
- `ModuleRegistry` 未在 `main.rs` 中使用
|
||||
- `EventBus` 未创建实例
|
||||
- `TenantContext` 未通过中间件注入
|
||||
66
wiki/erp-server.md
Normal file
66
wiki/erp-server.md
Normal file
@@ -0,0 +1,66 @@
|
||||
# erp-server
|
||||
|
||||
## 设计思想
|
||||
|
||||
`erp-server` 是 L3 层——**唯一的组装点**。它不包含业务逻辑,只负责把所有业务模块组装成可运行的服务。
|
||||
|
||||
核心决策:
|
||||
- **配置优先** — 使用 `config` crate 从 TOML 文件 + 环境变量加载,`ERP__` 前缀覆盖(如 `ERP__DATABASE__URL`)
|
||||
- **启动序列严格有序** — 配置 → 日志 → 数据库 → 迁移 → Redis → 路由 → 监听,每步失败即终止
|
||||
- **单一入口** — 所有模块通过 `ModuleRegistry` 注册,server 本身不直接 import 业务模块的类型
|
||||
|
||||
## 代码逻辑
|
||||
|
||||
### 启动流程 (`main.rs`)
|
||||
```
|
||||
1. AppConfig::load() ← config/default.toml + 环境变量
|
||||
2. init_tracing(level) ← JSON 格式日志
|
||||
3. db::connect(&db_config) ← SeaORM 连接池 (max=20, min=5)
|
||||
4. Migrator::up(&db_conn) ← 运行所有待执行迁移
|
||||
5. redis::Client::open(url) ← Redis 客户端(当前未使用)
|
||||
6. Router::new() ← 当前仅有 404 fallback
|
||||
7. bind(host, port).serve() ← 启动 HTTP 服务
|
||||
```
|
||||
|
||||
### 配置结构
|
||||
```
|
||||
AppConfig
|
||||
├── server: ServerConfig { host: "0.0.0.0", port: 3000 }
|
||||
├── database: DatabaseConfig { url, max_connections: 20, min_connections: 5 }
|
||||
├── redis: RedisConfig { url: "redis://localhost:6379" }
|
||||
├── jwt: JwtConfig { secret, access_token_ttl, refresh_token_ttl }
|
||||
└── log: LogConfig { level: "info" }
|
||||
```
|
||||
|
||||
### 当前状态
|
||||
- 数据库连接池正常工作
|
||||
- 迁移自动执行
|
||||
- **没有注册任何路由** — 仅返回 404
|
||||
- **没有使用 ModuleRegistry** — 未集成业务模块
|
||||
- Redis 客户端已创建但未执行任何命令
|
||||
- 缺少 CORS、压缩、请求追踪中间件
|
||||
|
||||
## 关联模块
|
||||
|
||||
- **[[erp-core]]** — 提供 AppError、ErpModule trait、ModuleRegistry
|
||||
- **[[database]]** — 迁移文件通过 `erp-server-migration` crate 引用
|
||||
- **[[infrastructure]]** — Docker 提供 PostgreSQL 和 Redis 服务
|
||||
- **[[frontend]]** — Vite 代理 `/api` 请求到 server 的 3000 端口
|
||||
|
||||
## 关键文件
|
||||
|
||||
| 文件 | 职责 |
|
||||
|------|------|
|
||||
| `crates/erp-server/src/main.rs` | 服务启动入口 |
|
||||
| `crates/erp-server/src/config.rs` | 5 个配置 struct + 加载逻辑 |
|
||||
| `crates/erp-server/src/db.rs` | SeaORM 连接池配置 |
|
||||
| `crates/erp-server/config/default.toml` | 默认配置值 |
|
||||
| `crates/erp-server/Cargo.toml` | 依赖声明 |
|
||||
|
||||
## 待完成 (Phase 1 剩余)
|
||||
|
||||
1. 实例化 `ModuleRegistry` 并注册模块
|
||||
2. 添加 CORS 中间件(tower-http)
|
||||
3. 添加请求追踪中间件
|
||||
4. 将 Redis 连接注入 AppState
|
||||
5. 健康检查端点 (`/api/v1/health`)
|
||||
81
wiki/frontend.md
Normal file
81
wiki/frontend.md
Normal file
@@ -0,0 +1,81 @@
|
||||
# frontend (Web 前端)
|
||||
|
||||
## 设计思想
|
||||
|
||||
前端是一个 Vite + React SPA,遵循 **UI 层只做展示** 的原则:
|
||||
|
||||
- **组件库优先** — 使用 Ant Design,不自造轮子
|
||||
- **状态集中** — Zustand 管理全局状态(主题、侧边栏、认证)
|
||||
- **API 层分离** — HTTP 调用封装到 service 层,组件不直接 fetch
|
||||
- **代理开发** — Vite 开发服务器代理 `/api` 到后端 3000 端口
|
||||
|
||||
版本实际使用情况(与设计规格有差异):
|
||||
| 技术 | 规格 | 实际 |
|
||||
|------|------|------|
|
||||
| React | 18 | 19.2.4 |
|
||||
| Ant Design | 5 | 6.3.5 |
|
||||
| React Router | 7 | 7.14.0 |
|
||||
|
||||
## 代码逻辑
|
||||
|
||||
### 应用结构
|
||||
```
|
||||
main.tsx → App.tsx (ConfigProvider + HashRouter) → MainLayout → 各页面组件
|
||||
```
|
||||
|
||||
### MainLayout 布局
|
||||
经典 SaaS 后台管理布局:
|
||||
- **左侧 Sidebar** — 可折叠暗色菜单,分组:首页/用户/权限/设置
|
||||
- **顶部 Header** — 侧边栏切换 + 通知徽标(硬编码5) + 头像("Admin")
|
||||
- **中间 Content** — React Router Outlet,多标签页切换
|
||||
- **底部 Footer** — 租户名 + 版本号
|
||||
|
||||
### 状态管理 (Zustand)
|
||||
```typescript
|
||||
appStore {
|
||||
isLoggedIn: boolean // 未使用,无登录页
|
||||
tenantName: string // 默认 "ERP Platform"
|
||||
theme: 'light' | 'dark' // 切换 Ant Design 主题
|
||||
sidebarCollapsed: boolean
|
||||
toggleSidebar(), setTheme(), login(), logout()
|
||||
}
|
||||
```
|
||||
|
||||
### 开发服务器代理
|
||||
```
|
||||
http://localhost:5173/api/* → http://localhost:3000/* (API)
|
||||
ws://localhost:5173/ws/* → ws://localhost:3000/* (WebSocket)
|
||||
```
|
||||
|
||||
### 当前状态
|
||||
- 布局壳体完整,暗色/亮色主题切换可用
|
||||
- 只有一个路由 `/` → 占位 HomePage ("Welcome to ERP Platform")
|
||||
- 无 API 调用、无认证流程、无真实数据
|
||||
- 通知计数硬编码为 5,用户名硬编码为 "Admin"
|
||||
- 未实现 i18n(代码中有 zh_CN locale 但文案硬编码)
|
||||
|
||||
## 关联模块
|
||||
|
||||
- **[[erp-server]]** — API 后端,通过 Vite proxy 连接
|
||||
- **[[infrastructure]]** — Docker 提供 PostgreSQL + Redis
|
||||
|
||||
## 关键文件
|
||||
|
||||
| 文件 | 职责 |
|
||||
|------|------|
|
||||
| `apps/web/src/main.tsx` | React 入口 |
|
||||
| `apps/web/src/App.tsx` | 根组件:ConfigProvider + 路由 |
|
||||
| `apps/web/src/layouts/MainLayout.tsx` | 完整后台管理布局 |
|
||||
| `apps/web/src/stores/app.ts` | Zustand 全局状态 |
|
||||
| `apps/web/src/index.css` | TailwindCSS 导入 |
|
||||
| `apps/web/vite.config.ts` | Vite 配置 + API 代理 |
|
||||
| `apps/web/package.json` | 依赖声明 |
|
||||
|
||||
## 待实现 (按 Phase)
|
||||
|
||||
| Phase | 内容 |
|
||||
|-------|------|
|
||||
| Phase 2 | 登录页、用户管理页、角色权限页 |
|
||||
| Phase 3 | 系统配置管理页 |
|
||||
| Phase 4 | 工作流设计器、审批列表 |
|
||||
| Phase 5 | 消息中心、通知设置 |
|
||||
65
wiki/index.md
Normal file
65
wiki/index.md
Normal file
@@ -0,0 +1,65 @@
|
||||
# ERP 平台底座 — 知识库
|
||||
|
||||
## 项目画像
|
||||
|
||||
**模块化 SaaS ERP 底座**,Rust + React 技术栈,提供身份权限/工作流/消息/配置四大基础模块,支持行业业务模块快速插接。
|
||||
|
||||
关键数字:
|
||||
- 8 个 Rust crate(4 个 placeholder),1 个前端 SPA
|
||||
- 1 个数据库迁移(tenant 表)
|
||||
- Phase 1 基础设施完成约 85%
|
||||
|
||||
## 模块导航树
|
||||
|
||||
### L1 基础层
|
||||
- [[erp-core]] — 错误体系 · 事件总线 · 模块 trait · 共享类型
|
||||
- [[erp-common]] — 共享工具(当前为 stub)
|
||||
|
||||
### L2 业务层(均为 placeholder)
|
||||
- erp-auth — 身份与权限(Phase 2)
|
||||
- erp-config — 系统配置(Phase 3)
|
||||
- erp-workflow — 工作流引擎(Phase 4)
|
||||
- erp-message — 消息中心(Phase 5)
|
||||
|
||||
### L3 组装层
|
||||
- [[erp-server]] — Axum 服务入口 · 配置加载 · 数据库连接 · 迁移执行
|
||||
|
||||
### 基础设施
|
||||
- [[database]] — SeaORM 迁移 · 多租户表结构 · 软删除模式
|
||||
- [[infrastructure]] — Docker Compose · PostgreSQL 16 · Redis 7
|
||||
- [[frontend]] — React SPA · Ant Design 布局 · Zustand 状态
|
||||
|
||||
### 横切关注点
|
||||
- [[architecture]] — 架构决策记录 · 设计原则 · 技术选型理由
|
||||
|
||||
## 核心架构决策
|
||||
|
||||
**模块间如何通信?** 通过 [[erp-core]] 的 EventBus 发布/订阅 DomainEvent,不直接依赖。
|
||||
|
||||
**多租户怎么隔离?** 共享数据库 + tenant_id 列过滤,中间件从 JWT 注入 TenantContext。详见 [[database]] 和 [[architecture]]。
|
||||
|
||||
**错误怎么传播?** 业务 crate 用 thiserror → AppError → Axum IntoResponse 自动转 HTTP。详见 [[erp-core]] 错误处理链。
|
||||
|
||||
**为什么没有路由?** Phase 1 只搭建基础设施。ModuleRegistry 已定义但未集成到 [[erp-server]],Phase 2 开始注册路由。
|
||||
|
||||
**版本差异怎么办?** package.json 使用 React 19 + Ant Design 6(比规格文档更新),以实际代码为准。
|
||||
|
||||
## 开发进度
|
||||
|
||||
| Phase | 内容 | 状态 |
|
||||
|-------|------|------|
|
||||
| 1 | 基础设施 | 85% — 缺 README、ModuleRegistry 集成、中间件 |
|
||||
| 2 | 身份与权限 | 待开始 |
|
||||
| 3 | 系统配置 | 待开始 |
|
||||
| 4 | 工作流引擎 | 待开始 |
|
||||
| 5 | 消息中心 | 待开始 |
|
||||
| 6 | 整合与打磨 | 待开始 |
|
||||
|
||||
## 关键文档索引
|
||||
|
||||
| 文档 | 位置 |
|
||||
|------|------|
|
||||
| 设计规格 | `docs/superpowers/specs/2026-04-10-erp-platform-base-design.md` |
|
||||
| 实施计划 | `docs/superpowers/plans/2026-04-10-erp-platform-base-plan.md` |
|
||||
| 协作规则 | `CLAUDE.md` |
|
||||
| 设计评审 | `plans/squishy-pondering-aho-agent-a23c7497aadc6da41.md` |
|
||||
57
wiki/infrastructure.md
Normal file
57
wiki/infrastructure.md
Normal file
@@ -0,0 +1,57 @@
|
||||
# infrastructure (Docker 与开发环境)
|
||||
|
||||
## 设计思想
|
||||
|
||||
开发环境使用 Docker Compose 提供基础设施服务,应用服务在宿主机运行。这种设计允许:
|
||||
- 后端 Rust 服务快速重启(无需容器化构建)
|
||||
- 前端 Vite 热更新直接在宿主机
|
||||
- 数据库和缓存服务标准化,团队成员环境一致
|
||||
|
||||
## 代码逻辑
|
||||
|
||||
### 服务配置
|
||||
|
||||
| 服务 | 镜像 | 端口 | 用途 |
|
||||
|------|------|------|------|
|
||||
| erp-postgres | postgres:16-alpine | 5432 | 主数据库 |
|
||||
| erp-redis | redis:7-alpine | 6379 | 缓存 + 会话 |
|
||||
|
||||
### 连接信息
|
||||
```
|
||||
PostgreSQL: postgres://erp:erp_dev_2024@localhost:5432/erp
|
||||
Redis: redis://localhost:6379
|
||||
```
|
||||
|
||||
### 健康检查
|
||||
- PostgreSQL: `pg_isready` 每 5 秒,5 次重试
|
||||
- Redis: `redis-cli ping` 每 5 秒,5 次重试
|
||||
|
||||
### 数据持久化
|
||||
- `postgres_data` — 命名卷,PostgreSQL 数据
|
||||
- `redis_data` — 命名卷,Redis 数据
|
||||
|
||||
### 环境变量
|
||||
通过 `docker/.env.example` 文档化,使用默认值即可启动开发环境。
|
||||
|
||||
## 关联模块
|
||||
|
||||
- **[[erp-server]]** — 连接 PostgreSQL 和 Redis
|
||||
- **[[database]]** — 迁移在 PostgreSQL 中执行
|
||||
- **[[frontend]]** — Vite 代理 API 到后端
|
||||
|
||||
## 关键文件
|
||||
|
||||
| 文件 | 职责 |
|
||||
|------|------|
|
||||
| `docker/docker-compose.yml` | 服务定义 |
|
||||
| `docker/.env.example` | 环境变量模板 |
|
||||
| `crates/erp-server/config/default.toml` | 默认连接配置 |
|
||||
|
||||
## 常用命令
|
||||
|
||||
```bash
|
||||
cd docker && docker compose up -d # 启动服务
|
||||
docker compose -f docker/docker-compose.yml ps # 查看状态
|
||||
docker compose -f docker/docker-compose.yml down # 停止
|
||||
docker exec -it erp-postgres psql -U erp # 连接数据库
|
||||
```
|
||||
Reference in New Issue
Block a user