Webとデザインのあれこれ

プログラミングとUIデザインの学習記録です。

deviseの導入について

deviseについて

deviseはユーザー認証用のgemです。こちらを利用して、ログイン・ログアウト機能やアカウントの登録機能をBookアプリに実装します!

devise利用の手順

導入の手順は意外とシンプルです。

  1. Gemfileに追加
  2. generatorを実行
  3. デフォルトURLの設定
  4. Userモデルのセットアップ
  5. テンプレート編集
  6. Controller編集

1. Gemfileに追加

# Gemfile
gem 'devise'

この後、bundle installを実行します。

2. generatorを実行

rails generate devise:installでインストールは完了。

3. デフォルトURLの設定

デフォルトURLのセットアップは、config/environments/development.rbに以下を追加。

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

4. Userモデルのセットアップ

ユーザー機能を実装するので、以下のコマンドのMODELの部分をUserに置き換えて実行します。モデル名はお好みで変更しましょう。

$ rails generate devise MODEL

以下のコマンドを忘れずに!

$ rails db:migrate

5. テンプレートの編集

成功した場合に表示されるnoticeと失敗した場合に表示されるalertを埋め込みます。

# app/views/layouts/application.html.erb

<% if notice %>
  <p class="alert alert-success"><%= notice %></p>
<% end %>

<% if alert %>
  <p class="alert alert-danger"><%= alert %></p>
<% end %>

また、ログインのリンクなども追加します。

# app/views/layouts/application.html.erb
<p class="navbar-text pull-right">
  <% if user_signed_in? %>
    Logged in as <strong><%= current_user.email %></strong>.
    <%= link_to 'Edit profile', edit_user_registration_path, class: 'navbar-link' %> |
    <%= link_to "Logout", destroy_user_session_path, method: :delete, class: 'navbar-link'  %>
  <% else %>
    <%= link_to "Sign up", new_user_registration_path, class: 'navbar-link'  %> |
    <%= link_to "Login", new_user_session_path, class: 'navbar-link'  %>
  <% end %>
</p>

こちらのテンプレートの内容はRails Girls Guideを参考にしております。 リンク先の名称や配置などはお好みで変更してください!

6. Controllerの編集

deviseでは、Controllerやviews内で複数のヘルパーを利用することが可能です。

ログインしていない場合、本の登録内容が確認できないように以下の記述をコントローラーに追加します。

# app/controllers/application_controller.rb
before_action :authenticate_user!

以上がデフォルトの利用手順となります。

言語化について

deviseで実装したログイン画面を日本語化したい場合におすすめのgemがあります。 それがこちら。

github.com

利用方法は、Gemfileに追加してbundle install実行。

gem 'devise-i18n'

基本はこれだけでOKです!(この記事はi18nの利用を前提としています。)

カスタマイズ方法

公式にも記載があるのですが、deviseではviewsやControllerを追加したり変更したりしてカスタマイズが可能です。 また、DBにカラムを追加することももちろん可能です。

例えば、UserモデルのControllerを追加したい場合は、以下コマンドを実行します。

$ rails g devise:controllers users

そうすると、app/controllers/users内にControllerが作成されます。

f:id:b_leiu:20190512194557p:plain

そして、対応するルーティングの設定を下記のようにconfig/routes.rbで設定します。

devise_for :users, :controllers => {
 :registrations => 'users/registrations',
 :sessions => 'users/sessions'
}

上記は、registrations_controller.rbとsessions_controller.rbのルーティングを記述しています。

同様にviewsも以下のコマンドで生成できます。

$ rails generate devise:views users

追記(2019/05/17)

カスタマイズしたviewsの翻訳について

以下のコマンドを実行すると、devise-i18nのviewsファイルをコピーしてくれるため、その内容を各自で修正することも可能です。

$ rails g devise:i18n:views 

注意点として、こちらのコマンドを実行すると将来的にviewsの内容が変更されたり、アップデートされた場合もその分が反映されないというリスクがあります。

デフォルトのdevise-i18nのviewsを使用するのが無難かと思います。


Strong Parametersについて補足

deviseでユーザーの認証機能を実装する際に、nameなどの新カラムをDBに追加したい場合があるかと思います。

