CheckPermission 检查用户权限
(userID, resource, action string, context map[string]any)
| 519 | |
| 520 | // CheckPermission 检查用户权限 |
| 521 | func (ac *AccessController) CheckPermission(userID, resource, action string, context map[string]any) (*AccessDecision, error) { |
| 522 | start := time.Now() |
| 523 | |
| 524 | // 检查缓存 |
| 525 | cacheKey := ac.generateCacheKey(userID, resource, action, context) |
| 526 | if ac.cache != nil { |
| 527 | if entry := ac.cache.get(cacheKey); entry != nil { |
| 528 | decision := entry.decision |
| 529 | decision.CacheHit = true |
| 530 | decision.DecisionTime = time.Since(start) |
| 531 | return decision, nil |
| 532 | } |
| 533 | } |
| 534 | |
| 535 | ac.mu.RLock() |
| 536 | defer ac.mu.RUnlock() |
| 537 | |
| 538 | user, exists := ac.users[userID] |
| 539 | if !exists { |
| 540 | return &AccessDecision{ |
| 541 | Allowed: false, |
| 542 | Effect: PolicyEffectDeny, |
| 543 | Reason: "User not found", |
| 544 | DecisionTime: time.Since(start), |
| 545 | EvaluatedAt: time.Now(), |
| 546 | Context: context, |
| 547 | }, nil |
| 548 | } |
| 549 | |
| 550 | if !user.Enabled || user.Status != UserStatusActive { |
| 551 | return &AccessDecision{ |
| 552 | Allowed: false, |
| 553 | Effect: PolicyEffectDeny, |
| 554 | Reason: "User is disabled or inactive", |
| 555 | DecisionTime: time.Since(start), |
| 556 | EvaluatedAt: time.Now(), |
| 557 | Context: context, |
| 558 | }, nil |
| 559 | } |
| 560 | |
| 561 | decision := &AccessDecision{ |
| 562 | Allowed: false, |
| 563 | Effect: PolicyEffectDeny, |
| 564 | Reason: "Access denied", |
| 565 | Roles: user.Roles, |
| 566 | DecisionTime: time.Since(start), |
| 567 | EvaluatedAt: time.Now(), |
| 568 | Context: context, |
| 569 | } |
| 570 | |
| 571 | // 1. 检查显式策略 |
| 572 | policyDecision := ac.evaluatePolicies(userID, resource, action, context) |
| 573 | if policyDecision != nil { |
| 574 | decision.Allowed = policyDecision.Allowed |
| 575 | decision.Effect = policyDecision.Effect |
| 576 | decision.Reason = policyDecision.Reason |
| 577 | decision.Policies = policyDecision.Policies |
| 578 | } else { |