mengstack-api/internal/modules/rbac/middleware/permission.go
MengStack Dev f8c374a624 feat(rbac): M3 RBAC 权限模型完整实现
- 4 表设计: permissions, roles, role_permissions(m2m), user_roles
- 多租户隔离: 角色和用户角色分配按 tenant_id 隔离
- 权限并集: 多角色用户取权限并集,无继承
- 系统角色保护: is_system 角色不可修改/删除
- 种子数据: 7 个默认权限 + 3 个系统角色(super_admin/tenant_admin/member)
- 权限中间件: RequirePermission 支持按路由粒度控制
- API 路由: /api/v1/rbac/ 下完整 CRUD 端点
- fx 注册: RBAC Module 集成到 app.go
2026-10-03 00:54:26 +08:00

42 lines
1022 B
Go

package middleware
import (
"net/http"
"mengstack/internal/modules/rbac/application"
"github.com/gin-gonic/gin"
)
type PermissionMiddleware struct {
svc *application.Service
}
type RequirePermissionFunc func(permCode string) gin.HandlerFunc
func NewPermissionMiddleware(svc *application.Service) *PermissionMiddleware {
return &PermissionMiddleware{svc: svc}
}
func (m *PermissionMiddleware) RequirePermission(permCode string) gin.HandlerFunc {
return func(c *gin.Context) {
userID, exists := c.Get("user_id")
if !exists {
c.AbortWithStatusJSON(http.StatusUnauthorized, gin.H{"code": -1, "message": "unauthorized"})
return
}
has, err := m.svc.UserHasPermission(c.Request.Context(), userID.(uint), permCode)
if err != nil {
c.AbortWithStatusJSON(http.StatusInternalServerError, gin.H{"code": -1, "message": "permission check failed"})
return
}
if !has {
c.AbortWithStatusJSON(http.StatusForbidden, gin.H{"code": -1, "message": "permission denied"})
return
}
c.Next()
}
}