我有一个设计用户(我在我的应用程序中称为提供程序),我正在尝试编写自定义身份验证方法,以防止提供程序删除彼此的帖子(在我的应用程序中称为过程)。现在我在程序控制器中有了correct_user方法。
def correct_user
@provider = @procedure.provider.find(params[:id])
redirect_to(provider_path(current_provider)) unless current_provider?(@provider)
结束
我在过滤之前使用以下内容调用它,也在我的过程控制器中调用它:
before_filter :correct_user, :except => [:index, :show]
我在尝试编辑程序时遇到以下错误,甚至是提供程序自己的程序:
NoMethodError (undefined method `provider' for nil:NilClass)
app/controllers/procedures_controller.rb:8:in `correct_user'
Parameters: {"id"=>"523"}
从这个错误的外观来看,correct_user方法是找到过程id而不是提供者id。我怎样才能解决这个问题?感谢
答案 0 :(得分:0)
错误消息告诉您:
在调用方法@procedure
时,您的变量correct_user
为nil。
答案 1 :(得分:0)
身份验证是为了确保用户是他所说的人。 Devise是一个授权库。它提供的唯一访问控制是您可以为未知用户限制操作。
授权正在制定关于谁可以做什么的规则。受欢迎的图书馆包括Pundit& CanCanCan。
即使没有lib,您也可以编写一个简单的授权规则:
class Provider < ActiveRecord::Base
class NotAuthorized < StandardError; end
end
class ApplicationController < ActionController::Base
rescue_from Provider::NotAuthorized, with: :deny_access
private
def deny_access
render 'some_view', status: 403
end
end
class ProceduresController < ApplicationController
before_action :find_procedure, only: [:show, :edit, :update, :destroy]
before_action :authorize_resource!, except: [:new, :index, :show]
# DELETE /procedures/:id
def destroy
# This line never gets run if the user is not authorized.
@procedure.destroy
end
private
def find_procedure
@procedure = Procedure.find(params[:id])
end
def authorize_resource!
unless current_provider == @procedure.provider
raise Provider::NotAuthorized and return false
end
end
end
请注意,在authorize_resource!
方法中,您将要授权的记录的用户ID与会话中的用户ID进行比较。
如果您使用了params中的id,那么您将自己置身于欺骗性攻击之中,用户通过在params中传递其他用户的id来伪装成其他人。
但是,我不建议您从头开始编写授权解决方案,除非您真的知道自己在做什么。