rails应用程序中的来宾用户功能,设备中存在设计+存储

时间:2013-11-11 06:49:09

标签: ruby-on-rails session devise

我希望用户能够使用我的应用程序的某些功能而无需创建帐户 - 非常标准。例如,我有一个列表制作功能,用户可以在其中创建列表并向其添加项目。我在我的控制器和视图中使用了current_user来做这种类型的事情,并且每当非用户尝试时,它可以预测会抛出各种错误。我知道Devise可以通过在会话中存储用户属性然后用cookie记住来解决这个问题,对吗?我的问题是:如何在会话中存储current_user属性?我已经搜索了关于这个和类似问题的文档,但是没有太多运气。如果已经被淘汰了(我确信它已经在某个地方),请随意指导我获得一个好的资源。这是我的用户模型:

class User < ActiveRecord::Base

  devise :database_authenticatable, :registerable,
         :recoverable, :rememberable, :trackable, :validatable
end

如果我能澄清我正在尝试做什么,请告诉我,并提前感谢!

2 个答案:

答案 0 :(得分:1)

我理解你的担忧。当许多依赖于它的功能时,错过current_user是不方便的。

第一步是在任何情况下创建current_user。

class ApplicationController

  def current_user
    super || User.new
  end

end

通过此设置,当Devise中没有current_user可用时,您将自动为该访问者创建一个新的User实例。

第二步,您现在可以像往常一样将current_user的信息存储到会话中。我不是会话的忠实粉丝,但是当你真的需要它时它仍然有用。

答案 1 :(得分:1)

经过多次搜索,我认为我找到了解决这个问题的好方法。我在github上关于guest_users的设计文档中找到了它。这是链接:https://github.com/plataformatec/devise/wiki/How-To:-Create-a-guest-user

以下是设计建议:

class ApplicationController < ActionController::Base

  protect_from_forgery

  # if user is logged in, return current_user, else return guest_user
  def current_or_guest_user
    if current_user
      if session[:guest_user_id]
        logging_in
        guest_user.destroy
        session[:guest_user_id] = nil
      end
      current_user
    else
      guest_user
    end
  end

  # find guest_user object associated with the current session,
  # creating one as needed
  def guest_user
    # Cache the value the first time it's gotten.
    @cached_guest_user ||= User.find(session[:guest_user_id] ||= create_guest_user.id)

  rescue ActiveRecord::RecordNotFound # if session[:guest_user_id] invalid
     session[:guest_user_id] = nil
     guest_user
  end

  private

  # called (once) when the user logs in, insert any code your application needs
  # to hand off from guest_user to current_user.
  def logging_in
    # For example:
    # guest_comments = guest_user.comments.all
    # guest_comments.each do |comment|
      # comment.user_id = current_user.id
      # comment.save!
    # end
  end

  def create_guest_user
    u = User.create(:name => "guest", :email => "guest_#{Time.now.to_i}#{rand(99)}@example.com")
    u.save!(:validate => false)
    session[:guest_user_id] = u.id
    u
  end

end

我认为这是一个很好的解决方案。我需要修改我的应用程序的某些部分,使用current_user和rework接受guest_user和current_user。