2012-11-19 07:02:42 -05:00
|
|
|
require "pundit"
|
|
|
|
require "pry"
|
2013-06-17 19:13:07 -04:00
|
|
|
require "active_support/core_ext"
|
2012-11-19 07:02:42 -05:00
|
|
|
require "active_model/naming"
|
|
|
|
|
|
|
|
class PostPolicy < Struct.new(:user, :post)
|
|
|
|
def update?
|
|
|
|
post.user == user
|
|
|
|
end
|
|
|
|
def destroy?
|
|
|
|
false
|
|
|
|
end
|
|
|
|
def show?
|
|
|
|
true
|
|
|
|
end
|
|
|
|
end
|
|
|
|
class PostPolicy::Scope < Struct.new(:user, :scope)
|
|
|
|
def resolve
|
|
|
|
scope.published
|
|
|
|
end
|
|
|
|
end
|
|
|
|
class Post < Struct.new(:user)
|
|
|
|
def self.published
|
|
|
|
:published
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
class CommentPolicy < Struct.new(:user, :comment); end
|
|
|
|
class CommentPolicy::Scope < Struct.new(:user, :scope)
|
|
|
|
def resolve
|
|
|
|
scope
|
|
|
|
end
|
|
|
|
end
|
|
|
|
class Comment; extend ActiveModel::Naming; end
|
|
|
|
|
|
|
|
class Article; end
|
|
|
|
|
2012-11-30 10:21:46 -05:00
|
|
|
class BlogPolicy < Struct.new(:user, :blog); end
|
|
|
|
class Blog; end
|
|
|
|
class ArtificialBlog < Blog
|
|
|
|
def self.policy_class
|
|
|
|
BlogPolicy
|
|
|
|
end
|
|
|
|
end
|
2012-12-13 18:20:12 -05:00
|
|
|
class ArticleTag
|
|
|
|
def self.policy_class
|
|
|
|
Struct.new(:user, :tag) do
|
|
|
|
def show?
|
|
|
|
true
|
|
|
|
end
|
|
|
|
def destroy?
|
|
|
|
false
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
2012-11-30 10:21:46 -05:00
|
|
|
|
2012-11-19 07:02:42 -05:00
|
|
|
describe Pundit do
|
|
|
|
let(:user) { stub }
|
|
|
|
let(:post) { Post.new(user) }
|
|
|
|
let(:comment) { Comment.new }
|
|
|
|
let(:article) { Article.new }
|
|
|
|
let(:controller) { stub(:current_user => user, :params => { :action => "update" }).tap { |c| c.extend(Pundit) } }
|
2012-11-30 10:21:46 -05:00
|
|
|
let(:artificial_blog) { ArtificialBlog.new }
|
2012-12-13 18:20:12 -05:00
|
|
|
let(:article_tag) { ArticleTag.new }
|
2012-11-19 07:02:42 -05:00
|
|
|
|
|
|
|
describe ".policy_scope" do
|
|
|
|
it "returns an instantiated policy scope given a plain model class" do
|
|
|
|
Pundit.policy_scope(user, Post).should == :published
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns an instantiated policy scope given an active model class" do
|
|
|
|
Pundit.policy_scope(user, Comment).should == Comment
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns nil if the given policy scope can't be found" do
|
|
|
|
Pundit.policy_scope(user, Article).should be_nil
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
describe ".policy_scope!" do
|
|
|
|
it "returns an instantiated policy scope given a plain model class" do
|
|
|
|
Pundit.policy_scope!(user, Post).should == :published
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns an instantiated policy scope given an active model class" do
|
|
|
|
Pundit.policy_scope!(user, Comment).should == Comment
|
|
|
|
end
|
|
|
|
|
|
|
|
it "throws an exception if the given policy scope can't be found" do
|
|
|
|
expect { Pundit.policy_scope!(user, Article) }.to raise_error(Pundit::NotDefinedError)
|
|
|
|
end
|
2012-12-13 18:20:12 -05:00
|
|
|
|
|
|
|
it "throws an exception if the given policy scope can't be found" do
|
|
|
|
expect { Pundit.policy_scope!(user, ArticleTag) }.to raise_error(Pundit::NotDefinedError)
|
|
|
|
end
|
2012-11-19 07:02:42 -05:00
|
|
|
end
|
|
|
|
|
|
|
|
describe ".policy" do
|
|
|
|
it "returns an instantiated policy given a plain model instance" do
|
|
|
|
policy = Pundit.policy(user, post)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.post.should == post
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns an instantiated policy given an active model instance" do
|
|
|
|
policy = Pundit.policy(user, comment)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.comment.should == comment
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns an instantiated policy given a plain model class" do
|
|
|
|
policy = Pundit.policy(user, Post)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.post.should == Post
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns an instantiated policy given an active model class" do
|
|
|
|
policy = Pundit.policy(user, Comment)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.comment.should == Comment
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns nil if the given policy can't be found" do
|
|
|
|
Pundit.policy(user, article).should be_nil
|
|
|
|
Pundit.policy(user, Article).should be_nil
|
|
|
|
end
|
2012-12-13 18:20:12 -05:00
|
|
|
|
|
|
|
describe "with .policy_class set on the model" do
|
|
|
|
it "returns an instantiated policy given a plain model instance" do
|
|
|
|
policy = Pundit.policy(user, artificial_blog)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.blog.should == artificial_blog
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns an instantiated policy given a plain model class" do
|
|
|
|
policy = Pundit.policy(user, ArtificialBlog)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.blog.should == ArtificialBlog
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns an instantiated policy given a plain model instance providing an anonymous class" do
|
|
|
|
policy = Pundit.policy(user, article_tag)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.tag.should == article_tag
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns an instantiated policy given a plain model class providing an anonymous class" do
|
|
|
|
policy = Pundit.policy(user, ArticleTag)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.tag.should == ArticleTag
|
|
|
|
end
|
|
|
|
end
|
2012-11-19 07:02:42 -05:00
|
|
|
end
|
|
|
|
|
|
|
|
describe ".policy!" do
|
|
|
|
it "returns an instantiated policy given a plain model instance" do
|
|
|
|
policy = Pundit.policy!(user, post)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.post.should == post
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns an instantiated policy given an active model instance" do
|
|
|
|
policy = Pundit.policy!(user, comment)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.comment.should == comment
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns an instantiated policy given a plain model class" do
|
|
|
|
policy = Pundit.policy!(user, Post)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.post.should == Post
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns an instantiated policy given an active model class" do
|
|
|
|
policy = Pundit.policy!(user, Comment)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.comment.should == Comment
|
|
|
|
end
|
|
|
|
|
|
|
|
it "throws an exception if the given policy can't be found" do
|
|
|
|
expect { Pundit.policy!(user, article) }.to raise_error(Pundit::NotDefinedError)
|
|
|
|
expect { Pundit.policy!(user, Article) }.to raise_error(Pundit::NotDefinedError)
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
describe "#verify_authorized" do
|
|
|
|
it "does nothing when authorized" do
|
|
|
|
controller.authorize(post)
|
|
|
|
controller.verify_authorized
|
|
|
|
end
|
|
|
|
|
|
|
|
it "raises an exception when not authorized" do
|
|
|
|
expect { controller.verify_authorized }.to raise_error(Pundit::NotAuthorizedError)
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2013-04-18 01:05:24 -04:00
|
|
|
describe "#verify_policy_scoped" do
|
|
|
|
it "does nothing when policy_scope is used" do
|
|
|
|
controller.policy_scope(Post)
|
|
|
|
controller.verify_policy_scoped
|
|
|
|
end
|
|
|
|
|
|
|
|
it "raises an exception when policy_scope is not used" do
|
|
|
|
expect { controller.verify_policy_scoped }.to raise_error(Pundit::NotAuthorizedError)
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2012-11-19 07:02:42 -05:00
|
|
|
describe "#authorize" do
|
|
|
|
it "infers the policy name and authorized based on it" do
|
|
|
|
controller.authorize(post).should be_true
|
|
|
|
end
|
|
|
|
|
|
|
|
it "can be given a different permission to check" do
|
|
|
|
controller.authorize(post, :show?).should be_true
|
|
|
|
expect { controller.authorize(post, :destroy?) }.to raise_error(Pundit::NotAuthorizedError)
|
|
|
|
end
|
|
|
|
|
2012-12-13 18:20:12 -05:00
|
|
|
it "works with anonymous class policies" do
|
|
|
|
controller.authorize(article_tag, :show?).should be_true
|
|
|
|
expect { controller.authorize(article_tag, :destroy?) }.to raise_error(Pundit::NotAuthorizedError)
|
|
|
|
end
|
|
|
|
|
2012-11-19 07:02:42 -05:00
|
|
|
it "raises an error when the permission check fails" do
|
|
|
|
expect { controller.authorize(Post.new) }.to raise_error(Pundit::NotAuthorizedError)
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2013-07-12 23:42:34 -04:00
|
|
|
describe "#pundit_user" do
|
|
|
|
it 'returns the same thing as current_user' do
|
|
|
|
controller.pundit_user.should eq controller.current_user
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2012-11-19 07:02:42 -05:00
|
|
|
describe ".policy" do
|
|
|
|
it "returns an instantiated policy" do
|
|
|
|
policy = controller.policy(post)
|
|
|
|
policy.user.should == user
|
|
|
|
policy.post.should == post
|
|
|
|
end
|
|
|
|
|
|
|
|
it "throws an exception if the given policy can't be found" do
|
|
|
|
expect { controller.policy(article) }.to raise_error(Pundit::NotDefinedError)
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
describe ".policy_scope" do
|
|
|
|
it "returns an instantiated policy scope" do
|
|
|
|
controller.policy_scope(Post).should == :published
|
|
|
|
end
|
|
|
|
|
|
|
|
it "throws an exception if the given policy can't be found" do
|
|
|
|
expect { controller.policy_scope(Article) }.to raise_error(Pundit::NotDefinedError)
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|