Files
backend/pkg/auth/casbin.go

125 lines
2.9 KiB
Go
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

package auth
import (
"fmt"
"sync"
"github.com/casbin/casbin/v2"
gormadapter "github.com/casbin/gorm-adapter/v3"
"go.uber.org/zap"
"gorm.io/gorm"
)
// CasbinService Casbin权限服务
type CasbinService struct {
enforcer *casbin.Enforcer
logger *zap.Logger
mu sync.RWMutex
}
// NewCasbinService 创建Casbin服务
func NewCasbinService(db *gorm.DB, modelPath string, logger *zap.Logger) (*CasbinService, error) {
// 使用Gorm适配器自动使用casbin_rule表
adapter, err := gormadapter.NewAdapterByDBUseTableName(db, "", "casbin_rule")
if err != nil {
return nil, fmt.Errorf("创建Casbin适配器失败: %w", err)
}
// 创建Enforcer
enforcer, err := casbin.NewEnforcer(modelPath, adapter)
if err != nil {
return nil, fmt.Errorf("创建Casbin执行器失败: %w", err)
}
// 加载策略
if err := enforcer.LoadPolicy(); err != nil {
return nil, fmt.Errorf("加载Casbin策略失败: %w", err)
}
logger.Info("Casbin权限服务初始化成功")
return &CasbinService{
enforcer: enforcer,
logger: logger,
}, nil
}
// Enforce 检查权限
// sub: 主体(用户角色), obj: 资源, act: 操作
func (s *CasbinService) Enforce(sub, obj, act string) (bool, error) {
s.mu.RLock()
defer s.mu.RUnlock()
return s.enforcer.Enforce(sub, obj, act)
}
// CheckPermission 检查用户权限(便捷方法)
func (s *CasbinService) CheckPermission(role, resource, action string) bool {
allowed, err := s.Enforce(role, resource, action)
if err != nil {
s.logger.Error("权限检查失败",
zap.String("role", role),
zap.String("resource", resource),
zap.String("action", action),
zap.Error(err),
)
return false
}
return allowed
}
// AddPolicy 添加策略
func (s *CasbinService) AddPolicy(sub, obj, act string) (bool, error) {
s.mu.Lock()
defer s.mu.Unlock()
return s.enforcer.AddPolicy(sub, obj, act)
}
// RemovePolicy 移除策略
func (s *CasbinService) RemovePolicy(sub, obj, act string) (bool, error) {
s.mu.Lock()
defer s.mu.Unlock()
return s.enforcer.RemovePolicy(sub, obj, act)
}
// AddRoleForUser 为用户添加角色
func (s *CasbinService) AddRoleForUser(user, role string) (bool, error) {
s.mu.Lock()
defer s.mu.Unlock()
return s.enforcer.AddRoleForUser(user, role)
}
// GetRolesForUser 获取用户的角色
func (s *CasbinService) GetRolesForUser(user string) []string {
s.mu.RLock()
defer s.mu.RUnlock()
roles, _ := s.enforcer.GetRolesForUser(user)
return roles
}
// GetPermissionsForRole 获取角色的所有权限
func (s *CasbinService) GetPermissionsForRole(role string) [][]string {
s.mu.RLock()
defer s.mu.RUnlock()
perms, _ := s.enforcer.GetPermissionsForUser(role)
return perms
}
// ReloadPolicy 重新加载策略
func (s *CasbinService) ReloadPolicy() error {
s.mu.Lock()
defer s.mu.Unlock()
return s.enforcer.LoadPolicy()
}
// GetEnforcer 获取原始Enforcer用于高级操作
func (s *CasbinService) GetEnforcer() *casbin.Enforcer {
return s.enforcer
}