LoginSignup
2
2

More than 3 years have passed since last update.

Rails6 ログインしているユーザとしていないユーザでアクセスできるページに制限をつけよう!

Posted at

目的

  • ログインしているユーザとしていないユーザでアクセスできるページを分ける方法をまとめる

すいません

  • 忘れないうちに記載したくて内容がとても雑です。申し訳ないです。。。

実施方法概要

  1. ログイン時にsession[:user_id]にユーザIDを格納
  2. アクセスページの制限

実施方法詳細

  1. ログイン時にsession[:user_id]にユーザIDを格納

    1. ユーザがログインシーケンスを実行するビューファイルの内容を下記に記載する。(付録のlogin_form.html.erbに記載)

      <%= form_tag("/login") do %>
        <p>メールアドレス</p>
        <input type="text" name="email" value="<%= @enail %>">
        <p>パスワード</p>
        <input type="password" name="password">
        <input type="submit" value="ログイン">
      <% end %>
      
    2. 前述のログインシーケンスの値を受け取るコントローラのアクションの内容を下記に記載する。(付録のusers_controller.rbに記載)

      def login
        @user = User.find_by(email: params[:email], password: params[:password])
        if @user
          #ここでsession[:user_id]にユーザIDを格納している。
          session[:user_id] = @user.id
          redirect_to("/posts/index")
        else
          @email = params[:email]
          render("users/login_form")
        end
      end
      
    3. ヘッダーに表示されているページリンクの表示/非表示をログインの有無によって設定する。ヘッダーのビューファイルの内容を下記に記載する。(付録のapplication.html.erbに記載。)

      <ul>
        <% if session[:user_id] %>
              #ログインしていてsession[:user_id]にユーザIDが入っている時の表示
          <li><%= link_to("Home", "/") %></li>
          <li><%= link_to("このサービスについて", "/about") %></li>
          <li><%= link_to("つみかさね一覧", "/posts/index") %></li>
          <li><%= link_to("つみかさね新規登録", "/posts/new") %></li>
          <li><%= link_to("ユーザ一覧", "/users/index") %></li>
          <li><%= link_to("ログアウト", "/logout") %></li>
          <li><%= link_to("#{@current_user.name}", "/users/#{@current_user.id}") %></li>
        <% else %>
              #ログインしておらずsession[:user_id]にユーザIDが入っていない時の表示    
          <li><%= link_to("Home", "/") %></li>
          <li><%= link_to("このサービスについて", "/about") %></li>
          <li><%= link_to("新規登録", "/signup") %></li>
          <li><%= link_to("ログイン", "/login") %></li>
        <% end %>
      </ul>
      
  2. アクセスページの制限

    1. 下記にsession[:user_id]の値を用いたアクセスページの制限する処理とメソッド定義を記載する。(付録のapplication_controller.rbに記載。application_controller.rbは必ず実行されるため)

      # set_current_userのメソッドを最初に実行する宣言
      before_action :set_current_user
      
      def set_current_user
          #session[:user_id]に格納されているIDを元にユーザデータを格納            
          @current_user = User.find_by(id: session[:user_id])            
      end
      
      # ログインしていない時にページのアクセス制限をつける分岐(判断材料は@current_userがnilかどうか)
      def authenticate_user
          if @current_user == nil
              #flash[:notice] = "ログインが必要です。"
              redirect_to("/login")
          end
      end
      
      # ログインしている時にページのアクセス制限をつける分岐(判断材料は@current_userがnilかどうか)
      def forbid_login_user
          if @current_user != nil
              #flash[:notice] = "すでにログインしています"
              redirect_to("/posts/index")
          end
      end
      
    2. ログインしていない時にアクセス制限をかけるページのアクション名を設定する。(本記載はアクセス制限をかけたいページを司るコントローラファイルに記載する。)(付録のusers_controller.rbに記載)

      before_action :authenticate_user, {only: [:アクション名1, :アクション名2, :アクション名3, :アクション名4]}
      
    3. ログインしている時にアクセス制限をかけるページのアクション名を設定する。(本記載はアクセス制限をかけたいページを司るコントローラファイルに記載する。)(付録のusers_controller.rbに記載)

      before_action :forbid_login_user, {only: [:アクション名1, :アクション名2, :アクション名3, :アクション名4]}
      

