Railsを使ったToDoリストの作成(8.ログイン機能の実装)


概要

本記事は、初学者がRailsを使ってToDoリストを作成する過程を記したものです。
私と同じく初学者の方で、Railsのアウトプット段階でつまづいている方に向けて基礎の基礎を押さえた解説をしております。
抜け漏れや説明不足など多々あるとは思いますが、読んでくださった方にとって少しでも役に立つ記事であれば幸いです。

環境

  • Homebrew: 2.5.10 -> MacOSのパッケージ管理ツール
  • ruby: 2.6.5p114 -> Ruby
  • Rails: 6.0.3.4 -> Rails
  • node: 14.3.0 -> Node.js
  • yarn: 1.22.10 -> JSのパッケージ管理ツール
  • Bundler: 2.1.4 -> gemのバージョン管理ツール
iTerm
$ brew -v => Homebrew 2.5.10
$ ruby -v => ruby 2.6.5p114
$ rails -v => Rails 6.0.3.4
$ npm version => node: '14.3.0'
$ yarn -v => 1.22.10
$ Bundler -v => Bundler version 2.1.4

第8章 Deviseを使ったユーザ認証機能の実装

第8章では、Railsのライブラリであるdeviseを使ってユーザ認証機能を実装していきます。

1 deviseの設定を行う

まず、Gemfileにてdeviseを読み込みます。

Gemfile
gem 'devise'

🙋‍♂️diviseというライブラリを読み込んでください
->Gemfileに追記した時は必ずiTermにて$bundle installを行う

$bundle installができたらiTermにて以下のコマンドを入力しジェネレーターを実行します。

iTerm
$ rails generate devise:install
=>create  config/initializers/devise.rb
  create  config/locales/devise.en.yml

🙋‍♂️ジェネレーターをインストールしてください
💻configのinitializersにdevise.rbというファイルを作成しました
💻configのlocalesにdevise.en.ymlというファイルを作成しました

また、コンソールには上記2つのファイルを作成した旨に加え、以下4つの設定が必要である旨も表示されるため、指示に従い設定していきます。

config/environments/development.rbに以下のようなメール設定に関する情報を入力します。

development.rb
config.action_mailer.default_url_options = { host: 'localhost', port: 3000 }

config/routes.rbにroot_urlを設定します。

routes.rb
Rails.application.routes.draw do
  root to: "home#index"
end

app/views/layouts/application.html.erbにフラッシュメッセージが表示されるように設定します。

application.html.erb
<p class="notice"><%= notice %></p>
<p class="alert"><%= alert %></p>

④ログイン画面のHTMLテンプレートファイルを作成します。

iTerm
$ rails g devise:views

上記の設定が完了したら、最後にUserを管理するモデルを作成します。

iTerm
$ rails generate devise User
=>create db/migrate/20201114092712_devise_create_users.rb
  create app/models/user.rb

🙋‍♂️Userを管理できるモデルを作成してください
💻migrationファイル(データを作るためのテーブルを作成する場所)を作成しました
💻userモデルを作成しました
->migrationファイルを作成した場合は必ず$rails db:migrateでmigrationファイルを読み込む

※エラーが起こってしまう場合は定期的に$rails sでサーバを立ち上げ直しましょう。

ここまできたら以下のようなページ等が作成できているはずです。

2 ビュー

deviseの設定が終わったらビューの設定をしていきます。
deviseは初期設定がerbなので、まずはhamlに書き換えます。

既存のerbファイルをhamlに置き換えるためにはターミナルにて以下のコマンドを実行します。

iterm
$ bundle exec rake haml:replace_erbs

また、デフォルトではエラーメッセージなどが英語のままなので日本語化します。
日本語化するためにはconfig/localsdevise.ja.ymlファイルを作り、ルールを記述します。

3 ログイン状態によって表示を変更する

まずは、ログアウト機能を実装しましょう。

app/views/layouts/application.html.haml
= link_to 'Log out', destroy_user_session_path, data: { method: 'delete' }

rails infoで確認すると、userのログイン状況を削除するためにはdestroy_user_session_pathを指定することがわかるので指定します。
link_toはデフォルトはGETリクエストのため、data: { method: 'delete' }を指定します。

では、次にログイン状態によって表示を変更できるよう条件分けしていきます。

app/views/layouts/application.html.haml
- if user_signed_in?
  .dropdown
    = image_tag 'default-avatar.png', class: 'header_avatar dropbtn'
    .dropdown-content
      %a{:href => "#"} Profile
      = link_to 'Log out', destroy_user_session_path, data: { method: 'delete' }
- else
  = link_to new_user_session_path, class: 'header_loginBtn' do
    = image_tag 'log-in.png'

ポイントは2つあります。

  • if user_signed_in?でログイン時の状態を表示します。user_signed_in?メソッドがdeviseでは用意されており、ユーザがログインしているか否かを判断してくれます。
  • ログインしていないときはnew_user_session_pathでログインページに遷移するようにします。

4 一部機能をログイン時にしか操作できないようにする

投稿機能や編集機能や削除機能をログイン時のみ使えるようにしていきます。
コントローラに以下のように記述します。

app/controllers/boards_controller.rb
before_action :authenticate_user!, only: [:new, :create, :edit, :update, :destroy]

authenticate_user!はdeviseが用意してくれているメソッドでログインしているユーザのみ操作を許可し、ログインしていない場合はログイン画面に遷移するようにしてくれます。
beeforeアクションを使うことで各アクションの前にログイン状況を判断できるようにします。
しかし、Read機能はログインしていなくてもできるようにしたいので、onlyオプションで対象を絞っています。