【Django】ユーザーがログインしているかどうかを識別する方法を解説!

Django

(最終更新月:2021年12月)

「ログインしているかどうかってどうやったらわかるの?」

「ログインの有無によりHTML表示を変更したい!」

というDjango初学者の方へ向けた記事となります

当記事では、ユーザーのログイン状況を識別した上で、

  • ログイン/ログアウトなどの表示を切り替える方法
  • リンク先を詳細/編集ページで切り替える方法

について解説していきます

アクセスしているユーザーのログイン状況を識別する

テンプレート上で、

{{ request.user.is_authenticated }}

とすることで、ログイン時は「True」、ログアウト時は「False」を返します

基本的には、is_authenticatedメソッドを使って条件分岐をしながらHTMLコードを書いていきます

まずは、ログイン/ログアウトの表示を切り替えていく方法をお伝えします

ログイン状況によりHTMLコードを変更する

ログイン前

ログイン後

変更する箇所はこちらになります↓

is_authenticatedメソッドを使い、条件分岐をします

<ul class="dropdown-menu" aria-labelledby="navbarDropdown">
      {% if request.user.is_authenticated %}
          <li><a class="dropdown-item" href="#">アカウント設定</a></li>
          <li><hr class="dropdown-divider"></li>
          <li><a class="dropdown-item" href={% url "account_logout" %}>ログアウト</a></li>
      {% else %}
          <li><a class="dropdown-item" href={% url "account_login" %}>ログイン</a></li>
          <li><hr class="dropdown-divider"></li>
          <li><a class="dropdown-item" href={% url "account_signup" %}>サインアップ</a></li>
      {% endif %}
</ul>

リンク先の変更

開発中の日報アプリにおいて、一覧ページ上各日報のタイトルにはリンクが貼られています

ログインユーザーと日報の作者が同じ場合編集ページへのリンク、それ以外は、詳細ページでの読み取り専用となります

【request.user == nippo.user】

【request.user != nippo.user】

それぞれのレイアウトも多少変更していますが、

  1. nippo-list.html
  2. nippo-create.html
  3. nippo-detail.html

とそれぞれコードを見ていきましょう!

nippo-list.html

{% extends "base.html" %}
{% block head_title %}日報アプリ一覧{% endblock %}
{% block content %}
<div class="container">
    {% if request.user.is_authenticated %}
        <div class="mt-3 d-flex justify-content-end">
            <a href={% url "nippo-create" %} class="btn btn-outline-primary float-end">
              <i class="bi bi-plus"></i>
            </a>
        </div>
    {% endif %}
    {% if object_list %}
        {% for obj in object_list %}
            <div class="card my-3">
                <div class="card-body">
                    <h5 class="card-title">
                      {% if obj.user == request.user %} 
                      <span class="float-end text-danger" data-bs-toggle="modal" data-bs-target="#deleteModal-{{obj.pk}}">
                          <i class="bi bi-trash-fill"></i>
                      </span>
                        <a href={% url 'nippo-update' obj.pk %}>
                      {% else %}
                        <a href={% url 'nippo-detail' obj.pk %}>
                      {% endif %}
                            {{ obj.title }}
                        </a>
                    </h5>
                    <p class="card-text">
                        {{ obj.content }}
                    </p>
                </div>
                <div class="card-footer">

                </div>
            </div>
            {% include "nippo/nippo-delete.html" with object=obj %}
        {% endfor %}
      {% else %}
        <div>日報が見つかりません</div>
      {% endif %}
</div>
{% endblock %}

変更点は下記のとおりです

  • 「編集」リンクをなくしたこと
  • ログインユーザーによる条件分岐を追記
  • Cardに「max-width」などのスタイルを追加

nippo-create.html

{% extends 'base.html' %}

{% block content %}
<div class="container my-3" style="max-width:700px;">
    
    <div class="text-center my-3">
    {% if object %}
        <h2>{{ object }}の編集</h2>
    {% else %}
        <h2>新しく日報を作成</h2>
    {% endif %}
    </div>
    
    <form method="POST"> {% csrf_token %}
    {{ form.as_p }}
    {% if object %}
        <button class="btn btn-primary form-control" type="submit">保存</button>
        <p class="my-3 text-danger" viewBox="0 0 16 16" data-bs-toggle="modal" data-bs-target="#deleteModal" style="cursor:pointer;display:inline-block;font-weight:700; font-size:12px;">
            <u>日報を削除する</u>
        </p>
    {% else %}
        <button class="btn btn-primary form-control" type="submit">登録</button>
    {% endif %}      
    </form>
    {% if object %}
        {% include 'nippo/nippo-delete.html' %}
    {% endif %}
</div>
{% endblock %}

変更点は下記のとおりです

  • pタグ「日報を削除する」で、Deleteモダルを表示
  • Deleteモダル(nippo-delete.html)をinclude

nippo-detail.html

{% extends 'base.html' %}

{% block content %}
<div class="container">
    <div class="card mx-auto my-5 w-50" style="min-width:300px;">
        <div class="card-header">
            【作成日時】{{ object.timestamp }}
        </div>
        <div class="card-body pb-3">
            <h3 class="card-title mb-3 px-2" style="border-bottom:solid 1px #f4f4f4;">
                {{ object.title }}
            </h3>
            <p class="card-text my-3 px-5">{{ object.content }}</p>
        </div>
        <div class="card-footer">
            <a href={% url 'nippo-list' %} class="btn btn-danger btn-sm">戻る</a>
        </div>
    </div>
</div>
{% endblock %}

変更点は下記のとおりです

  • 編集、削除ボタンを非表示
  • カードフッターに「戻る」ボタンの追加

まとめ

ユーザーのログイン情報を得るには、

request.user.is_authenticated

を使うととても便利です

条件分岐を活用し意図した表示やリンク先になるよう記述すれば、あなたの意図したとおりの動線が作れます

少しでも効率よくコードを書くヒントになれば幸いです

さて、次回については、ユーザーモデルクラスを拡張する方法、OneToOneFieldについて解説していきます

当ブログでは、日報アプリ開発を通じて、Webアプリを一から開発し公開するまでを初学者の方でもわかるようにと記事を連載しています

「Djangoでのアプリ開発を学びたい!」
「Djangoで開発したアプリをWebで公開するにはどうするの?」

という方は必見です!

【Django】チュートリアル|日報アプリの開発から公開まで
Djangoのチュートリアルをお探しですか?具体的に「手を動かして作ってみたい!」という方へ向けて、誰でもできる簡易的な日報アプリの開発を通じて、Djangoの様々な機能に触れていくシリーズとなっています。PythonでWebアプリを作りたい方、必見の記事となります!
タイトルとURLをコピーしました