Miau
Miau (MIcro AUthorization) is a simple authorization gem for Rails inspired by Pundit and Banken. Miau provides a set of helpers which restricts what resources a given user is allowed to access.
Installation
As usual:
# Gemfile
gem "miau"
and run "bundle install".
Usage (as intended)
# app/models/application_controller.rb
class ApplicationController < ActionController::Base
...
include Miau
...
end
# app/controllers/posts_controller.rb # app/views/posts/update.erb
class PostsController < ApplicationController <% if authorized? %>
... ...
def update <% else %>
... ...
authorize! <% end %>
...
end
...
end
# app/policies/application_policy.rb # app/policies/posts_policy.rb
class ApplicationPolicy class PostsPolicy < ApplicationPolicy
attr_reader :user, :resource, :action ...
def update
... user.admin? && resource.published?
end end
...
end
"authorize!" will raise an exception (which can be handled by "rescue") in case a policy returns "false" or isn't available.
"authorized?" will return the value of the policy.
"app/policies/application_policy.rb" is included in the gem.
Internals
At the bottom line based on a "policy" and an "action" a corresponding policy method is called.
The policy method has access to the "user" and the "resource".
The "controller" policy method has access to the "user" and the "action".
"user" is set by the default method "miau_user" (can be overwritten) as:
# app/models/application_controller.rb
...
def miau_user
current_user
end
...
The default value for "policy" is inferred from "params[:controller]", i.e. "authorize!" called from "PostsController" will set the "policy" to "PostsPolicy".
The default value for "action" is set by "params[:action]".
"resource" may be set as a parameter.
A full blown sample :
authorize! article, policy: :posts, action: :show
Usage (more elaborated)
# app/models/application_controller.rb
class ApplicationController
...
include Miau
...
after_action { verify_authorized }
def miau_user
current_user
end
rescue Miau::NotDefinedError
# do some logging or whatever
rescue Miau::NotAuthorizedError
# do some logging or whatever
rescue Miau::AuthorizationNotPerformedError
# do some logging or whatever
...
end
Policies remain as before. Rescue's may be inserted previously in the exception chain.
"verify_authorized" checks that an "authorize!" has been called.
Authorize Controller
Sometimes a whole controller can be authorized, e.g. all actions requires admin priviledges.
The corresponding authorization is triggered by a "before_action :authorize_controller!". The corresponding policy is defined by (e.g):
class PostsPolicy < ApplicationPolicy
...
def controller
user.is_admin?
end
...
end
DRYing
# app/policies/posts_policy.rb --> # app/policies/posts_policy.rb
class PostsPolicy < ApplicationPolicy class PostsPolicy < ApplicationPolicy
def new miau %i[create edit], :new
user.admin? && Time.now.monday?
end def new
user.admin? && Time.now.monday?
def create end
user.admin? && Time.now.monday? ...
end end
def edit
user.admin? && Time.now.monday?
end
...
end
PORO
Miau is a small gem, it just provides a few helpers. All of the policy classes are just plain Ruby classes, allowing DRY, encapsulation, aliasing and inheritance.
There is no magic behind the scenes. Just the embedding in Rails required some specific knowledge.
Miscellaneous
Copyright (c) 2021-2024 Dittmar Krall (www.matiq.com), released under the MIT license.