You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

146 lines
3.7 KiB

package middleware
import (
"fmt"
"net/http"
"gofaster/internal/auth/model"
"gofaster/internal/auth/repository"
"github.com/gin-gonic/gin"
"gorm.io/gorm"
)
// PermissionMiddleware 权限中间件
func PermissionMiddleware(db *gorm.DB, jwtSecret string) gin.HandlerFunc {
return func(c *gin.Context) {
// 获取用户信息
userID := GetUserID(c)
if userID == 0 {
c.JSON(http.StatusUnauthorized, gin.H{"error": "用户未认证"})
c.Abort()
return
}
// 获取当前请求的路由信息
path := c.Request.URL.Path
method := c.Request.Method
// 检查路由映射
routeMappingRepo := repository.NewRouteMappingRepository(db)
routeMapping, err := routeMappingRepo.FindByBackendRoute(path, method)
if err != nil {
// 如果找不到路由映射,允许通过(可能是公开接口)
c.Next()
return
}
// 检查用户是否有权限访问该路由
if err := checkUserPermission(db, userID, routeMapping); err != nil {
c.JSON(http.StatusForbidden, gin.H{"error": fmt.Sprintf("权限不足: %s", err.Error())})
c.Abort()
return
}
c.Next()
}
}
// checkUserPermission 检查用户权限
func checkUserPermission(db *gorm.DB, userID uint, routeMapping *model.RouteMapping) error {
// 这里实现三级权限检查逻辑
// 1. 菜单级别权限
// 2. 权限组级别权限
// 3. 路由级别权限
// 暂时返回nil,允许所有已认证用户访问
// TODO: 实现完整的权限检查逻辑
return nil
}
// OptionalPermissionMiddleware 可选的权限中间件(不强制要求权限)
func OptionalPermissionMiddleware(db *gorm.DB, jwtSecret string) gin.HandlerFunc {
return func(c *gin.Context) {
// 获取用户信息
userID := GetUserID(c)
if userID == 0 {
// 没有用户信息,继续处理请求
c.Next()
return
}
// 获取当前请求的路由信息
path := c.Request.URL.Path
method := c.Request.Method
// 检查路由映射
routeMappingRepo := repository.NewRouteMappingRepository(db)
routeMapping, err := routeMappingRepo.FindByBackendRoute(path, method)
if err != nil {
// 如果找不到路由映射,继续处理请求
c.Next()
return
}
// 检查用户是否有权限访问该路由
if err := checkUserPermission(db, userID, routeMapping); err != nil {
// 权限不足,但因为是可选权限,所以继续处理请求
c.Set("permission_warning", fmt.Sprintf("权限不足: %s", err.Error()))
}
c.Next()
}
}
// GetRouteAuthGroup 获取路由的权限分组
func GetRouteAuthGroup(c *gin.Context, db *gorm.DB) string {
path := c.Request.URL.Path
method := c.Request.Method
routeMappingRepo := repository.NewRouteMappingRepository(db)
routeMapping, err := routeMappingRepo.FindByBackendRoute(path, method)
if err != nil {
return "Unknown"
}
// 根据模块和HTTP方法确定权限组
return getAuthGroupByMethod(routeMapping.Module, routeMapping.HTTPMethod)
}
// getAuthGroupByMethod 根据模块和HTTP方法确定权限组
func getAuthGroupByMethod(module, method string) string {
switch method {
case "GET":
return "read"
case "POST":
return "create"
case "PUT", "PATCH":
return "update"
case "DELETE":
return "delete"
default:
return "unknown"
}
}
// HasPermission 检查用户是否有指定权限
func HasPermission(c *gin.Context, db *gorm.DB, requiredAuthGroup string) bool {
userID := GetUserID(c)
if userID == 0 {
return false
}
// 获取当前路由的权限分组
currentAuthGroup := GetRouteAuthGroup(c, db)
// 简单的权限检查逻辑
// Read权限可以访问Read和Edit
// Edit权限只能访问Edit
if requiredAuthGroup == "Read" {
return currentAuthGroup == "Read" || currentAuthGroup == "Edit"
} else if requiredAuthGroup == "Edit" {
return currentAuthGroup == "Edit"
}
return false
}