GoLand 项目从 0 到 1:第四天 —— 技术选型落地与方案设计
第四天核心任务:表设计、接口文档、权限体系搭建、认证落地
首先我们确定了技术选型:Golang + docker + 社区版配置中心 + min.io(文件存储)+ PgSQL(关系型数据库)+ Redis + Neo4j(记忆图谱)+docker-compse+ansible+shell+python
项目模块分配:我负责用户权限管理及文档列表
主要任务:表设计,接口文档设计,实现方案等
一、模块概述:用户权限管理的核心目标
用户权限管理模块需实现三大核心功能:
- 用户 - 角色 - 权限的关联管理:通过多表关联实现灵活的权限分配
- 接口级权限校验:每个接口请求需经过权限验证,确保合法访问
- 身份认证与会话管理:基于 JWT 实现无状态的用户身份验证
同时需支撑文档列表模块的权限控制(如 “谁能查看 / 编辑哪些文档”),因此设计时需预留与业务模块的权限关联扩展点。
二、数据模型设计:五表联动的权限体系
为实现 “用户 - 角色 - 权限” 的多对多关系,设计五张核心表,形成完整的权限数据链路:
| 表名 | 作用 | 核心字段 |
|---|---|---|
tb_user | 存储用户基础信息 | id(用户 ID)、username(用户名)、password_hash(密码哈希) |
tb_role | 定义角色类型(如管理员、普通用户) | id(角色 ID)、role_name(角色名称)、description(描述) |
tb_user_role_ref | 用户与角色的关联映射 | id、user_id(关联用户)、role_id(关联角色) |
tb_permission | 定义权限点(如 “文档编辑”“用户管理”) | id、perm_key(权限标识,如doc:edit)、description |
tb_role_permission | 角色与权限的关联映射 | id、role_id(关联角色)、perm_id(关联权限) |
设计逻辑:
- 一个用户对应一个角色(如 “管理员 + 编辑”),通过
tb_user_role_ref关联 - 一个角色可包含多个权限(如 “管理员” 包含所有权限),通过
tb_role_permission关联 - 权限点与接口一一对应(如接口
/files/upload对应权限file:upload)
三、权限控制流程:从请求到响应的校验链路
通过时序图梳理权限校验的完整流程:

四、JWT 认证实现:无状态的身份验证
基于 JWT(JSON Web Token)实现用户身份认证,核心代码如下:
登录时生成JWT令牌
// Claims JWT声明结构
type Claims struct {UserID int64 `json:"user_id"`Username string `json:"username"`Role string `json:"role"`jwt.RegisteredClaims
}// GenerateToken 生成JWT令牌
func GenerateToken(userID int64, username, role string) (string, error) {cfg := config.GetConfig()claims := Claims{UserID: userID,Username: username,Role: role,RegisteredClaims: jwt.RegisteredClaims{ExpiresAt: jwt.NewNumericDate(time.Now().Add(time.Duration(cfg.JWT.ExpireTime) * time.Second)),IssuedAt: jwt.NewNumericDate(time.Now()),NotBefore: jwt.NewNumericDate(time.Now()),},}token := jwt.NewWithClaims(jwt.SigningMethodHS256, claims)return token.SignedString([]byte(cfg.JWT.Secret))
}
func main() {token, _ := GenerateToken(10000, "zhudayang", "admin")fmt.Println(token)
}// ParseToken 解析JWT令牌
func ParseToken(tokenString string) (*Claims, error) {cfg := config.GetConfig()token, err := jwt.ParseWithClaims(tokenString, &Claims{}, func(token *jwt.Token) (interface{}, error) {return []byte(cfg.JWT.Secret), nil})if err != nil {return nil, err}if claims, ok := token.Claims.(*Claims); ok && token.Valid {return claims, nil}return nil, errors.New("invalid token")
}// RefreshToken 刷新令牌
func RefreshToken(tokenString string) (string, error) {claims, err := ParseToken(tokenString)if err != nil {return "", err}// 生成新令牌return GenerateToken(claims.UserID, claims.Username, claims.Role)
}解析JWT令牌:
// Auth 认证中间件
func Auth() gin.HandlerFunc {return func(c *gin.Context) {// 获取Authorization头authHeader := c.GetHeader("Authorization")if authHeader == "" {stackTrace := getStackTrace()logger.Error(fmt.Sprintf(" | Authorization缺失 - method: %s | path: %s | client_ip: %s | user_agent: %s\nStack trace:\n%s",c.Request.Method,c.Request.URL.Path,c.ClientIP(),c.Request.UserAgent(),stackTrace,))response.Unauthorized(c, "Authorization header is required")c.Abort()return}// 检查Bearer前缀parts := strings.Split(authHeader, " ")if len(parts) != 2 || parts[0] != "Bearer" {stackTrace := getStackTrace()logger.Error(fmt.Sprintf(" | 无效token - method: %s | path: %s | client_ip: %s | auth_header: %s\nStack trace:\n%s",c.Request.Method,c.Request.URL.Path,c.ClientIP(),authHeader,stackTrace,))response.Unauthorized(c, "Invalid authorization header format")c.Abort()return}token := parts[1]// 解析JWT令牌claims, err := auth.ParseToken(token)if err != nil {stackTrace := getStackTrace()logger.Error(fmt.Sprintf(" | 解析JWT令牌 - method: %s | path: %s | client_ip: %s | error: %s\nStack trace:\n%s",c.Request.Method,c.Request.URL.Path,c.ClientIP(),err.Error(),stackTrace,))response.Unauthorized(c, "token is expired")c.Abort()return}// 将用户信息存储到上下文中c.Set("user_id", claims.UserID)c.Set("username", claims.Username)c.Set("role", claims.Role)// 记录认证成功logger.Info(fmt.Sprintf(" | 认证成功 - method: %s | path: %s | client_ip: %s | user_id: %d | username: %s | role: %s",c.Request.Method,c.Request.URL.Path,c.ClientIP(),claims.UserID,claims.Username,claims.Role,))c.Next()}
}六、总结与次日计划
第四天成果
- 完成用户权限管理模块的五表数据模型设计,明确 “用户 - 角色 - 权限” 的关联逻辑
- 梳理权限校验流程,通过时序图固化接口请求的权限判断链路
- 实现 JWT 令牌生成功能,为身份认证提供核心支撑
