sk

開発で得たこと

ユーザーの作成

この記事で行うこと

チケットを予約するユーザーを作成します。

f:id:sksksksksk:20180726231701p:plain

使うもの

Ruby 2.4.2
Rails 5.1.6
devise 4.4.3

現場では?

認証機能を実装する際は今でもdeviseが主流です。
大企業や認証を頻繁にカスタマイズしたい企業などは独自の認証ライブラリを実装するケースが多いです。食べログなどは独自の認証機能を開発していると聞いたことがあります。

deviseはオーバライドしてカスタマイズすることが可能です。
一般的なサービスにおいてはほぼ間違いなくカスタマイズするのでこの記事で基本的な操作をマスターしましょう。

実装手順

① deviseのインストール

Gemfile

gem 'devise'

インストールしてください。

bundle install
② deviseの設定

deviseの関連ファイルをインストールします。

$ rails g devise:install
Running via Spring preloader in process 37183
      create  config/initializers/devise.rb
      create  config/locales/devise.en.yml
===============================================================================

Some setup you must do manually if you haven't yet:

  1. Ensure you have defined default url options in your environments files. Here
     is an example of default_url_options appropriate for a development environment
     in config/environments/development.rb:

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

     In production, :host should be set to the actual host of your application.

  2. Ensure you have defined root_url to *something* in your config/routes.rb.
     For example:

       root to: "home#index"

  3. Ensure you have flash messages in app/views/layouts/application.html.erb.
     For example:

       <p class="notice"><%= notice %></p>
       <p class="alert"><%= alert %></p>

  4. You can copy Devise views (for customization) to your app by running:

       rails g devise:views

===============================================================================


上記1~4の設定を順に行なっていきます。


1. 環境設定ファイルにデフォルトURLを設定する。
開発環境ですので、localhostを設定しましょう。

config/environments/development.rb

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

ここで本番環境も一緒に設定しておきます。

config/environments/production.rb

config.action_mailer.default_url_options = { host: ENV['WEB_DOMAIN'], protocol: 'https' }

ドメイン部分は環境(dev/stg/pro)ごとに異なるので現場では環境変数として扱います。環境変数環境変数の設定 - さがえもん を読んで設定してみましょう。

完了したらRailsサーバを再起動します。

POINT 再起動

config配下のファイルを修正したり、Gemをインストールした際は再起動をする癖をつけましょう。


2. ルートの設定
TOPページを用意します。

$ rails g controller welcome index

config/routes.rb

root 'welcome#index'

POINT 「'」(シングルクォーテーション)を使おう

なるべく「"」(ダブルクォーテーション)ではなく「'」(シングルクォーテーション)を使用しましょう。
企業の好みもありますが、「'」の方が文量が少なくなります。
さらに、「'」には、変数を含むことが('#{}'は)できないので可読性をあげることもできます。


ここまで設定するとトップページは以下のような表示になります。

f:id:sksksksksk:20180726203132p:plain


3. フラッシュメッセージの準備

ログインの成功・失敗のメッセージが表示されるようになります。
app/views/layouts/application.html.haml

!!!
%html
  %head
    %meta{:content => "text/html; charset=UTF-8", "http-equiv" => "Content-Type"}/
    %title TicketReservation
    = csrf_meta_tags
    = stylesheet_link_tag    'application', media: 'all', 'data-turbolinks-track': 'reload'
    = javascript_include_tag 'application', 'data-turbolinks-track': 'reload'
  %body
    %p.notice= notice
    %p.alert= alert
    = yield


4. deviseのviewファイルを作成

今後、登録・ログインページなどカスタマイズしなければならない機会があるので作成しておきましょう。今回はuserスコープで作成します。

$ rails g devise:views users
Running via Spring preloader in process 37639
      invoke  Devise::Generators::SharedViewsGenerator
      create    app/views/users/shared
      create    app/views/users/shared/_links.html.erb
      invoke  form_for
      create    app/views/users/confirmations
      create    app/views/users/confirmations/new.html.erb
      create    app/views/users/passwords
      create    app/views/users/passwords/edit.html.erb
      create    app/views/users/passwords/new.html.erb
      create    app/views/users/registrations
      create    app/views/users/registrations/edit.html.erb
      create    app/views/users/registrations/new.html.erb
      create    app/views/users/sessions
      create    app/views/users/sessions/new.html.erb
      create    app/views/users/unlocks
      create    app/views/users/unlocks/new.html.erb
      invoke  erb
      create    app/views/users/mailer
      create    app/views/users/mailer/confirmation_instructions.html.erb
      create    app/views/users/mailer/email_changed.html.erb
      create    app/views/users/mailer/password_change.html.erb
      create    app/views/users/mailer/reset_password_instructions.html.erb
      create    app/views/users/mailer/unlock_instructions.html.erb

コントローラーも作成しておきます。

$ rails g devise:controllers users
Running via Spring preloader in process 37972
      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
===============================================================================

