# 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 ``` #### 1. 获取当前用户信息 ```bash GET /api/v1/auth/me Authorization: Bearer ``` #### 2. 获取当前用户粉丝档案 ```bash GET /api/v1/me/profile Authorization: Bearer ``` #### 3. 更新昵称 ```bash PUT /api/v1/me/nickname Authorization: Bearer Content-Type: application/json { "nickname": "新昵称" } ``` #### 4. 更新密码 ```bash POST /api/v1/account/password Authorization: Bearer Content-Type: application/json { "old_password": "password123", "new_password": "newpassword456" } ``` #### 5. 添加粉丝身份 ```bash POST /api/v1/my/fan-identities Authorization: Bearer Content-Type: application/json { "star_id": 88, "nickname": "粉丝小红" } ``` #### 6. 切换粉丝身份 ```bash POST /api/v1/my/fan-identities/switch Authorization: Bearer Content-Type: application/json { "new_star_id": 88 } ``` #### 7. 刷新 Token ```bash POST /api/v1/auth/refresh Authorization: Bearer ``` #### 8. 登出 ```bash POST /api/v1/auth/logout Authorization: Bearer ``` --- ## 🧪 测试 ### 完整测试流程 ```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 ↓ 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