access-control-rbac
Scannednpx machina-cli add skill secondsky/claude-skills/access-control-rbac --openclawAccess Control & RBAC
Implement secure access control systems with fine-grained permissions using RBAC, ABAC, or hybrid approaches.
Access Control Models
| Model | Description | Best For |
|---|---|---|
| RBAC | Role-based - users assigned to roles with permissions | Most applications |
| ABAC | Attribute-based - policies evaluate user/resource attributes | Complex rules |
| MAC | Mandatory - system-enforced classification levels | Government/military |
| DAC | Discretionary - resource owners control access | File systems |
| ReBAC | Relationship-based - access via entity relationships | Social apps |
Node.js RBAC Implementation
class Permission {
constructor(resource, action) {
this.resource = resource;
this.action = action;
}
matches(resource, action) {
return (this.resource === '*' || this.resource === resource) &&
(this.action === '*' || this.action === action);
}
}
class Role {
constructor(name, permissions = [], parent = null) {
this.name = name;
this.permissions = permissions;
this.parent = parent;
}
hasPermission(resource, action) {
if (this.permissions.some(p => p.matches(resource, action))) return true;
return this.parent?.hasPermission(resource, action) ?? false;
}
}
class RBACSystem {
constructor() {
this.roles = new Map();
this.userRoles = new Map();
}
createRole(name, permissions = [], parentRole = null) {
const parent = parentRole ? this.roles.get(parentRole) : null;
this.roles.set(name, new Role(name, permissions, parent));
}
assignRole(userId, roleName) {
const userRoles = this.userRoles.get(userId) || [];
userRoles.push(this.roles.get(roleName));
this.userRoles.set(userId, userRoles);
}
can(userId, resource, action) {
const roles = this.userRoles.get(userId) || [];
return roles.some(role => role.hasPermission(resource, action));
}
}
// Express middleware
const requirePermission = (resource, action) => (req, res, next) => {
if (!rbac.can(req.user.id, resource, action)) {
return res.status(403).json({ error: 'Forbidden' });
}
next();
};
// Setup default roles
const rbac = new RBACSystem();
rbac.createRole('viewer', [new Permission('*', 'read')]);
rbac.createRole('editor', [new Permission('*', 'write')], 'viewer');
rbac.createRole('admin', [new Permission('*', '*')], 'editor');
Python ABAC Pattern
class Policy:
def __init__(self, name, effect, resource, action, conditions):
self.name = name
self.effect = effect # 'allow' or 'deny'
self.resource = resource
self.action = action
self.conditions = conditions
def matches(self, context):
if self.resource != "*" and self.resource != context.get("resource"):
return False
if self.action != "*" and self.action != context.get("action"):
return False
return True
def evaluate(self, context):
return all(cond(context) for cond in self.conditions)
class ABACEngine:
def __init__(self):
self.policies = []
def add_policy(self, policy):
self.policies.append(policy)
def check_access(self, context):
for policy in self.policies:
if policy.matches(context) and policy.evaluate(context):
return policy.effect == 'allow'
return False # Deny by default
# Condition functions
def is_resource_owner(ctx):
return ctx.get("user_id") == ctx.get("resource_owner_id")
def is_within_business_hours(ctx):
from datetime import datetime
return 9 <= datetime.now().hour < 18
See references/python-abac.md for complete implementation with Flask integration.
Java Spring Security
See references/java-spring-security.md for enterprise implementation with:
- Spring Security configuration
- Method-level security with
@PreAuthorize - Custom permission service
- Custom security expressions
Best Practices
Do:
- Apply least privilege principle
- Use role hierarchies to reduce duplication
- Audit all access changes
- Review permissions quarterly
- Cache permission checks for performance
- Separate authentication from authorization
Don't:
- Hardcode permission checks
- Allow permission creep without review
- Skip audit logging
- Use overly broad wildcards
References
Source
git clone https://github.com/secondsky/claude-skills/blob/main/plugins/access-control-rbac/skills/access-control-rbac/SKILL.mdView on GitHub Overview
This skill implements secure access control using role-based access control (RBAC), with optional ABAC or hybrid approaches. It covers defining roles, permissions, and role inheritance to support admin dashboards, enterprise access, and multi-tenant apps, while addressing complex policy relationships and conflicts.
How This Skill Works
Define roles with permission sets, optionally using a parent role to enable inheritance. Assign roles to users and check access with a can(userId, resource, action) query, then protect routes with middleware like requirePermission(resource, action). The included Node.js example demonstrates role creation, assignment, and permission checks, plus a Python ABAC pattern for flexible policies.
When to Use It
- Securing admin dashboards in SaaS or enterprise apps
- Provisioning users with least-privilege access via roles
- Multi-tenant apps needing tenant-scoped permissions
- Implementing fine-grained authorization for resources and actions
- Managing role inheritance and policy conflicts
Quick Start
- Step 1: Define roles and permissions (e.g., viewer, editor, admin) and any parent roles
- Step 2: Assign roles to users and wire up RBACSystem.can(userId, resource, action) checks
- Step 3: Protect routes with middleware (requirePermission(resource, action)) and test coverage
Best Practices
- Define small, cohesive roles with explicit permissions
- Use role inheritance sparingly to avoid ambiguity
- Bind RBAC checks into centralized middleware and authorization gates
- Regularly audit roles, permissions, and access logs
- Pair RBAC with ABAC or policies for exceptions and dynamic rules
Example Use Cases
- Admin, Editor, and Viewer roles in an admin dashboard
- Enterprise HR system restricting salary and payroll data
- Multi-tenant CRM where users access only their tenant data
- Content platform with read/write permissions and owner-based access
- Internal tools with progressive access via role inheritance (viewer -> editor -> admin)