Ruby on rails CanCan授权问题-作者编辑帖子
我正在开发Rails应用程序,使用CanCan进行授权。该应用程序具有db models User和PositionGameStat。PositionGameStat有一个用户id的外键。PositionGameStat的索引页显示了用户提交的统计信息列表,每个列表都有一个编辑按钮。当前易受注入攻击(…/position\u game\u stats/130/edit) 我希望用户只能编辑等于当前用户的position_game_stat条目 换句话说,如果有人试图插入url…/position\u game\u stats/129/edit,但他们没有输入这些统计信息,那么CanCan将拒绝访问这些信息 下面是我的代码 我的代码: app/controllers/position\u game\u stats\u controller.rbRuby on rails CanCan授权问题-作者编辑帖子,ruby-on-rails,devise,authorization,cancan,Ruby On Rails,Devise,Authorization,Cancan,我正在开发Rails应用程序,使用CanCan进行授权。该应用程序具有db models User和PositionGameStat。PositionGameStat有一个用户id的外键。PositionGameStat的索引页显示了用户提交的统计信息列表,每个列表都有一个编辑按钮。当前易受注入攻击(…/position\u game\u stats/130/edit) 我希望用户只能编辑等于当前用户的position_game_stat条目 换句话说,如果有人试图插入url…/position
class PositionGameStatsController < ApplicationController
before_filter :authenticate_user!
...
def edit
authorize! :manage, @position_game_stat
@position_game_stat = PositionGameStat.find(params[:id])
end
...
end
class PositionGameStatsController < ApplicationController
before_filter :authenticate_user!
load_and_authorize_resource
...
def edit
authorize! :manage, PositionGameStat
@position_game_stat = PositionGameStat.find(params[:id])
end
...
end
任何建议都将不胜感激
更新:
根据Billy Chan的建议,似乎至少与以下代码更接近:
才能
控制器
class PositionGameStatsController < ApplicationController
before_filter :authenticate_user!
...
def edit
authorize! :manage, PositionGameStat
@position_game_stat = PositionGameStat.find(params[:id])
end
...
end
类位置GameStatsController
这让我更接近了,因为它并没有拒绝访问该页面,但它仍然容易被注入。例如/position\u game\u stats/137/edit仍然可以访问,即使它是由不同的用户创建的
有什么建议吗?以您的能力。rb您需要指定如何应用授权规则:
can :manage, PositionGameStat, PositionGameStat.find_all_by_user_id(user.id) do |position_game_stat|
position_game_stat.new_record? or position_game_stat.user.id == user.id
end
然后,您可以在控制器中通过以下方式应用授权:
load_and_authorize_resource
注意:加载和授权资源实际执行的操作类似于@position\u game\u stat=PositionGameStat.find(params[:id])
。如果不希望出现这种行为,可以像下面这样手动执行授权:
@position_game_stat = PositionGameStat.accessible_by(current_ability).find(params[:id])
最后,有关更多详细信息,请参阅CanCan文档的这一部分:
完成了
更新
好吧,我明白问题所在了。这条线错了
authorize! :manage, @position_game_stat
您仅授权此特定实例。这是错误的。应该是
authorize! :manage, PositionGameStat
最终解决办法:
PositionGameStatsController.rb
class PositionGameStatsController < ApplicationController
before_filter :authenticate_user!
...
def edit
authorize! :manage, @position_game_stat
@position_game_stat = PositionGameStat.find(params[:id])
end
...
end
class PositionGameStatsController < ApplicationController
before_filter :authenticate_user!
load_and_authorize_resource
...
def edit
authorize! :manage, PositionGameStat
@position_game_stat = PositionGameStat.find(params[:id])
end
...
end
谢谢Billy Chan和Steakchaser的建议,这足够让我走了。无论出于何种原因,当前用户不能在Ability.rb中工作。在为其分配值之前,您为什么要授权
@position\u game\u stat
?你到底遇到了什么问题?我遇到的问题是授权正在阻止用户编辑position\u game\u stat。我让它为“user”工作,因此你无法向参数中注入不同的用户值,但现在我正在使用外键,在使用position_game_stat模型时遇到问题。得到错误未定义的方法“include”,原因是“能否将load_和_authorize_资源放在控制器定义的顶部;在任何动作之前?我想我对“@position\u game\u stat”的加载语句是错误的。取下它或将其设置为标准的@position\u game\u stat=PositionGameStat.find(params[:id])。当我的position\u game\u stat\u控制器顶部有load\u和\u authorize\u资源时,在加载def edit偶数下的代码之前会发生错误。我现在正在考虑这个问题,并尝试一些选项。是的,我尝试了许多不同的选项,但我一直遇到“加载”和“授权”资源的问题。不幸的是,这对我不起作用,CanCan仍然拒绝访问。@lando2319,您是否准备好了当前用户
方法?不管是Desive还是你自己的。事实上我刚刚注意到它仍然容易注射。例如/position\u game\u stat/137/edit即使来自不同的用户也可以访问。我会继续努力的。
class PositionGameStatsController < ApplicationController
before_filter :authenticate_user!
load_and_authorize_resource
...
def edit
authorize! :manage, PositionGameStat
@position_game_stat = PositionGameStat.find(params[:id])
end
...
end
class Ability
include CanCan::Ability
def initialize(user)
can :show, User, :id => user.id
can :manage, PositionGameStat do |t|
t.user.id == user.id
end
end
end