Pundit provides authorization to the application.
Add this to your Gemfile
Pundit is focused around the notion of policy classes. A simple example of how to use policy is as shown below
class UserPolicy attr_reader :user, :record def initialize(user, record) @user = user @record = record end def create? user.super_admin? end end
- UserPolicy is the class name where User is the model and Policy is suffixed to it. This format should be followed when creating a policy.
- First argument is the currentuser. Pundit calls the currentuser method to get the result.
- Second argument is the model object.
- Method name in the policy class should be same as controller action. If the method name is not same then you should write in the controller the name as second argument.
How to use pundit in controller
- If controller action is same as policy method
Authorize method automatically starts looking for UserPolicy class and method as create? from action name
class UsersController < ApplicationController ... def create @user = User.build(parameters) authorize @user # Authorizing here if @user.save redirect_to users_path else render :new end end end
- If controller action is not same as policy method
Authorize method automatically starts looking for UserPolicy class and method as create? because it is passed explicitly
class UsersController < ApplicationController ... def invite @user = User.find(params[:id]) authorize @user, :create? # Authorizing here ... end end
How to pass additional arguments to policy
Pundit does not allow to pass additional arguments to policy class but in the cases where we have to pass additional arguments, you can use special wrapper class and pass it to policy.
If I have to pass organization_id(field) to policy, I will do as below
class UserContext attr_reader :user, :organization_id def initialize(user, organization_id) @user = user @organization_id = organization_id end end class ApplicationController include Pundit def pundit_user UserContext.new(current_user, request.organization_id) end end
Using that in a policy will be
class ProjectPolicy < ApplicationPolicy def show? user.user.admin? && user.user.organization_id == user.organization_id end end
Here I am allowing only the user who is admin and is same organization as the organization I am passing in the parameter to see the project page.
Keep Coding !!!
Contact us to work on your website.