Some setup you must do manually if you haven't yet:

  Ensure you have overridden routes for generated controllers in your routes.rb.
  For example:

    Rails.application.routes.draw do
      devise_for :users, controllers: {
        sessions: 'users/sessions'
      }
    end

===============================================================================

routes.rbは以下のように設定してください。

routes.rb

Rails.application.routes.draw do
  root 'welcome#index'
  devise_for :users, path: 'users', controllers: {
    registrations: 'users/registrations', # 登録
    confirmations: 'users/confirmations', # 確認
    sessions: 'users/sessions'            # ログイン
  }
  resources :tickets, only: %i(new create index)
end

deviseのビュー作成ではhamlの自動変換が聞かないので以下のコマンドを叩いておきましょう。

$ rails haml:replace_erbs

また、今回はUserスコープでViewを作成したのでdeviseに認識させましょう。

config/initializers/devise.rb

Devise.setup do |config|
  # The secret key used by Devise. Devise uses this key to generate
  # random tokens. Changing this key will render invalid all existing
  # confirmation, reset password and unlock tokens in the database.
  # Devise will use the `secret_key_base` as its `secret_key`
  # by default. You can change it below and use your own secret key.
  # config.secret_key = 'a7b382632d6274a5ced712f49307a5f8793d1cbd1912399a24849f1f80dc44d75510108fc81d9089f5bd82271b2ebdfa914cc7877dfd0b33c0e1bec443ce5b47'

  # ==> Controller configuration
  # Configure the parent class to the devise controllers.
  # config.parent_controller = 'DeviseController'
  config.scoped_views = true
・・・

Railsサーバを再起動させてください。


以上でdevise関連ファイルの設定は終了です。

③ ユーザーモデルの作成

deviseを使ってユーザーモデルを作成します。

$ rails g devise User

専用のマイグレーションファイルが作成されるので、データベースへ反映します。

db/migrate/20180726114118_devise_create_users.rb

# frozen_string_literal: true

class DeviseCreateUsers < ActiveRecord::Migration[5.1]
  def change
    create_table :users do |t|
      ## Database authenticatable
      t.string :email,              null: false, default: ""
      t.string :encrypted_password, null: false, default: ""

      ## Recoverable
      t.string   :reset_password_token
      t.datetime :reset_password_sent_at

      ## Rememberable
      t.datetime :remember_created_at

      ## Trackable
      t.integer  :sign_in_count, default: 0, null: false
      t.datetime :current_sign_in_at
      t.datetime :last_sign_in_at
      t.string   :current_sign_in_ip
      t.string   :last_sign_in_ip

      ## Confirmable
      # t.string   :confirmation_token
      # t.datetime :confirmed_at
      # t.datetime :confirmation_sent_at
      # t.string   :unconfirmed_email # Only if using reconfirmable

      ## Lockable
      # t.integer  :failed_attempts, default: 0, null: false # Only if lock strategy is :failed_attempts
      # t.string   :unlock_token # Only if unlock strategy is :email or :both
      # t.datetime :locked_at


      t.timestamps null: false
    end

    add_index :users, :email,                unique: true
    add_index :users, :reset_password_token, unique: true
    # add_index :users, :confirmation_token,   unique: true
    # add_index :users, :unlock_token,         unique: true
  end
end

app/models/user.rb

class User < ApplicationRecord
  # Include default devise modules. Others available are:
  # :confirmable, :lockable, :timeoutable and :omniauthable
  devise :database_authenticatable, :registerable,
         :recoverable, :rememberable, :trackable, :validatable
end


データベースへ反映

$ rails db:migrate
== 20180726114118 DeviseCreateUsers: migrating ================================
-- create_table(:users)
   -> 0.0020s
-- add_index(:users, :email, {:unique=>true})
   -> 0.0008s
-- add_index(:users, :reset_password_token, {:unique=>true})
   -> 0.0011s
== 20180726114118 DeviseCreateUsers: migrated (0.0044s) =======================
④ Viewの編集

登録・ログイン画面に遷移できるようにリンクをつけてあげます。

app/views/layouts/application.html.haml

  %body
    %header
      %nav
        - if user_signed_in?
          %strong= link_to 'ホーム', :root
          = link_to 'プロフィール変更', :edit_user_registration
          = link_to 'ログアウト', :destroy_user_session, method: :delete
        - else
          = link_to 'サインアップ', :new_user_registration
          = link_to 'ログイン', :new_user_session
    %p.notice= notice
    %p.alert= alert
    = yield

動作確認

① トップページ

f:id:sksksksksk:20180726211357p:plain

② サインアップ(登録)ページ

f:id:sksksksksk:20180726211500p:plain

③ サインアップ後のトップページ

f:id:sksksksksk:20180726211626p:plain

質疑応答

コメントしてください。

ProgateやRailsチュートリアル、プログラミングスクールを通い終えたが現場のコードはかけない、

一体どうやって書くの?と思っているエンジニアのみなさんのためのチュートリアルを公開しています。

チュートリアル