package middleware import ( "net/http" "strings" "github.com/edu-cloud/api-gateway/internal/observability" "github.com/gin-gonic/gin" ) // AdminRoleMiddleware 强制校验请求者具备 admin 角色。 // // 用途:保护 /api/admin/* 路由组(admin-portal 入口),拒绝非 admin 角色访问。 // 前置条件:必须在 AuthMiddleware 之后注册,依赖 AuthMiddleware 注入的 x-user-roles 头。 // // 响应规范(W1/W2 裁决):拒绝时返回 ActionState 信封, // 错误码 GW_FORBIDDEN,HTTP 403。 // // 注意:DevMode 旁路由 AuthMiddleware 注入 x-user-roles=teacher,admin, // 因此 dev-token 自动通过 admin 校验,无需在此重复 DevMode 判断。 func AdminRoleMiddleware() gin.HandlerFunc { return func(c *gin.Context) { rolesHeader := c.GetHeader("x-user-roles") if rolesHeader == "" { observability.IncAuthFailure("admin_missing_roles") abortGW(c, http.StatusForbidden, "GW_FORBIDDEN", "missing roles header") return } if !hasAdminRole(rolesHeader) { observability.IncAuthFailure("admin_role_required") abortGW(c, http.StatusForbidden, "GW_FORBIDDEN", "admin role required") return } c.Next() } } // hasAdminRole 判断逗号分隔的角色列表中是否包含 admin(大小写敏感)。 // 角色列表格式示例:"teacher,admin" / "admin" / "student,parent"。 func hasAdminRole(rolesHeader string) bool { for _, r := range strings.Split(rolesHeader, ",") { if strings.TrimSpace(r) == "admin" { return true } } return false }