ブログBLOG

\ Web・ゲーム開発に関する情報を発信中 /

Djangoの500エラーをSlackに通知する方法を解説(トレースバック付き)

Django
django , python , slack
20241213_django-send-error-to-slack-tmb

ご覧いただきありがとうございます!
領護(りょうご)です。

Djangoを本番環境で運用していると、エラーが発生していないか気になりますよね?
今回は、Djangoの500エラーをSlackに通知し、トレースバックの内容まで確認する方法を解説します。


Google Chatエラー通知画像
上記のように、Slackにエラー内容を通知し、トレースバックも確認できます。

目次

実行環境

Docker Desktop:4.37.0
Python:3.12.8
Django:5.1.3
requests:2.31.0

SlackのWebhook URLを取得する

Slackに通知を送るには、Webhook URLが必要です。
Webhook URLとは、特定のサービスやアプリケーションが他のサービスと通信する時に使用するURLです。
主に、イベントが発生した際に自動で通知を送信したり、データを送るために使用します。

以下の手順で取得します。

20241213_django-send-error-to-slack-01

1.https://samurai-world.slack.com/intl/ja-jp/appsを開き、右上の「サインイン」をクリック

20241213_django-send-error-to-slack-02

2.各Slackのアカウントにサインイン
※ Slackのアカウントをお持ちでない場合は、アカウント作成を行ってください。

20241213_django-send-error-to-slack-03

3.サインイン完了後、右上の「管理」をクリック
※ ページリンクが「https://ワークスペース名.slack.com/marketplace」になっていることを確認してください。

20241213_django-send-error-to-slack-04

4.右上の検索窓「incoming webhooks」と入力して検索
5.検索結果の中から「incoming Webhook」をクリック

20241213_django-send-error-to-slack-05

6.「Slackに追加」をクリック

20241213_django-send-error-to-slack-06

7.通知を送りたいチャンネルを選択

注意!

チャンネルを作成していない場合は、選択ができないので、先に通知用のチャンネルを作成しておいてください。

20241213_django-send-error-to-slack-07

8.チャンネル選択後、「Incoming Webhook インテグレーションの追加」をクリック

20241213_django-send-error-to-slack-08

9.Webhook URLの項目にある「URLをコピーする」をクリック
次のプログラム作成に使うのでどこかに控えておいてください。

20241213_django-send-error-to-slack-09

10.説明ラベル、名前、アイコンのカスタマイズができるので自分好みに設定する
※ 初期設定でも大丈夫です。
11.設定完了後、「設定を保存する」をクリック
これでWebhook URLの新規作成と取得が完了しました。

続いてプログラムの作成に移ります。

フォルダ構成

sample_web/
├── .env                        # 環境変数ファイル
├── docker-compose.yml          # Docker Compose設定ファイル
├── manage.py                   # Django管理スクリプト
├── sample_project/             # プロジェクト名
│   ├── asgi.py                 # ASGI設定ファイル
│   ├── settings.py             # プロジェクト設定ファイル
│   ├── urls.py                 # URLルーティング
│   ├── wsgi.py                 # WSGI設定ファイル
│   ├── static/                 # 静的ファイルディレクトリ
│   │   └── css/
│   │       └── base.css        # ベースCSSファイル
│   └── templates/              # HTMLテンプレートディレクトリ
│       └── home.html           # ホームページのテンプレート
├── home/                       # アプリフォルダ
│   ├── views.py                # ビューファイル
│   └── migrations/             # マイグレーションファイル
└── common/                     # 共通機能用フォルダ
    └── send_error_log.py       # エラーログ送信スクリプト

今回、解説するフォルダ構成は、上記の構成になります。
解説に使用するのは、common/send_error_log.py、home/views.py、sample_project/urls.py、sample_project/settings.pyの4つを使用します。

必要なライブラリのインストール

pip install requests

通知を送信する時に必要なライブラリ「requests」をインストールします。
※ 既にインストールしている方は、スキップしてください。

Slackにエラーを通知するプログラムを作成

Slackにエラーを通知する処理をcommon/send_error_log.pyに作成します。

send_error_log.py
import traceback
import requests
import json

from django.views.decorators.csrf import requires_csrf_token
from django.views.defaults import server_error

# Slackにメッセージを送信する
def send_error_to_slack(message_list, color, username):

    WEBHOOK_URL = "ここに先ほどコピーしたWebhook URLを張り付け"

    # メッセージを送信
    requests.post(
        WEBHOOK_URL,
        data=json.dumps(
            {
                "attachments": [
                    {
                        "text": "\n".join(message_list),
                        "color": color,
                    }
                ],
                "username": username,
            }
        ),
    )

