I'm using CanCan 1.6.1 in a Rails 3.2 application. I use authorize_resource in my controllers to limit what users can :read, :create, :update: and :delete.
In my V2Posts controller, the authorize_resource call isn't working for my :show action.
In my abilities file, I'm trying to limit the user to only read their own posts. There's no error, but unfortunately, they're able to view other users posts.
class V2PostsController < ApplicationController
layout 'panel_layout', only: :show
before_filter :redirect_if_existing, only: [:new, :create]
authorize_resource
def show
@v2_post = V2Post.find(params[:id], include: :user_updates)
@organization = @v2_post.organization
respond_to do |format|
format.html
format.js
end
end
...
end
ability.rb:
class Ability
include CanCan::Ability
@user = nil
def initialize(user)
alias_action :taco,
:sandwich,
to: :read
@user = user
if user.is_in_role?(:admin)
can :manage, :all
else
default_rules
user.roles_list.each do |role|
meth = :"#{role}_rules"
send(meth) if respond_to? meth
end
end
end
def default_rules
cannot [:read, :create, :update, :destroy], :all
...
end
def pro_user_rules
can :read, V2Post, proid: @user.id
end
...
end
models/v2_post.rb:
class V2Post < ActiveRecord::Base
attr_accessible :proid, :user_updates_attributes, :organization
belongs_to :user, :foreign_key => "proid"
has_many :user_updates, as: :pro_post, dependent: :destroy
accepts_nested_attributes_for :user_updates
end
load_and_authorize_resource works for keeping the users from viewing other users' posts. But, it loads the resource for me and also adds additional database calls to other actions. Shouldn't authorize_resource work for my case? I've explicitly defined @v2_posts in the show action (loading the resource myself). Why isn't it getting passed to the authorize_resource call?
- I want to avoid requiring extra calls to the database
- I don't want to automatically load the resource for custom actions
- I want to authorize every CRUD action.
Given that, which of load_and_authorize_resource and authorize_resource works better, and what are the benefits/drawbacks of each? I've read the documentation, I'm confused.