Cancan не загружает вложенные ресурсы, как я ожидаю

Cancan работает нормально, когда пользователь вошел в систему. Но когда пользователь является «гостем», я хотел бы, чтобы он мог видеть некоторые фотографии, но не те, где родительский пост Photo имеет установленный флаг ограничения employees_only.

Проблема в том, что если в массиве @photos есть какая-либо фотография, связанная с постом employee_only, Cancan выдаст CanCan::AccessDenied in PhotosController#index. Но разве load_and_authorize_resource :photo, :through => :event в контроллере не должно было удалить эти несанкционированные записи из @photos?

способность.rb

class Ability
  include CanCan::Ability

  def initialize(user)  
    user ||= User.new # guest user (not logged in)

    if user.role? :admin
      can :manage, :all
    elsif user.role? :moderator
      can :read, :all
      can :manage, Post
      can :manage, Event
    elsif user.role? :employee
      can :read, :all
      can :create, Post
      can :update, Post, :user_id => user.id
      can :destroy, Post, :user_id => user.id
      can :update, User, :id => user.id
      can :create, Photo
      can :update, Photo, :id => user.id
      can :destroy, Photo, :id => user.id
    else
      can :read, :all
      cannot :read, Post, :employee_only => true
      cannot :read, Photo, :post => { :employee_only => true } ## <- problem?
    end
  end
end

событие.rb:

class Event < ActiveRecord::Base
Event has_many :posts
Event has_many :photos, :through => :posts

пост.рб

class Post < ActiveRecord::Base
  belongs_to :user
  belongs_to :event
  has_many :photos, :dependent => :destroy

photos_controller:

class PhotosController < ApplicationController
  load_and_authorize_resource :event                       ## <- problem?
  load_and_authorize_resource :photo, :through => :event   ## <- problem?

  def index
    # @event = Event.find(params[:event_id])
    # @photos = @event.photos.all

    respond_to do |format|
      format.html # index.html.erb
      format.json { render json: @events }
    end
  end
  ...

user.rb # не уверен, что это необходимо для решения этой проблемы, но J.I.C.:

class User < ActiveRecord::Base
  attr_protected :roles_mask
  has_many :posts
  has_many :photos, :through => :posts
  ...

person Meltemi    schedule 30.08.2011    source источник
comment
‹сверчки› Cancan потерял популярность, и я не получил записку?   -  person Meltemi    schedule 31.08.2011


Ответы (1)


Во-первых, в вашем файле способностей удалите

cannot :read, Photo, :post => { :employee_only => true } ## <- problem?

Я не думаю, что вам это нужно, поскольку вы ограничиваете пост.

Затем в вашем контроллере измените

load_and_authorize_resource :event                       ## <- problem?
load_and_authorize_resource :photo, :through => :event   ## <- problem?

To

load_and_authorize_resource :post
load_and_authorize_resource :photo, :through => :post

Я считаю, что вы пытаетесь загрузить фотографии через сообщение, и, поскольку сообщение ограничено теми, у кого employee_only = false, вы неявно ограничиваете фотографии. Затем в вашем контроллере фотографий вам нужно загрузить пост, чтобы его можно было использовать для загрузки и авторизации фотографий. Что должно произойти в канкане (я думаю), так это внутреннее соединение между сообщениями и фотографиями, где posts.employee_only = false.

person Joshua Harris    schedule 21.07.2012