初めに
こんにちは、GMOアドマーケティングのryoutakoです。普段はRuby on Railsを使った開発やプロダクトの脆弱性診断などセキュリティ関連の仕事をしています。
今回のブログはRuby on Railsのdevise Gemについての内容です。
経緯
みなさんはRuby on RailsのGemをオーバーライドして実装したことはあるでしょうか?さまざまな理由で独自の機能を追加したくなり、オーバーライドした経験のある方も多いと思います。私も最近開発をしていてdeviseのDevise::SessionsControllerをオーバーライドする機会がありました。そしてその際にdeviseのコード(特にnewメソッド)を読み込んだのでその内容を本ブログで共有します。
今後devise Gemのオーバーライドをする方のお役に立てれば幸いです!
deviseとは
deviseはRuby on Railsアプリケーションに認証機能を追加するためのGemです。ユーザーのサインアップ、ログイン、ログアウト、パスワードのリセットなどの一般的な認証機能を提供します。devise Gemのソースコード
newメソッド解説
今回はnewメソッドについて解説していきます。v4.9.0現在の実装↓
1 2 3 4 5 6 |
def new self.resource = resource_class.new(sign_in_params) clean_up_passwords(resource) yield resource if block_given? respond_with(resource, serialize_options(resource)) end |
概要
Devise::SessionsControllerのnewメソッドでは新しいセッションを作成するためのログインフォームの表示を行います。1, self.resource = resource_class.new(sign_in_params)
resource_class(deviseで定義したユーザーのクラス)の新しいインスタンスを作成しself.resourceに格納します。sign_in_paramsにはログイン画面で入力したメールアドレスやパスワードの情報が入っており、認証失敗で再度ログイン画面に飛ばされた時のために一度入力した情報を含むようになっています。2, clean_up_passwords(resource)
resourceに含まれるパスワード関連の情報を空にします。これにより既存のパスワード関連の情報が表示されないようになります。3, yield resource if block_given?
ブロックが渡された際にそのブロックパラメータにresourceを代入します。これにより(主に開発者が)ブロックを渡して追加の処理を行うことができるようになります。RegistrationsControllerのクラスなどで使用されています。4, respond_with(resource, serialize_options(resource))
ログイン画面のテンプレートを表示します。serialize_options(resource)にはそのユーザの認証に何が必要かの情報(メアドやパスワード)が入っており、それらをまとめてログインフォームを作ってくれます。オーバーライドの方法
deviseの初期設定として、アカウントとなるクラスのコントローラの作成を行なった時に、以下のような中身になったと思います。オーバーライドする場合はコメントを取り除いて行います。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 |
class Users::SessionsController < Devise::SessionsController # before_action :configure_sign_in_params, only: [:create] # GET /resource/sign_in # def new # super # end # POST /resource/sign_in # def create # super # end # DELETE /resource/sign_out # def destroy # super # end # protected # If you have extra params to permit, append them to the sanitizer. # def configure_sign_in_params # devise_parameter_sanitizer.permit(:sign_in, keys: [:attribute]) # end end |
newメソッドをオーバーライドする場合
基本的には↓のようにsuperを使用しつつオーバーライドすることをお勧めします。(理由は後述)
1 2 3 4 5 6 |
# GET /resource/sign_in def new # 追加したい前処理 super # 追加したい後処理 end |
1 2 3 4 5 6 7 8 9 10 |
# GET /resource/sign_in def new # 追加したい処理 self.resource = resource_class.new(sign_in_params) clean_up_passwords(resource) # 追加したい処理 yield resource if block_given? respond_with(resource, serialize_options(resource)) # 追加したい処理 end |
最後に
今回はdevise Gemについて書いてみましたがいかがだったでしょうか?なかなかGemのソースコードを読む機会はなく今回でかなり勉強になったので、もし別のソースコードを読む機会があったらまた書いてみたいと思います。
ここまで読んでいただきありがとうございます!!
Ruby on Railsを使った開発、プロダクトの脆弱性診断などをやってます
オレンジ色と犬と猫と食べることと歌うこととピアノが好きです。