# 500番エラーをSlackに通知
@requires_csrf_token
def server_error_send_to_slack(
    request,
    template_name="500.html",
):
    # Slackにエラーメッセージを通知する
    message_list = [
        "🚨 **500 Internal Server Error 発生** 🚨",
        f"URL: {request.build_absolute_uri()}",
        f"メソッド: {request.method}",
        f"Traceback:```\n{traceback.format_exc()}\n```",
    ]

    # Slackにエラーメッセージを通知する
    send_error_to_slack(message_list, "danger", "システムエラー通知")

    return server_error(request, template_name)

Slackにエラーを送信する処理全体のプログラムです。
send_error_to_slack関数は、メッセージを送信する基本設定になります。
server_error_send_to_slack関数は、送信するメッセージの内容を設定しています。

send_error_log.py
WEBHOOK_URL = "ここに先ほどコピーしたWebhook URLを張り付け"

ここには、先ほどコピーしたWebhook URLを張り付けてください。

注意!

解説を簡単にするために、今回はWebhook URLをコードに直接書いていますが、実際には環境変数にして読み込むことをおすすめします!

send_error_log.py
WEBHOOK_URL = "https://hooks.slack.com/services/~~~"

張り付けると上記のようになります。

send_error_log.py
# Slackにエラーメッセージを通知する
message_list = [
    "🚨 **500 Internal Server Error 発生** 🚨",
    f"URL: {request.build_absolute_uri()}",
    f"メソッド: {request.method}",
    f"Traceback:```\n{traceback.format_exc()}\n```",
]

今回通知するメッセージ内容は、下記のようにしています。
ここは通知したい内容を自由に変更してもOKです!

通知メッセージ内容
URL:エラーが発生したページリンク
メソッド:GET / POSTのどちらでエラーが発生したか
Traceback:エラーの詳細を表示するトレースバックを表示

500エラーのトリガー設定

500エラーが発生した時に処理が実行するようにトリガーをsample_project/urls.pyに設定します。

urls.py
from django.contrib import admin
from django.urls import include, path
from common.send_error_log import server_error_send_to_slack

urlpatterns = [
    path("admin/", admin.site.urls),
    # ~~~
]

# 500番エラーをSlackに通知する設定
handler500 = server_error_send_to_slack

500エラーが発生した際にSlackへ通知を送るため、先ほど作成した関数をインポートし、handler500に設定します。
これで、エラー発生時に自動で通知が届くようになります!

500エラーが届くかテストする

settings.py
# SECURITY WARNING: don't run with debug turned on in production!
DEBUG = False

500エラーが届くかテストするには、sample_project/settings.pyDEBUGFalseに設定を変更してください。

views.py
from django.views.generic import TemplateView

# ホームページ
class HomePage(TemplateView):

    template_name = "home.html"

    def get(self, request, *args, **kwargs):

        # 500エラーを起こす
        print(hogehoge)
        return super().get(request, *args, **kwargs)

home/views.pyに定義していない「hogehoge」変数をprintするように500エラーをわざと起こしてみます。

20241213_django-send-error-to-slack-10

そうするとSlackにエラーが通知されます!
トレースバックもきっちり表示されています。
簡単ですね!

おまけ:特定の処理を監視する方法

今回は、500エラーのSlackに通知する方法を解説しましたが、実は特定の処理にもエラー通知を送ることができます。

views.py
from django.views.generic import TemplateView
from common.send_error_log import send_error_to_slack

# ホームページ
class HomePage(TemplateView):

    template_name = "home.html"

    def get(self, request, *args, **kwargs):
        try:
            # 感知させたい処理を行う
            pass
        except Exception:

            # 処理が上手くいかない時にエラーメッセージを設定して通知
            message_list = [
                "🚨 **500 Internal Server Error 発生** 🚨",
                f"〇〇の処理でエラーが起きちゃった!テヘペロ!",
            ]
            send_error_to_slack(message_list, "danger", "システムエラー通知")

        return super().get(request, *args, **kwargs)

例えば、home/views.pyに例外処理を追加することで、エラーを感知した際に独自のエラーメッセージを作成し、Slackに通知することが可能です。

20241213_django-send-error-to-slack-11

実際のエラー通知になります。
重要な処理を監視したい場合に便利ですね!

最後に

Djangoの500エラーをSlackに通知し、トレースバックを表示する方法を解説しました。
本番環境の監視や運用の効率化にぜひ活用してください!

参考にさせて頂いたサイト様

https://www.sejuku.net/blog/74471


\ よかったらシェアしてね /

関連記事