topfans/backend/gateway/README.md
2026-04-07 22:29:48 +08:00

403 lines
7.3 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.

# Top-Fans Gateway 网关服务
## 📋 概述
Top-Fans Gateway 是一个基于 Gin 框架的 HTTP 网关,负责:
- 接收客户端 HTTP 请求
- JWT Token 认证和验证
- 将 HTTP 请求转换为 Dubbo RPC 调用
- 通过 Dubbo Attachments 传递用户信息到后端微服务
---
## 🏗️ 架构
```
客户端 (Mobile/Web)
↓ HTTP/HTTPS + JWT Token
Gin Gateway (本服务)
↓ Dubbo RPC + Attachments
UserService (Dubbo 微服务)
Database
```
---
## 📦 安装依赖
```bash
cd backend/gateway
# ⚠️ 重要:先配置 Go 代理(避免 TLS 证书错误)
export GOPROXY=https://goproxy.io,direct
# 安装依赖
go mod tidy
```
**常见问题**
- 如果遇到 `tls: failed to verify certificate` 错误,请使用上面的代理配置
- 可选代理:`https://proxy.golang.org,direct` 或 `https://mirrors.aliyun.com/goproxy/,direct`
---
## ⚙️ 配置
网关通过环境变量配置,支持的环境变量:
| 环境变量 | 说明 | 默认值 |
|---------|------|--------|
| `SERVER_PORT` | 网关监听端口 | `8080` |
| `GIN_MODE` | Gin 运行模式 (`debug`, `release`, `test`) | `debug` |
| `DUBBO_USER_SERVICE_URL` | UserService Dubbo 地址 | `127.0.0.1:20000` |
| `JWT_SECRET` | JWT 密钥 | `topfans-secret-key-please-change-in-production` |
### 配置示例
```bash
# 开发环境
export SERVER_PORT=8080
export GIN_MODE=debug
export DUBBO_USER_SERVICE_URL=127.0.0.1:20000
# 生产环境
export SERVER_PORT=8080
export GIN_MODE=release
export DUBBO_USER_SERVICE_URL=prod-userservice:20000
export JWT_SECRET=your-secure-secret-key
```
---
## 🚀 启动服务
### 方式 1直接运行
```bash
cd backend/gateway
go run main.go
```
### 方式 2编译后运行
```bash
cd backend/gateway
go build -o gateway main.go
./gateway
```
### 方式 3使用环境变量
```bash
cd backend/gateway
SERVER_PORT=8080 GIN_MODE=debug go run main.go
```
---
## 📡 API 接口
### 公开接口(无需认证)
#### 1. 健康检查
```bash
GET /health
```
#### 2. 用户注册
```bash
POST /api/v1/auth/register
Content-Type: application/json
{
"mobile": "13800000001",
"password": "password123",
"star_id": 87,
"nickname": "测试用户"
}
```
#### 3. 用户登录
```bash
POST /api/v1/auth/login
Content-Type: application/json
{
"mobile": "13800000001",
"password": "password123"
}
# 响应
{
"base": {...},
"accessToken": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
"expiresIn": "86400",
"user": {...},
"fanProfile": {...}
}
```
#### 4. 获取指定用户信息
```bash
GET /api/v1/users/:user_id
```
#### 5. 获取粉丝档案
```bash
GET /api/v1/fan-profiles?user_id=44&star_id=87
```
#### 6. 获取明星列表
```bash
GET /api/v1/fan-identities?keyword=
```
### 受保护接口(需要认证)
**请求头格式**
```
Authorization: Bearer <access_token>
```
#### 1. 获取当前用户信息
```bash
GET /api/v1/auth/me
Authorization: Bearer <token>
```
#### 2. 获取当前用户粉丝档案
```bash
GET /api/v1/me/profile
Authorization: Bearer <token>
```
#### 3. 更新昵称
```bash
PUT /api/v1/me/nickname
Authorization: Bearer <token>
Content-Type: application/json
{
"nickname": "新昵称"
}
```
#### 4. 更新密码
```bash
POST /api/v1/account/password
Authorization: Bearer <token>
Content-Type: application/json
{
"old_password": "password123",
"new_password": "newpassword456"
}
```
#### 5. 添加粉丝身份
```bash
POST /api/v1/my/fan-identities
Authorization: Bearer <token>
Content-Type: application/json
{
"star_id": 88,
"nickname": "粉丝小红"
}
```
#### 6. 切换粉丝身份
```bash
POST /api/v1/my/fan-identities/switch
Authorization: Bearer <token>
Content-Type: application/json
{
"new_star_id": 88
}
```
#### 7. 刷新 Token
```bash
POST /api/v1/auth/refresh
Authorization: Bearer <token>
```
#### 8. 登出
```bash
POST /api/v1/auth/logout
Authorization: Bearer <token>
```
---
## 🧪 测试
### 完整测试流程
```bash
# 1. 启动 UserService
cd backend/services/userService
go run main.go
# 2. 启动 Gateway新终端
cd backend/gateway
go run main.go
# 3. 测试注册
curl -X POST http://localhost:8080/api/v1/auth/register \
-H "Content-Type: application/json" \
-d '{
"mobile": "13800000001",
"password": "password123",
"star_id": 87,
"nickname": "测试用户"
}'
# 4. 测试登录
TOKEN=$(curl -s -X POST http://localhost:8080/api/v1/auth/login \
-H "Content-Type: application/json" \
-d '{
"mobile": "13800000001",
"password": "password123"
}' | jq -r '.accessToken')
echo "Token: $TOKEN"
# 5. 测试获取当前用户信息(需要认证)
curl -X GET http://localhost:8080/api/v1/auth/me \
-H "Authorization: Bearer $TOKEN"
# 6. 测试获取粉丝档案
curl -X GET http://localhost:8080/api/v1/me/profile \
-H "Authorization: Bearer $TOKEN"
```
---
## 📂 项目结构
```
gateway/
├── main.go # 主入口
├── go.mod # 依赖管理
├── README.md # 本文档
├── config/
│ └── config.go # 配置管理
├── middleware/
│ └── auth_middleware.go # JWT 认证中间件
├── controller/
│ ├── auth_controller.go # 认证控制器(登录、注册等)
│ └── user_controller.go # 用户控制器(需要认证的接口)
└── router/
└── router.go # 路由配置
```
---
## 🔑 认证流程
```
1. 客户端登录
POST /api/v1/auth/login
2. Gateway 转发到 UserService
Dubbo RPC: Login()
3. UserService 验证用户,生成 JWT
4. 返回 accessToken 给客户端
5. 客户端访问受保护接口
GET /api/v1/auth/me
Header: Authorization: Bearer <token>
6. Gateway 认证中间件验证 JWT
7. 提取 user_id, star_id
8. Gateway 通过 Dubbo Attachments 传递
ctx = context.WithValue(ctx, constant.AttachmentKey, map[string]interface{}{
"user_id": user_id,
"star_id": star_id,
})
9. UserService 从 Attachments 获取用户信息
userID := dubbo.GetAttachment(ctx, "user_id")
10. 执行业务逻辑,返回结果
```
---
## 📝 日志
日志文件存储在 `logs/` 目录:
- `logs/gateway.log` - 网关日志
查看日志:
```bash
tail -f logs/gateway.log
```
---
## ⚠️ 注意事项
1. **生产环境必须修改 JWT_SECRET**
2. **建议使用 HTTPS**
3. **配置合适的 CORS 策略**
4. **定期轮换 JWT 密钥**
5. **监控网关性能和错误率**
---
## 🐛 常见问题
### 1. 连接 Dubbo 服务失败
```
Error: Failed to create Dubbo client
```
**解决方案**
- 确保 UserService 正在运行
- 检查 `DUBBO_USER_SERVICE_URL` 配置是否正确
- 检查网络连接
### 2. Token 验证失败
```
Error: invalid or expired token
```
**解决方案**
- 确保 Gateway 和 UserService 使用相同的 JWT_SECRET
- 检查 Token 是否过期
- 确认 Token 格式正确Bearer + 空格 + token
### 3. 端口冲突
```
Error: bind: address already in use
```
**解决方案**
- 修改 `SERVER_PORT` 环境变量
- 或停止占用该端口的其他进程
---
## 📚 相关文档
- [完整测试流程](../services/userService/完整测试流程.md)
- [网关架构说明](../services/userService/网关架构说明.md)
- [Proto 定义](../proto/user.proto)
---
**版本**v1.0.0
**最后更新**2026-01-04