0

Devise と Rails 4.0 を使用して、サインイン ページに別のフィールドを追加しようとしています。ユーザーは、ユーザー名、パスワード、および組織/ロケーション コードを提供する必要があります。ユーザーには多くの場所があり、ログインすると、この組織コードをセッションに保存する必要があります。

この時点で、ほとんどの作業が完了したと思います (これを行うためのより良い方法があれば教えてください) が、無効な場所コードが入力された場合に何が起こるかを処理する方法がわかりません。これが私がこれまでに持っているものです。

class SessionsController < Devise::SessionsController
  def create
    user = User.find_by_username(params["user"]["username"])
    org_code = params["user"]["check_org_code"].downcase
    user.locations.each do |location|
      if location.org_code == org_code
        super
        session[:location] = location
      else
        < return a warden.authenticate! fail? >
        super
      end
    end
  end
end
4

1 に答える 1

0

最初に throw(:warden) を使用してこれを解決しましたが、これは機能しますが、おそらく最善の解決策ではありません。その後、r00kによるカスタム デバイス戦略の例に出くわし、独自のバリエーションを実装しました。以下に両方のソリューションを含めました。

r00k-esque ソリューション NB いくつかのコードがありましたが、それは私にとってはうまくいかなかった r00k のソリューションです。r00k のソリューションがうまくいかない場合は、「fail!」との違いに注意してください。および「valid_password?」。

# config/initializers/local_override.rb

require 'devise/strategies/authenticatable'

module Devise
  module Strategies
    class LocalOverride < Authenticatable
      def valid?
        true
      end

      def authenticate!
        if params[:user]
          user = User.find_by_username(params["user"]["username"])
          if user.present?
            code = params["user"]["check_org_code"].downcase
            codes = user.locations.pluck(:org_code).map{ |code| code.downcase }
            check_code = code.in?(codes)
            check_password = user.valid_password?(params["user"]["password"])

            if check_code && check_password
              success!(user)
            else
              fail!(:invalid)
            end
          else
            fail!(:invalid)
          end
        else
          fail!(:invalid)
        end
      end
    end
  end
end

Warden::Strategies.add(:local_override, Devise::Strategies::LocalOverride)

# config/initializers/devise.rb
config.warden do |manager|
  manager.default_strategies(:scope => :user).unshift :local_override
end

初期ソリューション

class SessionsController < Devise::SessionsController
  def create
    user = User.find_by_username(params["user"]["username"])
    org_code = params["user"]["check_org_code"].downcase
    matching = false

    user.locations.each do |location|
      if location.org_code == org_code
        super
        session[:location] = location
        matching = true
        break
      end
    end

    if matching == false
      throw(:warden, :message => :invalid)
    end
  end
end
于 2013-11-12T19:37:51.517 に答える