【问题标题】:Using a deleted scope with Devise authentication将已删除的范围与设计身份验证一起使用
【发布时间】:2013-04-04 20:57:15
【问题描述】:

我正在使用 Devise 处理 Rails 应用程序中的身份验证,并且正在使用 Permanent_records 软删除用户。我的 User 模型的默认范围是未删除的用户。如果用户删除(停用)他的帐户,我希望他能够通过登录重新激活他的帐户,类似于 Facebook 的做法。问题是,由于 Devise 不知道查找已删除的用户,因此找不到帐户。我考虑过覆盖会话#create 方法

 def create
    self.resource = warden.authenticate!(auth_options)
    set_flash_message(:notice, :signed_in) if is_navigational_format?
    sign_in(resource_name, resource)
    respond_with resource, :location => after_sign_in_path_for(resource)
  end

但由于这是由 Warden 处理的,看来我很不走运。我担心如果我开始挖掘得太深,我会开始破坏东西。

有什么想法吗?

谢谢!

【问题讨论】:

    标签: ruby-on-rails devise warden soft-delete


    【解决方案1】:

    你需要:

    1. 在 User 模型中覆盖 find_for_authentication 方法以允许查找任何用户 https://github.com/plataformatec/devise/blob/master/lib/devise/models/authenticatable.rb#L229

    2. 在您的模型中重新定义 after_database_authentication 方法以在此处删除已删除的标志 https://github.com/plataformatec/devise/blob/master/lib/devise/models/database_authenticatable.rb#L98

    这就是全部,我相信。无需触摸控制器操作。

    【讨论】:

    • 太棒了!因此,如果我要覆盖 find_for_authentication,我如何告诉它不要使用默认范围?他们的例子是 find_first_by_auth_conditions(tainted_conditions, :active => true),但我不想要 :deleted => true,我想要删除和未删除的记录,这样我就可以对删除的记录应用一些特殊的逻辑。
    • 更具体地说,如果我能做类似 user = super || 的事情,那就太棒了find_first_by_auth_conditions(tainted_conditions, :deleted_at => "IS NOT NULL") 但当然“IS NOT NULL”不是我可以传递给哈希的东西。如何找到已删除_at 存在的记录?
    • 你可以在这里写自己的finder(因为你知道你的适配器和字段)unscoped.where(tainted_conditions).first
    • 太棒了。先生,您是救生员。
    【解决方案2】:

    这适用于偏执狂宝石:

    class << self
      def find_for_authentication(conditions)
        User.unscoped do
          user = super(conditions)
          user.restore!(recursive: true) if user.deleted?
          user
        end
      end
    end
    

    【讨论】:

      猜你喜欢
      • 2018-08-12
      • 2011-07-16
      • 1970-01-01
      • 2013-02-10
      • 2020-03-12
      • 2018-05-15
      • 2011-11-25
      • 2017-05-10
      • 1970-01-01
      相关资源
      最近更新 更多