【问题标题】:current_user defined in application.rb will not work in create actionapplication.rb 中定义的 current_user 在创建操作中不起作用
【发布时间】:2015-11-13 19:04:45
【问题描述】:

这是来自我的 application_controller.rb

 private

  def current_user
    return unless session[:user_id]
    @current_user ||= User.find_by_id(session[:user_id])
  end

  helper_method :current_user

这是来自我的 cmets_controller.rb 的创建方法

def create

    @user = User.find(params[:user_id]) 
    @user.comments.create(:user_id => @user.id, :commenter => current_user.login, :body => params[:comment][:body])
    respond_to do |format| 
         format.js 
         format.html { redirect_to(@user, :notice => 'Comment was successfully created.') } 
     end
  end

调用时会说:

nil:NilClass 的未定义方法 `login'

什么会阻止 current_user 被发现?

【问题讨论】:

  • 将其移至私有上方后尝试,私有方法只能在同一类中调用。
  • 在私有之上移动没有帮助
  • @RahulSingh 私有方法也可以在子类中调用。这是 Ruby 与其他语言的区别。

标签: ruby-on-rails ruby-on-rails-4.1


【解决方案1】:

current_user 已正确找到。如果没有,会有一个NoMethodError

在您的情况下,current_user 只是返回nil。然后您尝试在nil 上使用.login,这会导致您看到的错误:

undefined method `login' for nil:NilClass

因此,请尝试找出 current_user 在您的创建操作中返回 nil 的原因。可能是因为session[:user_id]没有设置或者找不到用户?


基于 cmets,问题在于 CSRF 保护。由于 CSRF 错误,会话未在 create 中初始化,因此 current_user 为空白。

CSRF 保护通常在ApplicationController 中启用:

class ApplicationController < ActionController::Base
  protect_from_forgery with: :exception
end

您应该找出 CSRF 保护起作用的原因并修复它。禁用它会使您的网站不安全。看看ruby security guide about CSRF

【讨论】:

  • 如何不设置session[:user_id]?发表评论的是登录用户
  • 尝试在create开头输出puts current_user.inspect,看看真的是nil,和session[:user_id]一样。如果不是nil,您确定错误来自create 操作中的行而不是其他行吗?
  • p current_user 在创建时不产生任何输出。我收到无法验证 CSRF 令牌的真实性这与它有什么关系吗?
  • 是的,看起来您的会话在 POST 上未正确初始化,因此 session[:user_id] 为空 --> 没有用户
  • '是的,看起来你的会话在 POST 上没有正确初始化' 有什么解决办法吗?但是我可以从该站点发送电子邮件吗?
猜你喜欢
  • 2014-02-28
  • 1970-01-01
  • 1970-01-01
  • 2013-09-22
  • 1970-01-01
  • 1970-01-01
  • 2011-05-17
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多