File size: 4,996 Bytes
9853396 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 | # 开发指南
---
## 架构设计
AxonHub 实现了一个双向数据转换管道,确保客户端与 AI 提供商之间的无缝通信。
<div align="center">
<img src="../../transformation-flow.svg" alt="AxonHub Transformation Flow" width="900"/>
</div>
### 管道组件
| 组件 | 用途 | 关键特性 |
| --- | --- | --- |
| **客户端** | 应用层 | Web 应用、移动应用、API 客户端 |
| **入站转换器** | 请求预处理 | 解析、验证、规范化输入 |
| **统一请求** | 核心处理 | 路由选择、负载均衡、故障转移 |
| **出站转换器** | 提供商适配 | 格式转换、协议映射 |
| **提供商** | AI 服务 | OpenAI、Anthropic、DeepSeek 等 |
该架构确保:
- ⚡ **低延迟**:优化的处理管道
- 🔄 **自动故障转移**:无缝提供商切换
- 📊 **实时监控**:完整的请求追踪
- 🛡️ **安全与验证**:输入清理与输出校验
## 技术栈
### 后端技术栈
- **Go 1.24+**
- **Gin**
- **Ent ORM**
- **gqlgen**
- **JWT**
### 前端技术栈
- **React 19**
- **TypeScript**
- **Tailwind CSS**
- **TanStack Router**
- **Zustand**
## 开发环境搭建
### 前置要求
- Go 1.24 或更高版本
- Node.js 18+ 与 pnpm
- Git
### 克隆项目
```bash
git clone https://github.com/looplj/axonhub.git
cd axonhub
```
### 启动后端
```bash
# 方式 1:直接构建并运行
make build-backend
./axonhub
# 方式 2:使用 air 热重载(推荐)
go install github.com/air-verse/air@latest
air
```
后端服务默认启动在 `http://localhost:8090`。
### 启动前端
在新的终端窗口中:
```bash
cd frontend
pnpm install
pnpm dev
```
前端开发服务器默认启动在 `http://localhost:5173`。
## 项目构建
### 构建完整项目
```bash
make build
```
该命令会构建后端与前端,并将前端产物嵌入到后端二进制文件中。
### 仅构建后端
```bash
make build-backend
```
### 仅构建前端
```bash
cd frontend
pnpm build
```
## 代码生成
当修改 Ent schema 或 GraphQL schema 后,需要重新生成代码:
```bash
make generate
```
## 测试
### 运行后端测试
```bash
go test ./...
```
### 运行 E2E 测试
```bash
bash ./scripts/e2e/e2e-test.sh
```
## 代码质量
### 运行 Go Linter
```bash
golangci-lint run -v
```
### 运行前端 Lint/格式化检查
```bash
cd frontend
pnpm lint
pnpm format:check
```
## 事务处理(Ent)
### 何时使用事务
- 多次写入需要保证“要么全部成功,要么全部失败”。
- 需要在同一个逻辑操作中保证读写一致性。
### 推荐:使用 `AbstractService.RunInTransaction`
`RunInTransaction` 会:
- 如果 `ctx` 已经携带事务,则复用当前事务。
- 否则开启新事务,将 tx 绑定的 `*ent.Client` 放入 `ctx`,并自动 commit/rollback。
```go
func (s *SomeService) doWork(ctx context.Context) error {
return s.RunInTransaction(ctx, func(ctx context.Context) error {
// ctx 现在同时携带:
// - ent.TxFromContext(ctx)(当前 tx)
// - ent.FromContext(ctx)(绑定到 tx 的 *ent.Client)
//
// 可以继续调用其它 service,它们会通过 ctx 复用同一个事务。
return nil
})
}
```
### 注意事项
- 事务 client 不适合在多个 goroutine 间共享。
- 事务作用域尽量保持小,并避免在事务内执行耗时 I/O。
## 添加新的 Channel
新增渠道时需要同时关注后端与前端的改动:
1. **在 Ent Schema 中扩展枚举**
- 在 [internal/ent/schema/channel.go](../../../internal/ent/schema/channel.go) 的 `field.Enum("type")` 列表里添加新的渠道标识
- 执行 `make generate` 以生成代码与迁移
2. **在业务层构造 Transformer**
- 在 `ChannelService.buildChannel` 的 switch 中为新枚举返回合适的 outbound transformer
- 必要时在 `internal/llm/transformer` 下实现新的 transformer
3. **注册 Provider 元数据**
- 在 [frontend/src/features/channels/data/config_providers.ts](../../../frontend/src/features/channels/data/config_providers.ts) 添加或扩展 Provider 配置
- 确保 `channelTypes` 中引用的渠道都已经在 `CHANNEL_CONFIGS` 中存在
4. **同步前端的 schema 与展示**
- 将枚举值加入 [frontend/src/features/channels/data/schema.ts](../../../frontend/src/features/channels/data/schema.ts) 的 Zod schema
- 在 [frontend/src/features/channels/data/constants.ts](../../../frontend/src/features/channels/data/constants.ts) 中添加渠道配置
5. **添加国际化**
- 在两个 locale 文件中补充翻译:
- [frontend/src/locales/en.json](../../../frontend/src/locales/en.json)
- [frontend/src/locales/zh.json](../../../frontend/src/locales/zh.json)
|