【django】アクセス制限:ログインを必須にする(サイト全体・ページ毎)
2021.04.13 /
本記事では、PythonのWebフレームワークdjangoによるWebアプリケーションで、ログインを必須にする方法について解説していきます。
Webアプリケーションにログイン認証機能を組み込んでいるならば、ログインの有無によるアクセス制限を設けると、より一層使い勝手の良いWebアプリケーションになります。
例えば、会員のみが閲覧可能な会員専用ページを作成するなどが可能になります。
ログイン認証機能の組み込み方法は、以下記事をご参照ください。
アクセス制限(ログイン必須)は、サイト全体で一括して設定することもできますし、ページ毎(ビュー毎)で設定することも可能です。
本記事を通して以下の知識を学べます。
- アクセス制限(ログイン必須)について
- ログイン必須をページ毎に設定する方法
- ログイン必須をサイト全体で一括設定する方法
アクセス制限;ログイン必須とは
本記事で言っているログイン必須とは、
Webアプリケーションのページ(URL)にアクセスした際に、ログインしていなかった場合、ログインページに自動的にリダイレクトすることを言います。
このログインを必須にする機能は、djangoに初めから備わっている仕組みを使うことで、簡単に実装することができます。
以下でログイン必須にする機能の実装方法を解説していきます。
ログイン必須にする方法
Webアプリケーションをログイン必須にする方法は、大きく分けて以下2つあります。
- ページ毎にログイン必須にする
- サイト全体を一括でログイン必須にする
上記の2つは、それぞれ仕組みが異なります。
ご自身のWebアプリケーションに合う方法で組み込んでみてください。
ページ毎にログイン必須にする
特定のページに対して、ページ閲覧をログイン必須にする場合は、django.contrib.authを使用します。
django.contrib.authアプリケーションは、ログイン認証機能を組み込む際にも使いましたが、今回のログイン必須にする仕組みでも使います。
ページ毎にログイン必須にする方法は、クラスベースビューと関数ベースビューで異なります。
クラスベースビュー:LoginRequiredMixin
クラスベースビューの場合は、
django.contrib.auth.mixinsのLoginRequiredMixinを継承することで、このクラスベースビューの処理がログイン必須になります。
from django.contrib.auth.mixins import LoginRequiredMixin
class IndexView(TemplateView,LoginRequiredMixin):
template_name = "five/index.html"
LoginRequiredMixinを継承するだけなので、非常に簡単にログイン必須にできます。
しかしログイン必須にしたいクラスベースビューすべてにLoginRequiredMixinを継承させる必要があるので、ビューの数が多い場合は少し面倒になります。
関数ベースビュー:login_required
関数ベースビューの場合は、
django.contrib.auth. decoratorsのlogin_requiredのデコレーターをビュー関数の直前に記入することで、関数ビューの処理がログイン必須になります。
from django.contrib.auth.decorators import login_required
@login_required
def index(request):
return render(request,"five/index.html")
@login_requiredデコレーターは、アクセスしたユーザーがログインしていない場合、settings.pyのLOGIN_URL にリダイレクトします。
ユーザーがログインしていれば、そのまま関数ビューを処理します。
@login_requiredデコレーターも、ログインを必須にさせた関数ビューすべてに記入する必要があります。
そのためビューの数が多い場合は手間がかかります。
サイト全体を一括でログイン必須にする
すべてのビューでログイン必須にする場合は、一括でログイン必須にする方法を使用しましょう。
一括でサイトをログイン必須にするにはミドルウェア(Middleware)を使用します。
ミドルウェアによるログイン必須にするには、以下2つの方法があります。
- MiddlewareMixinを使用
- GlobalLoginRequiredMiddlewareを使用
各ミドルウェアの作成・使用方法を以下で解説します。
MiddlewareMixin
アプリケーションフォルダ直下(urls.pyやviews.pyの階層)にmiddlewareフォルダを作成します。
次に作成したmiddlewareフォルダ内にお好きな名前のpyファイル(ここではauth.pyとする)を作成し、以下のように記述します。
# middleware.auth.py
from django.utils.deprecation import MiddlewareMixin
from django.http import HttpResponseRedirect
class AuthMiddleware(MiddlewareMixin):
def process_response(self, request, response):
if request.path != '/login/' and not request.user.is_authenticated:
return HttpResponseRedirect('/login/')
return response
リクエストされたURLがloginの場合と、ユーザーがログインしている場合を除いて、loginにリダイレクトするよう記述されています。
ログインしているかどうかは、request.user.is_authenticatedで判別しています。
ミドルウェア(auth.py)を作成しましたら、settings.pyにそのミドルウェアを追加します。
# settings.py
# アプリケーション名がfiveの場合
MIDDLEWARE = [
'five.middleware.auth.authMiddleware',
]
これにより、Webアプリケーション全体がログイン必須になります。
まとめるとMiddlewareMixinによるログイン必須の方法は以下の流れで行います。
- middlewareフォルダを作成
- ミドルウェアpyファイルを作成
- settings.pyにミドルウェアを追加
GlobalLoginRequiredMiddleware
GlobalLoginRequiredMiddlewareモジュールを使用するために、pipを使用してdjango-glrmをインストールします。
pip django-glrm
次に以下のようにsettings.pyにミドルウェアを追加します。
# settings.py
MIDDLEWARE = [
'global_login_required.GlobalLoginRequiredMiddleware',
]
最後にsettings.pyにPUBLIC_PATHSを追加し、ログインを必須にしないURLを指定します。
PUBLIC_PATHS = [
'/login/',
]
これにより、上記で指定したURL以外はログイン必須となります。
まとめ
本記事「【django】アクセス制限:ログインを必須にする(サイト全体・ページ毎)」はいかがでしたか。
djangoでは、ログインを必須にするのは非常に簡単でしたね。
特別な記述をする必要なく、ログイン必須機能をWebアプリケーションに組み込めますので、ぜひご自身のサイトに組み込んでみてください。