Унаследованные ресурсы и вложенность уровней CanCan 3
У меня проблема с вложением 3-х уровней моделей в CanCan в сочетании с Inherited Resources. Я читал, что мы должны вкладывать все до двух уровней, но я должен был положить все под account
модель, и теперь я попытался сделать это в CanCan:
load_and_authorize_resource :account
load_and_authorize_resource :project, :through => :account
load_and_authorize_resource :model, :through => :project
Это дает мне переменную @account со значением @project, как будто она перезаписывает это. @project - это то, что должно быть, и @model тоже. Это моя вина, CanCan's, Inherited Resources или просто CanCan не поддерживает 3 уровня вложенности? Кроме того, я делаю это в IR для ModelsController.
belongs_to :account, :finder => :find_by_name! do
belongs_to :project, :finder => :find_by_name!
end
Еще одна странная вещь, когда я удаляю часть load_and_
из определения CanCan. Это работает тогда, но я читал, что может быть опасно не использовать load
часть.
Могу ли я использовать только authorize_resource
или я должен сделать что-то с CanCan?
1 ответ
Насколько я могу судить, ваши разрешения были верны.
Разработчик CanCan Gem ryan написал, как это должно вести себя: https://github.com/ryanb/cancan/issues/127
Это означает, что ваш
load_and_authorize_resource :account
load_and_authorize_resource :project, :through => :account
load_and_authorize_resource :model, :through => :project
закончится в блоке, подобном следующему (здесь: создайте действие. Для других действий должны последним авторизоваться! и изменить @model):
@account = Account.find(params[:account_id])
authorize! :read, @account
@project = @account.projects.find(params[:project_id])
authorize! :read, @project
@model = @project.models.build
authorize! :new, @model
Я надеюсь, что этот ответ может помочь разработчикам, ищущим авторизацию для вложенного cancan:-) .
источник: https://github.com/ryanb/cancan/issues/127
ps: неправильное поведение для / account /1/projects/2/models/new:
load_and_authorize_resource :project
load_and_authorize_resource :model, :through => :project
Это своего рода проблема безопасности, потому что это будет делать
@project = Project.find(params[:project_id]) [...]
и не проверяет, разрешено ли текущему аккаунту читать связанный аккаунт "1". И он не проверяет, действительно ли проект "2" является проектом аккаунта "1".