Rabarber
Simple role-based authorization library for Ruby on Rails
Install / Use
/learn @enjaku4/RabarberREADME
Rabarber: Simple Role-Based Authorization for Rails
Rabarber is a role-based authorization library for Ruby on Rails. It provides a set of tools for managing user roles and defining access rules, with support for multi-tenancy through context.
Example of Usage:
Consider a CRM system where users with different roles have distinct access levels. For instance, the role accountant can access invoice data but not marketing information, while the role analyst can view marketing data but not detailed financial records. You can define such authorization rules easily with Rabarber.
And this is how your controller might look with Rabarber:
class TicketsController < ApplicationController
grant_access roles: :admin
grant_access action: :index, roles: :manager
def index
# ...
end
def destroy
# ...
end
end
This means that admin users can access everything in TicketsController, while the manager role can access only the index action.
Table of Contents
Gem Usage:
- Installation
- Configuration
- User Role Methods
- Direct Role Management
- Authorization
- Dynamic Authorization Rules
- When Unauthorized
- Context / Multi-tenancy
- View Helpers
Community Resources:
Installation
Add Rabarber to your Gemfile:
gem "rabarber"
Install the gem:
bundle install
Generate the migration to store roles (replace users with your table name if different):
# For standard integer IDs
rails generate rabarber:roles users
# For UUID primary keys
rails generate rabarber:roles users --uuid
Run the migration:
rails db:migrate
Configuration
Create an initializer to customize Rabarber's behavior (optional):
Rabarber.configure do |config|
config.cache_enabled = true # Enable/disable role caching (default: true)
config.current_user_method = :current_user # Method to access current user (default: :current_user)
config.user_model_name = "User" # User model name (default: "User")
end
Roles are cached by default for better performance. Clear the cache manually when needed:
Rabarber::Cache.clear
User Role Methods
Your user model is automatically augmented with role management methods:
Role Assignment
# Assign roles (creates roles if they don't exist)
user.assign_roles(:admin, :manager)
# Assign only existing roles (don't create new ones)
user.assign_roles(:accountant, :manager, create_new: false)
# Revoke specific roles
user.revoke_roles(:admin, :manager)
# Revoke all roles
user.revoke_all_roles
All role assignment methods return the list of roles currently assigned to the user.
Role Queries
# Check if user has any of the specified roles
user.has_role?(:accountant, :manager)
# Get user's roles in the global context
user.roles
# Get all user's roles grouped by context
user.all_roles
# Get users with any of the specified roles
User.with_role(:admin, :manager)
Direct Role Management
You can also manage roles directly:
# Create a new role
Rabarber.create_role(:admin) # => true if created, false if already exists
# Rename a role
Rabarber.rename_role(:admin, :administrator) # => true if renamed, false if new name exists or role is assigned
Rabarber.rename_role(:admin, :administrator, force: true) # Force rename even if role is assigned
# Remove a role
Rabarber.delete_role(:admin) # => true if deleted, false if role is assigned
Rabarber.delete_role(:admin, force: true) # Force deletion even if role is assigned
# List available roles in the global context
Rabarber.roles
# List all available roles grouped by context
Rabarber.all_roles
Note: Some methods have been deprecated in favor of the new API shown above. Deprecated methods still work but will be removed in a future major version. See the changelog for the complete list of deprecated methods and their replacements.
Authorization
Setup
Include Rabarber::Authorization module in your controllers and configure protection:
class ApplicationController < ActionController::Base
include Rabarber::Authorization
with_authorization # Enable authorization check for all actions in all controllers by default
end
You can also enable authorization checks selectively. Both with_authorization and skip_authorization work exactly the same as Rails' before_action and skip_before_action methods:
class TicketsController < ApplicationController
skip_authorization only: [:index, :show] # Skip authorization for specific actions
end
class InvoicesController < ApplicationController
with_authorization except: [:index] # Enable authorization for all actions except index
end
Authorization requires an authenticated user. Rabarber will raise an error if no user is found via the configured current_user_method. Ensure authentication happens before authorization.
Authorization Rules
Define authorization rules using grant_access:
class TicketsController < ApplicationController
# Controller-wide access
grant_access roles: :admin
# Action-specific access
grant_access action: :index, roles: [:manager, :support]
def index
# Accessible to admin, manager, and support roles
end
def destroy
# Accessible to admin role only
end
end
Authorization rules are additive - they combine across inheritance chains and when defined multiple times for the same action:
class BaseController < ApplicationController
grant_access roles: :admin # Admin can access everything
end
class InvoicesController < BaseController
grant_access roles: :accountant # Accountant can also access InvoicesController (along with admin)
grant_access action: :index, roles: :manager
grant_access action: :index, roles: :supervisor
def index
# Index is accessible to admin, accountant, manager, and supervisor
end
end
It's possible to omit roles to allow unrestricted access:
class UnrestrictedController < ApplicationController
grant_access # Allow all users to access all actions
end
class MixedController < ApplicationController
grant_access action: :index # Unrestricted index action
def index
# Accessible to all users
end
grant_access action: :show, roles: :member # Restricted show action
def show
# Accessible to members only
end
end
Dynamic Authorization Rules
For more complex scenarios, Rabarber supports dynamic authorization rules:
class OrdersController < ApplicationController
grant_access roles: :manager, unless: -> { current_user.suspended? }
grant_access action: :show, roles: :client, if: :user_company_matches_order?
def show
# ...
end
private
def user_company_matches_order?
current_user.company == Order.find(params[:id]).company
end
end
You can pass a dynamic rule as an if or unless argument, which can be a symbol or a proc. Symbols refer to instance methods, and procs are evaluated in the controller at request time.
Dynamic rules can also be used without roles at all, allowing you to define custom logic or even delegate to custom policy objects:
class InvoicesController < ApplicationController
grant_access action: :update, unless: -> { Date.current.on_weekend? }
def update
# ...
end
grant_access action: :destroy, if: :destroy_allowed?
def destroy
# ...
end
private
def destroy_allowed?
InvoicePolicy.new(current_user).destroy?(Invoice.find(params[:id]))
end
end
When Unauthorized
By default, when unauthorized, Rabarber will redirect back (HTML format) or return 403 (other formats). You can override when_unauthorized method to customize unauthorized access behavior:
class ApplicationController < ActionController::Base
include Rabarber::Authorization
with_authorization
private
def when_unauthorized
head :not_found # Custom behavior to hide existence of protected resources
end
end
The when_unauthorized method can be overridden in any controller to provide controller-specific unauthorized access handling.
Context / Multi-tenancy
Rabarber supports multi-tenancy through its context feature. All Rabarber methods accept a context parameter, allowing you to work with roles within specific scopes. By default, context is nil, meaning roles are global. Context can also be an instance of an ActiveRecord model or a class.
For example, in a project management app, you might want users to have different roles in different projects - someone could be an owner in one project but just a member in another.
Contextual Role Assignment and Queries
# Assign roles within a specific model instance
user.assign_roles(:owner, context: project)
user.assign_roles(:member, context: project)
# Assign roles within a model class
user.assign_roles(:admin, context: Project)
# Check contextual roles
user.has_role?(:owner, context: project)
user.has_role?(:admin, context: Project)
# Revoke roles
user.revoke_roles(:owner, context: project)
# Get user roles
user.roles(context: project)
Related Skills
healthcheck
334.5kHost security hardening and risk-tolerance configuration for OpenClaw deployments
node-connect
334.5kDiagnose OpenClaw node connection and pairing failures for Android, iOS, and macOS companion apps
prose
334.5kOpenProse VM skill pack. Activate on any `prose` command, .prose files, or OpenProse mentions; orchestrates multi-agent workflows.
frontend-design
82.2kCreate distinctive, production-grade frontend interfaces with high design quality. Use this skill when the user asks to build web components, pages, or applications. Generates creative, polished code that avoids generic AI aesthetics.
