feat(gateway): 真实鉴权片1 —— JWT 注册/登录 + 校验中间件(后端核心)

替掉"裸 X-User-ID 头当身份"的临时方案,落地无状态 JWT 鉴权后端:

- internal/auth:JWT 签发/校验(HS256,密钥 env JWT_SECRET,仅接受 HMAC 防 alg 混淆)
  + bcrypt 密码哈希/校验。纯包,含单测。
- User 模型加 Name + PasswordHash(json:"-" 不外泄);store 加 CreateUser/GetUserByEmail/
  GetUserByID(邮箱唯一冲突 → ErrUserExists)。
- handler/auth:POST /auth/register(建用户+签发)· POST /auth/login(校验+签发,
  用户不存在与密码错同一文案防枚举)· GET /auth/me。
- middleware/auth:解析 Bearer JWT,校验通过把已验证 userID 注入上下文(非阻断)。
- userID(c) 改为优先取 JWT 注入的 uid,兜底 X-User-ID 头(前端尚未接登录,保持可用)。

验证:
- 单测:JWT 签发/解析往返、过期拒绝、篡改/非法拒绝、bcrypt 哈希校验。
- 实跑(nats+pg+gateway):注册→token+user(无密码)、重复注册 409、错密码 401、
  /auth/me 带 token 200 / 无 token 401;owner 隔离改用已验证 uid —— 带 token 建的库
  匿名/伪造 header 都看不到(JWT 用户数据归于雪花 id,header 无法臆测)。

片 2 待做:前端登录页 + 存令牌带 Bearer + 处理 401 + 去掉 header 兜底 + 保护路由。

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
Blizzard
2026-06-17 16:14:21 +08:00
parent 3ae009db38
commit 149c35c21b
12 changed files with 345 additions and 13 deletions
+6 -5
View File
@@ -27,6 +27,7 @@ require (
github.com/go-playground/universal-translator v0.18.1 // indirect
github.com/go-playground/validator/v10 v10.20.0 // indirect
github.com/goccy/go-json v0.10.2 // indirect
github.com/golang-jwt/jwt/v5 v5.3.1 // indirect
github.com/google/uuid v1.6.0 // indirect
github.com/jackc/pgpassfile v1.0.0 // indirect
github.com/jackc/pgservicefile v0.0.0-20240606120523-5a60cdf6a761 // indirect
@@ -58,11 +59,11 @@ require (
go.uber.org/atomic v1.11.0 // indirect
go.yaml.in/yaml/v3 v3.0.4 // indirect
golang.org/x/arch v0.11.0 // indirect
golang.org/x/crypto v0.51.0 // indirect
golang.org/x/net v0.53.0 // indirect
golang.org/x/sync v0.20.0 // indirect
golang.org/x/sys v0.44.0 // indirect
golang.org/x/text v0.37.0 // indirect
golang.org/x/crypto v0.53.0 // indirect
golang.org/x/net v0.55.0 // indirect
golang.org/x/sync v0.21.0 // indirect
golang.org/x/sys v0.46.0 // indirect
golang.org/x/text v0.38.0 // indirect
google.golang.org/protobuf v1.36.10 // indirect
gopkg.in/ini.v1 v1.67.2 // indirect
gopkg.in/yaml.v3 v3.0.1 // indirect