An open API service indexing awesome lists of open source software.

https://github.com/javierav/pundit-before

Before hook for Pundit
https://github.com/javierav/pundit-before

before hook pundit rails ruby

Last synced: 4 months ago
JSON representation

Before hook for Pundit

Awesome Lists containing this project

README

          

# Pundit::Before

![CI](https://github.com/javierav/pundit-before/workflows/CI/badge.svg)

Adds `before` hook to pundit policy classes to resolve things like varvet/pundit#474. Inspired by action_policy
[pre-checks](https://actionpolicy.evilmartians.io/#/pre_checks).

## Installation

Add this line to your application's Gemfile:

```ruby
gem "pundit-before"
```

And then execute:

```shell
bundle install
```

## Usage

Use `allow!` inside callback method or block to return `true` without evaluating `edit?` method defined in policy.

```ruby
class UserPolicy < ApplicationPolicy
include Pundit::Before

before :check_admin

def edit?
false
end

private

def check_admin
allow! if user.admin?
end
end

UserPolicy.new(User.new(admin: true), record).edit? # => true
UserPolicy.new(User.new(admin: false), record).edit? # => false
```

Use `deny!` inside callback method or block to return `false` without evaluating `edit?` method defined in policy.

```ruby
class UserPolicy < ApplicationPolicy
include Pundit::Before

before :check_admin

def edit?
true
end

private

def check_admin
deny! unless user.admin?
end
end

UserPolicy.new(User.new(admin: true), record).edit? # => true
UserPolicy.new(User.new(admin: false), record).edit? # => false
```

Internally `before` hook is implemented as `ActiveSupport::Callbacks`, so the callback chain will halt if do any call to
`allow!` or `deny!` method. It's similar as Rails controller action filters works.

### block form

```ruby
class UserPolicy < ApplicationPolicy
include Pundit::Before

before do
allow! if user.admin?
end

def edit?
false
end
end
```

### skip before hook

```ruby
class UserPolicy < ApplicationPolicy
include Pundit::Before

before :check_admin

def edit?
false
end

private

def check_admin
allow! if user.admin?
end
end

class OperatorPolicy < UserPolicy
skip_before :check_admin
end

UserPolicy.new(User.new(admin: true), record).edit? # => true
OperatorPolicy.new(User.new(admin: true), record).edit? # => false
```

### using `only` modifier

```ruby
class UserPolicy < ApplicationPolicy
include Pundit::Before

before :check_admin, only: :update?

def edit?
false
end

private

def check_admin
allow! if user.admin?
end
end

UserPolicy.new(User.new(admin: true), record).edit? # => false
```

### using `except` modifier

```ruby
class UserPolicy < ApplicationPolicy
include Pundit::Before

before :check_admin, except: :edit?

def edit?
false
end

def destroy?
false
end

private

def check_admin
allow! if user.admin?
end
end

UserPolicy.new(User.new(admin: true), record).edit? # => false
UserPolicy.new(User.new(admin: true), record).destroy? # => true
```

### calling multiple methods

```ruby
class UserPolicy < BasePolicy
before :check_presence, :check_admin

def edit?
false
end

private

def check_presence
deny! unless user.present?
end

def check_admin
allow! if user.admin?
end
end

UserPolicy.new(nil, record).edit? # => false
UserPolicy.new(User.new(admin: false), record).edit? # => false
UserPolicy.new(User.new(admin: true), record).edit? # => true
```

## Development

After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake test` to run the tests.
You can also run `bin/console` for an interactive prompt that will allow you to experiment.

To install this gem onto your local machine, run `bin/rake install`.

To release a new version, update the version number in `version.rb`, and then run `bin/rake release`,
which will create a git tag for the version, push git commits and the created tag, and push the `.gem` file to
[rubygems.org](https://rubygems.org).

## License

Copyright © 2023 Javier Aranda. Released under the terms of the [MIT license](LICENSE).