はじめに
現状としては、deviseとomniauthにて、Google認証のみのログイン機能を作成しています。ポートフォリオとして作成しておりますので、見てくださる方が確認しやすいようにゲストログインの機能を準備していきたいと思います。deviseの追加やGoogle認証については、私が準備した以下の記事をご覧ください。
手順
1 コントローラーの準備
まずは、ルーティングの設定をしていきたいと思います。
devise_scope :user do
post 'users/guest_sign_in', to: 'users/sessions#guest_sign_in'
end
devise_scopeはdeviseの標準ルート以外である、独自機能をスコープ内で定義するための記述です。sessionsコントローラにguest_sign_inアクションを追加しています。このアクションの記述は後ほど行います。
スコープとは(Chatgptより)
例えば、あなたが大きなスポーツ施設にいるとします。この施設には「野球エリア」と「サッカーエリア」があります。
野球エリアでは、野球のルールだけが有効です。サッカーエリアでは、サッカーのルールだけが有効です。
つまり、エリアごとにルールが決まっているのです。この「エリア」をプログラムの世界では 「スコープ」 と呼びます。
post 'users/guest_sign_in'によりguest_sign_inアクションにゲストデータのリクエストが送られます。
2 コントローラについて
以下はコントローラに記述するコードです。
class Users::SessionsController < Devise::SessionsController
def guest_sign_in
user = User.find_or_create_by(email: 'guest@example.com') do |user|
user.password = SecureRandom.urlsafe_base64
user.name = 'ゲストユーザー'
user.profile = '未設定'
user.muscle_training_history = 0
user.uid = nil # Google認証と混ざらないようにする
user.provider = nil
end
sign_in user
redirect_to edit_user_registration_path, success: 'ゲストユーザーとしてログインしました'
end
end
先ほどのリクエストを受けて、これらの処理が働きます。
まずはguest_sign_inメソッドを作成し、User.find_or_create_byにて、usersテーブルにemailが「guest@example.com」がないか探します。もし存在すればそれらのデータを取得し、見つからなければ新規作成されます。
また、user =の部分のuserにはユーザーオブジェクトが入ります。
オブジェクトとは
わかりやすく説明すると、クラスは「設計図」で、同じ設計図からは何軒でも家(オブジェクト)を建てられます。つまりここでは、1つの人(user)を作成しています。
それらのオブジェクトに必要な情報を入れていきます。もしユーザーオブジェクトが新たに作成された場合は、それを一時的に|user|として保管します。それにより、user.passwordやuser.nameを記述することで、オブジェクトにデータを追加していけます。パスワードは何でも良いので、ランダムに作成させています。
私はGoogle認証をしているので、uidやproviderにデータが入っていると、Google認証と混同してはいけないと思い、nilにしています。
sign_in user
redirect_to edit_user_registration_path, success: 'ゲストユーザーとしてログインしました'
上記の部分では、先ほどuser =の変数をDeviseのsign_inメソッドを活用して、ログイン状態にしています。
その後にredirect_toによりユーザーの編集画面にリンクするように設定しています。
3 ビューの準備
<%= link_to "ゲストログイン", users_guest_sign_in_path, method: :post %>
上記のコードをゲストログインの配置したいところに、記述してください。それをクリックすることでゲストログインが可能になります。注意点としては、link_toは基本的にgetメソッドとして機能するため、明示的にmethod: :postを記述しています。
さいごに
これでゲストログイン機能を作成することができました。比較的簡単にできましたが、コードの1つ1つを理解することが大切だなと改めて感じる機能でした。私自身が初心者のため、間違えたことを記載していたら、コメントなどでご教示くださいますようお願いします。
最後まで閲覧いただきありがとうございました。