現在作成中のアプリでは、UserとShop、二つのモデルが必要になってきます。
deviseを用いて二つのモデルのユーザー管理機能を実装しました。
環境
Ruby 2.6.5
rails 6.0.3.4
devise 4.7.3
目次
1.deviseのインストール
2.configの変更
3.モデルの作成
4.コントローラーの作成
5.ビューの作成
6.ルーティングの設定
7.ストロングパラメーターの設定
1. deviseのインストール
# [--- 中略 ---]#
gem 'devise'
bundle install
rails g devise:install
ここまでは一つのモデルを管理する時と同じです。
2. configの変更
# [--- 中略 ---]#
# ==> Scopes configuration
# Turn scoped views on. Before rendering "sessions/new", it will first check for
# "users/sessions/new". It's turned off by default because it's slower if you
# are using only default views.
# config.scoped_views = false
# [--- 中略 ---]#
の
# config.scoped_views = false
を
config.scoped_views = true # コメントアウトは外します
に変更。
deviseをインストールすると、config/initializer/devise.rbファイルが作成されます。
デフォルトの設定ではdeviseによって作成されたviewファイルは変更できません。
そのため、config.scoped_views = falseをtrueに変えることでビューファイルの変更を可能にします。
3. モデルの作成
rails g model user
rails g model shop
それぞれのモデルを作成します。
4. コントローラーの作成
rails g controllers users
rails g controllers shops
それぞれのコントローラーを作成します。
create app/controllers/users/confirmations_controller.rb
create app/controllers/users/passwords_controller.rb
create app/controllers/users/registrations_controller.rb
create app/controllers/users/sessions_controller.rb
create app/controllers/users/unlocks_controller.rb
create app/controllers/users/omniauth_callbacks_controller.rb
上記のように各機能ごとにコントローラーが作成されればOKです。
5. ビューの作成
rails g devise:views users
rails g devise:views shops
それぞれのビューを作成します。
6. ルーティングの設定
devise_for :users
devise_for :shops
# [--- 中略 ---]#
を
devise_for :users, controllers: {
sessions: 'users/sessions',
passwords: 'users/passwords',
registrations: 'users/registrations'
}
devise_for :shops, controllers: {
sessions: ‘shops/sessions',
passwords: ‘shops/passwords',
registrations: ‘shops/registrations'
}
# [--- 中略 ---]#
に変更。
元々の設定だと、users,shops共にdeviseコントローラーを通ってしまいます。先ほど作成したそれぞれのコントローラーを通るために、上記のように書き換えましょう。
7. ストロングパラメーターの設定
controllers/users/parameter_sanitizer.rb
controllers/shops/parameter_sanitizer.rb
の二つのファイルを新たに作成します。
(lib配下に置いたほうがいいかとは思ったのですが、上手くいかなかったので今回はそれぞれのコントローラーの配下に置きました。よりいい書き方があればご指摘いただきたいです。)
class Users::ParameterSanitizer < Devise::ParameterSanitizer
def initialize(*)
super
permit(:sign_up, keys: [:nickname,:first_name, :last_name, :first_kana, :last_kana, :birthday, :gender_id] )
end
end
class Shops::ParameterSanitizer < Devise::ParameterSanitizer
def initialize (*)
super
permit(:sign_up, keys: [:shop_name,:administrator, :postal, :prefecture_id, :address, :building, :nearest_station, :genre_id])
end
end
class ApplicationController < ActionController::Base
protected
def devise_parameter_sanitizer
if resource_class == User
Users::ParameterSanitizer.new(User, :user, params)
elsif resource_class == Shop
Shops::ParameterSanitizer.new(Shop, :shop, params)
else
super
end
end
end
デフォルトの設定では、パラメーターとしてemailとパスワードしか受け取ることができません。
今回は他の項目も追加しているため、ストロングパラメーターの設定をする必要があります。
一つのモデルだけ管理する場合は、devise_parameter_sanitizerメソッドをapplication.controller内に記述することで設定できましたが、今回は二つのモデルを使用しています。
そのため、Devise::ParameterSanitizerクラスを継承したUsers::ParameterSanitizerクラスと、Shops::ParameterSanitizerクラスを作成します。
(ちなみに私は「s」を抜かしてUser::ParameterSanitizerと記述してしまっていたために、しばらくハマってしましました。公式のリポジトリに書いてあるんだもん。。。コントローラーの名称に対応するみたいですね。)
間違っている点などあればご指摘お願いいたします。
参考URL
https://qiita.com/Yama-to/items/54ab4ce08e126ef7dade
https://github.com/heartcombo/devise#strong-parameters