django-maintenance-modeの紹介

2018-12-19 / PythonDjangoDjangoライブラリ

概要

django-maintenance-modeを使い、Djangoプロジェクトにメンテナンスモードを導入していきます。

Webサイトの大規模な更新作業で、Webページを一時的に非表示にしたいというケースや、急な不具合が発生した際に原因解明までの繋ぎとして使うとか、後は小規模なウェブサイトによくありますが、サーバー上のソースを直接編集しているようなケースで役に立つ機能です。

今回は、通常は次のように表示されるウェブページがあり... これが普通のページ

メンテナンスモードをオンにすると、次のようにお知らせが表示されます。 メンテナンス中なのを教えてくれる

お知らせがあるので、ユーザーにとっても分かりやすいでしょう。また、503というHTTPステータスコードで返してくれるので、SEO的な都合にも配慮してくれます。

準備

まず、pipでインストールしましょう。

pip install django-maintenance-mode

settings.pyINSTALLED_APPSに足します。

INSTALLED_APPS = [
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
    'maintenance_mode',  # これ
    'app.apps.AppConfig',  # 自作のDjangoアプリ
]

settings.pyMIDDLEWAREに追加します。

MIDDLEWARE = [
    'django.middleware.security.SecurityMiddleware',
    'django.contrib.sessions.middleware.SessionMiddleware',
    'django.middleware.common.CommonMiddleware',
    'django.middleware.csrf.CsrfViewMiddleware',
    'django.contrib.auth.middleware.AuthenticationMiddleware',
    'django.contrib.messages.middleware.MessageMiddleware',
    'django.middleware.clickjacking.XFrameOptionsMiddleware',
    'maintenance_mode.middleware.MaintenanceModeMiddleware'  # これ
]

503.htmlを作成しましょう。デフォルトではtemplates直下の503.htmlが読まれます。

CSSフレームワークBlumaを使った、シンプルなページです。

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <title>サイトメンテナンス中 - naritoブログ</title>
    <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/bulma/0.7.2/css/bulma.min.css">
    <script defer src="https://use.fontawesome.com/releases/v5.3.1/js/all.js"></script>
</head>
<body>
    <section class="section">
        <div class="container">
            <h1 class="title">サイトのメンテナンス中です...</h1>
            <span class="icon has-text-info is-large">
                <i class="fas fa-wrench fa-3x fa-spin"></i>
            </span>
        </div>
    </section>
</body>
</html>

メンテナンスモードの開始と終了

メンテナンスモードの開始と終了方法は幾つかあります。

URLにアクセスして切り替える(スーパーユーザー専用)

あるURLにアクセスするとメンテナンスモードがオンになるという方法です。そのためのURLをdjango-maintenance-mode側で提供しています。

urls.pyに追記しまして...

path('maintenance-mode/', include('maintenance_mode.urls')),

これにより、/maintenance-mode/on/にアクセスするとメンテナンスモードになり、/maintenance-mode/off/でオフにできます。

コマンドで切り替える

次のコマンドで、メンテナンスモードを切り替えることもできます。

python manage.py maintenance_mode on
python manage.py maintenance_mode off

関数を利用する

set_maintenance_mode()という関数が提供されており、それで切り替えることもできます。

from maintenance_mode.core import set_maintenance_mode
set_maintenance_mode(True)
set_maintenance_mode(False)

また、get_maintenance_mode()関数で今がメンテナンス中かどうかを判断することもできます。

from maintenance_mode.core import get_maintenance_mode

# メンテナンス中ならば
if get_maintenance_mode():
    ...

メンテナンス中でも一部ユーザーは見れるように

メンテナンスモード中でも、一部のユーザは通常のページアクセスできる、といった機能も欲しいはずです。

まずですが、settings.pyに以下を記述しましょう。メンテナンス中であってもadmin管理サイトが使えるようになり、ログイン等の操作が可能になります。

# メンテナンス中でも管理サイトは使えるように。
MAINTENANCE_MODE_IGNORE_ADMIN_SITE = True

更に、ログインしたユーザーは通常のページも見れるようにしたいなら次の指定をします。

# ログインユーザーは、メンテナンス中でも通常ページが見れる。
MAINTENANCE_MODE_IGNORE_AUTHENTICATED_USER = True

ログインユーザーではなく、is_staff権限やis_superuser権限のユーザーにだけ適用したいならば、次のような設定があります。

# is_staffなユーザーはメンテナンス中でも通常ページが見れる。
MAINTENANCE_MODE_IGNORE_STAFF = True

# is_superuserなユーザーはメンテナンス中でも通常ページが見れる。
MAINTENANCE_MODE_IGNORE_SUPERUSER = True

切り替えを簡単にできるようにする

スーパーユーザーが、ワンクリックでメンテナンスモードをon / off できると楽ちんです。ナビバー等にリンクを用意し、ワンクリックで切り替えれるようにしてみましょう。

そのためには、まずsettings.pycontext_processorsに追加します。

TEMPLATES = [
    {
        'BACKEND': 'django.template.backends.django.DjangoTemplates',
        'DIRS': [os.path.join(BASE_DIR, 'templates')]
        ,
        'APP_DIRS': True,
        'OPTIONS': {
            'context_processors': [
                'django.template.context_processors.debug',
                'django.template.context_processors.request',
                'django.contrib.auth.context_processors.auth',
                'django.contrib.messages.context_processors.messages',
                'maintenance_mode.context_processors.maintenance_mode',  # これ
            ],
        },
    },
]

メンテナンス中でもログインできるようにし、スーパーユーザーは通常ページにアクセスできるよう、次の設定をしておきます。

MAINTENANCE_MODE_IGNORE_ADMIN_SITE = True
MAINTENANCE_MODE_IGNORE_SUPERUSER = True

後は、テンプレートに次のような記述をしておきましょう。

    {% if user.is_superuser %}
        {% if maintenance_mode %}
            <a href="{% url 'maintenance_mode_off' %}">メンテナンス終了</a>
        {% else %}
            <a href="{% url 'maintenance_mode_on' %}">メンテナンス開始</a>
        {% endif %}
    {% endif %}

スタッフ権限等のユーザーで同様のことをする

もしスタッフ権限のユーザーで同様のことをしたい場合は、「関数を利用する」で紹介したon/off切り替え関数を呼び出すビューを自分で作成し、テンプレートの{% if user.is_superuser %}{% url 'maintenance_mode...' %}部分をスタッフ権限と自作ビューに変更、MAINTENANCE_MODE_IGNORE_STAFF=Trueでメンテナンス中でもスタッフは自作ビューにアクセスできるようにすればOKです。

もしくは、MAINTENANCE_MODE_IGNORE_URLSを設定して、切り替え用の自作URLにはメンテナンス中でもアクセスできるようにする、等でも良いでしょう。

公式サイト

django-maintenance-mode

この記事の関連記事

関連記事はありません。

コメント欄

記事にコメントする

まだコメントはありません。