概要

Railsのユーザ認証にDeviseを使っているという人は多いと思います。

私もDeviseを利用しているのですが、ログインの処理を少し変更したいなど、カスタマイズをしようとするとかなり面倒です。

今回は、Deviseのルーティングやカスタマイズをする際に関係する「スコープ」について調べたことをまとめていきます。

環境

  • Rails 5.1
  • Devise 4.4

スコープについて

例えば、RailsでUserというDeviseでユーザ管理をするモデルがあったとします。

このような場合、ユーザがログインしているかどうかは、user_signed_in?で確認します。

このuserの部分がスコープの部分です。

なぜスコープがあるのかというと、Deviseで複数のモデルを扱うことができるようにするためです。

ここでは、Userというモデルを用意しましたが、さらに管理者ユーザを管理するAdminUserというモデルを用意したとします。

このような場合には、管理者ユーザがログインしているのかどうかは、admin_user_signd_in?で確認します。

ユーザがログインしているかどうかを例にしましたが、そのほかのパスの生成メソッドの名前にもスコープが使われています。

そのため、Userモデルの登録をするためのパスを生成するのはnew_user_registration_path、AdminUserモデルの登録をするためのパスを生成するのは、new_admin_user_registration_pathとなります。

このスコープについて理解していないと、他のDeviseの使い方を説明した記事を参考にしてモデル名だけを変えた際に、うまくできないとなってしまいます。

ルーティング

このスコープについて知ってからroutes.rbを見てみましょう。

devise_for :users
devise_for :admin_users

devise_forでは、devise内のコントローラで処理をする際に、スコープを設定するという処理をしています。

そのため、例えばrails generate devise:controllers usersのようにして、UserモデルためのDeviseのコントローラを継承したコントローラを作成し、新たにアクションを追加した場合は次のようにして、スコープを経由するようにする必要があります。

devise_scope :user do
  get 'users/:id', to: 'users/registrations#other_show'
end

ここでは、idを指定して他のユーザの情報を見ることができるように、other_showアクションを追加し、そのアクションへのパスを記述しています。

スコープは、devise_scope :userのようにして追加しています。

これで、users/:idへのアクセス時には、userというスコープがコントローラに渡されて処理されます。

まとめ

Deviseでスコープは重要な考え方です。

実際に、devise_scopeを使わないでルーティングを追加しようとしたら、エラーが発生してうまくいきません。

Deviseを使うということは、簡単にユーザ認証などを行うことができますが、カスタマイズをしようとする際にDeviseのことを知らなくてはいけないということです。

この事を念頭に入れてDeviseを使っていきましょう。