ところがrails g migration AddNameToUsersを実行しようとすると、カラムを追加できない(エラーが発生する)場合があります。

理由はStrong Parametersというセキュリティ機能があるからです。

Strong ParametersとはDBに登録できるパラメーターに制限をかける仕組みのことです。

ブラウザがHTMLのソースを書き換える機能を備えていることから、マスアサインメント脆弱性というセキュリティホールができる可能性を孕んでおり、この対策としてRails 4.0で導入された機能です。

では新しいカラムを追加したい場合どうすればいいのでしょうか?

公式に書かれていますね! f:id:b_leiu:20190517123629p:plain

フィルターを記述してあげればいいのですね。一件落着です。

メール認証機能の実装

ユーザーの新規登録が完了したら、メールアドレスに確認メールが送られる機能を実装しましょう。

  1. Userモデルにconfirmableを追加
  2. confirmableをDBに追加するためコマンドを実行
  3. マイグレーションファイル修正
  4. letter_openerの利用

1. Userモデルにconfirmableを追加

app/models/user.rb:confirmableを追加します。

f:id:b_leiu:20190512202335p:plain

2. confirmableをDBに追加するためコマンドを実行

$ rails g migration add_confirmable_to_devise

3.マイグレーションファイル修正

生成されたdb/migrate内のマイグレーションファイルに以下を追加して保存、rake db:migrateを実行。

class AddConfirmableToDevise < ActiveRecord::Migration[5.1]
  # Note: You can't use change, as User.update_all will fail in the down migration
  def up
    add_column :users, :confirmation_token, :string
    add_column :users, :confirmed_at, :datetime
    add_column :users, :confirmation_sent_at, :datetime
    # add_column :users, :unconfirmed_email, :string # Only if using reconfirmable
    add_index :users, :confirmation_token, unique: true
    # User.reset_column_information # Need for some types of updates, but not for update_all.
    # To avoid a short time window between running the migration and updating all existing
    # users as confirmed, do the following
    User.all.update_all confirmed_at: DateTime.now
    # All existing user accounts should be able to log in after this.
  end

  def down
    remove_columns :users, :confirmation_token, :confirmed_at, :confirmation_sent_at
    # remove_columns :users, :unconfirmed_email # Only if using reconfirmable
  end
end

4. letter_openerの利用

最後にメール送信に不可欠なSMTPサーバの設定が必須となります。

通常は、config/environments/development.rbに以下の内容を追記する必要があります。

# config/environments/development.rb

config.action_mailer.raise_delivery_errors = true

ActionMailer::Base.delivery_method = :smtp
ActionMailer::Base.smtp_settings = {
  :enable_starttls_auto => false,
  :address => "smtp.gmail.com",
  :port => 587,
  :authentication => :plain,
  :user_name => "gmailのメールアドレス",
  :password => "メールのパスワード"
}

ただ、私はGitHubに自分のメールアドレスを公開するのに抵抗があったので、メール認証機能を追加するにあたり、letter_opener_webというgemを利用しました。

このgemを利用すると自分のメールアドレスを登録しなくても、ブラウザで送信したメールなどを確認できます。

利用方法は以下の手順を踏むだけです。

  1. Gemfileに以下の内容を追記
  2. app/config/routes.rbにルーティング設定を追記
  3. config/environments/development.rbにmailerの記載を追記

1. Gemfileに以下の内容を追記

group :development do #開発環境のみ
  gem 'letter_opener_web'
end

2. app/config/routes.rbにルーティング設定を追記

if Rails.env.development? #開発環境の場合
  mount LetterOpenerWeb::Engine, at: "/letter_opener"
end

3. config/environments/development.rbに以下を追記

config.action_mailer.delivery_method = :letter_opener_web

http://localhost:3000/letter_openerにアクセスすると、ブラウザ上から送信したメールが確認できます。

f:id:b_leiu:20190512203812p:plain

最後に

私はコントローラーを修正して、デフォルトの遷移先(localhost:3000)をログイン画面に変えたりしてアプリを実装しました。

ログイン画面

f:id:b_leiu:20190512201034p:plain:w300

ログイン成功

f:id:b_leiu:20190512201251p:plain

以上となります!

参考:

github.com

qiita.com

madogiwa0124.hatenablog.com