付録

  • 今回の一連の内容に関係するファイルを下記に記載する。

  • login_form.html.erb

    <%= form_tag("/login") do %>
        <%= @error_message %>
        <p>メールアドレス</p>
        <input type="text" name="email" value="<%= @enail %>">
        <p>パスワード</p>
        <input type="password" name="password">
        <input type="submit" value="ログイン">
    <% end %>
    
  • users_controller.rb

    class UsersController < ApplicationController
    
      # :index, :show, :edit, :updateのアクションアクセス時@current_userがnilならはじく
      before_action :authenticate_user, {only: [:index, :show, :edit, :update]}
      before_action :forbid_login_user, {only: [:login_form, :login, :new, :create]}
    
      def index
        @user = User.all
      end
    
      def show
        @user = User.find_by(id: params[:id])
      end
    
      def new
        @user = User.new
      end
    
      def create
        @user = User.new(name: params[:name], email: params[:email], password: params[:password])
        if @user.save
          # flash[:notice] = "登録完了"
          session[:user_id] = @user.id
          redirect_to("/users/#{@user.id}")
        else
          # flash[:notice] = "登録失敗"
          render ("users/new")
        end
      end
    
      def edit
        @user = User.find_by(id: params[:id])
      end
    
      def update
        @user = User.find_by(id: params[:id])
        @user.name = params[:name]
        @user.email = params[:email]
        if @user.save
          # flash[:notice] = "更新完了"
          redirect_to("/users/#{@user.id}")
        else
          # flash[:notice] = "更新失敗"
          render("users/edit")
        end
      end
    
      def login_form
    
      end
    
      def login
        @user = User.find_by(email: params[:email], password: params[:password])
        if @user
          #flash[:notice] = "ログインしました"
          session[:user_id] = @user.id
          redirect_to("/posts/index")
        else
          @error_message = "メールアドレスかパスワードが間違っています。"
          @email = params[:email]
          render("users/login_form")
        end
      end
    
      def logout
        session.delete(:user_id)
        #flash[:notice] = "ログアウトしました"
        redirect_to("/login")
      end
    end
    
  • application.html.erb

    <!DOCTYPE html>
    <html>
      <head>
        <title>EveyDayStudy</title>
        <%= csrf_meta_tags %>
        <%= csp_meta_tag %>
    
        <%= stylesheet_link_tag 'application', media: 'all', 'data-turbolinks-track': 'reload' %>
        <%= javascript_pack_tag 'application', 'data-turbolinks-track': 'reload' %>
      </head>
    
      <body>
        <!-- header -->
        <header>
          <nav class="navbar navbar-expand-md navbar-light bg-light sticky-top">
            <div class="container-fluid">
              <button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarResponsive">
                <span class="navbar-toggler-icon"></span>
              </button>
              <div class="collapse navbar-collapse" id="navbarResponsive">
                <ul class="navbar-nav ml-auto">
                  <% if session[:user_id] %>
                    <li class="navbar-item"><%= link_to("Home", "/", {class: "nav-link"}) %></li>
                    <li class="navbar-item"><%= link_to("このサービスについて", "/about", {class: "nav-link"}) %></li>
                    <li class="navbar-item"><%= link_to("つみかさね一覧", "/posts/index", {class: "nav-link"}) %></li>
                    <li class="navbar-item"><%= link_to("つみかさね新規登録", "/posts/new", {class: "nav-link"}) %></li>
                    <li class="navbar-item"><%= link_to("ユーザ一覧", "/users/index", {class: "nav-link"}) %></li>
                    <li class="navbar-item"><%= link_to("ログアウト", "/logout", {method: "delete", class: "nav-link"}) %></li>
                    <li class="navbar-item"><%= link_to("#{@current_user.name}", "/users/#{@current_user.id}", {class: "nav-link"}) %></li>
                  <% else %>    
                    <li class="navbar-item"><%= link_to("Home", "/", {class: "nav-link"}) %></li>
                    <li class="navbar-item"><%= link_to("このサービスについて", "/about", {class: "nav-link"}) %></li>
                    <li class="navbar-item"><%= link_to("新規登録", "/signup", {class: "nav-link"}) %></li>
                    <li class="navbar-item"><%= link_to("ログイン", "/login", {class: "nav-link"}) %></li>
                  <% end %>
                </ul>
              </div>
            </div>
          </nav>
        </header>
        <!--header end-->
    
        <!-- main -->
        <main>
          <%= yield %>
        </main>
        <!-- main end -->
    
        <!-- footer -->
        <footer>
            <div class="container-fluid padding">
                <div class="row text-center">
                    <div class="col-md-4">
                        <hr class="light">
                        <p>000-0000-0000</p>
                        <p>email@mail.com</p>
                        <p>miriwo</p>
                        <p>City, Statem, 0000</p>
                    </div>
                    <div class="col-md-4">
                        <hr class="light">
                        <h5>Our hours</h5>
                        <hr class="light">
                        <p>Monday: 9:00~17:00</p>
                        <p>Saturaday: 10:00~16:00</p>
                        <p>Sunday: close</p>
                    </div>
                    <div class="col-md-4">
                        <hr class="light">
                        <h5>service Area</h5>
                        <hr class="light">
                        <p>City, Statem, 0000</p>
                        <p>City, Statem, 0000</p>
                        <p>City, Statem, 0000</p>
                    </div>
                    <div class="col-12">
                        <hr class="light-100">
                        <h5>&copy; miriwo.com</h5>
                    </div>
                </div>
            </div>
        </footer>
        <!-- footer end -->
    
      </body>
    </html>
    
  • application_controller.rb

    class ApplicationController < ActionController::Base
        before_action :set_current_user                            
        def set_current_user            
            @current_user = User.find_by(id: session[:user_id])            
        end
    
        def authenticate_user
            if @current_user == nil
                #flash[:notice] = "ログインが必要です。"
                redirect_to("/login")
            end
        end
    
        def forbid_login_user
            if @current_user != nil
                #flash[:notice] = "すでにログインしています"
                redirect_to("/posts/index")
            end
        end
    end
    
2
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
2