djangoサイトでサーバーエラーをログに記録する方法


175

そのため、開発を試すときは、に設定settings.DEBUGするだけTrueでよく、エラーが発生した場合は、適切にフォーマットされ、スタックトレースとリクエスト情報が適切に表示されます。

しかし、本番サイトでは、使用してDEBUG=False、訪問者にいくつかの標準エラー500ページを表示し、現在このバグの修正に取り組んでいるという情報を示したいと思います。
同時に、すべてをログに記録する方法が欲しいです。これらの情報(スタックトレースとリクエスト情報)をサーバー上のファイルに出力します。これをコンソールに出力して、エラーのスクロールを監視したり、ログを1時間ごとにメールで送信したりすることができます。

これらの単純な要件を満たす、django-siteにはどのロギングソリューションをお勧めしますか?私はアプリケーションをfcgiサーバーとして実行しており、apache Webサーバーをフロントエンドとして使用しています(ただし、lighttpdへの移行を考えています)。




チェリアンが共有したリンクは今や死んでいる。Sentryを検索すると、有料の公式インスタンスの資料が見つかる可能性がありますが、セルフホストインスタンスを設定するためのリンクは次のとおりです。docs.sentry.io / server また、現在維持されているリポジトリは次のとおりです:github .com / getsentry / sentry
lehiester

回答:


103

ええと、DEBUG = FalseDjangoはADMINS設定にリストされている各ユーザーにエラーの完全なトレースバックを自動的にメールで送信します。これにより、ほぼ無料で通知を受け取ることができます。より細かい制御が必要な場合はprocess_exception()、発生した例外にアクセスできるという名前のメソッドを定義するミドルウェアクラスを記述して設定に追加できます。

http://docs.djangoproject.com/en/dev/topics/http/middleware/#process-exception

あなたのprocess_exception()、などなど、コンソールへの書き込みを、ファイルへの書き込み、:方法は、あなたが好きなログインのどんなタイプを実行することができます

編集:少し便利ではありませんがgot_request_exception、リクエストの処理中に例外が発生したときに送信される信号をリッスンすることもできます。

http://docs.djangoproject.com/en/dev/ref/signals/#got-request-exception

ただし、これによって例外オブジェクトにアクセスできるわけではないため、ミドルウェアメソッドを使用する方がはるかに簡単です。


7
スタックトレースをログアウトするだけの場合は、logging.exception('Some message')Pythonの標準ログモジュールをのsginalハンドラで使用すると問題なく機能することに注意してくださいgot_request_exception。つまり、トレースバックは引き続きで使用できますgot_request_exception
TM。

process_exceptionに渡された例外にスタックトレースがないようですが、それを取得する方法はありますか?
Nick BL

79

すでに述べたように、Django Sentryは良い方法ですが、(別のWebサイトとして)適切に設定するために少し作業が必要です。すべてを単純なテキストファイルに記録したい場合は、ここにログ設定を追加します。settings.py

LOGGING = {
    'version': 1,
    'disable_existing_loggers': False,
    'handlers': {
        # Include the default Django email handler for errors
        # This is what you'd get without configuring logging at all.
        'mail_admins': {
            'class': 'django.utils.log.AdminEmailHandler',
            'level': 'ERROR',
             # But the emails are plain text by default - HTML is nicer
            'include_html': True,
        },
        # Log to a text file that can be rotated by logrotate
        'logfile': {
            'class': 'logging.handlers.WatchedFileHandler',
            'filename': '/var/log/django/myapp.log'
        },
    },
    'loggers': {
        # Again, default Django configuration to email unhandled exceptions
        'django.request': {
            'handlers': ['mail_admins'],
            'level': 'ERROR',
            'propagate': True,
        },
        # Might as well log any errors anywhere else in Django
        'django': {
            'handlers': ['logfile'],
            'level': 'ERROR',
            'propagate': False,
        },
        # Your own app - this assumes all your logger names start with "myapp."
        'myapp': {
            'handlers': ['logfile'],
            'level': 'WARNING', # Or maybe INFO or DEBUG
            'propagate': False
        },
    },
}

私は同意します、私はセントリーが大好きです!私はそれの.Netポートを持ちたいです(最近.Netプロジェクトに取り組んでいます)。
Gromer

1
誰かが切り取って貼り付ける場合の小さなタイプミス:最後に「伝播」ではなく「伝播」。
user1228295 2012年

3
'include_html': True単にメールを「より良く」するだけではありません!これには、設定とローカル変数の値を含む完全なトレースバックが含まれます。ドキュメントごとのように、これはセキュリティ上の懸念がある: docs.djangoproject.com/en/1.8/topics/logging/...
トーマス

1
'disable_existing_loggers':falseがあり、このハンドラー(およびロガー)でデフォルトのdjangoロギングを複製しているだけなので、mail_adminsハンドラー(およびdjango.requestロガー)が必要かどうか知りたいです。テストしたらアップデートします。
DylanYoung

この回答を更新してください。django1.9 change-logから:Djangoのデフォルトのロギング設定は、「django.request」および「django.security」ロガーを定義しなくなりました。
narendra-choudhary 2016


30

明らかにJamesは正しいですが、例外をデータストアに記録したい場合は、いくつかのオープンソースソリューションがすでに利用可能です。

1)CrashLogは良い選択です:http ://code.google.com/p/django-crashlog/

2)Db-Logも良い選択です:http : //code.google.com/p/django-db-log/

2つの違いは何ですか?目に見えるものはほとんどないので、どちらでも十分です。

私は両方を使用しましたが、うまく機能します。


15

EMPの最も役立つコードの提出からしばらく時間が経過しました。私は今それを実装しました、manage.pyオプションでスラッシュしながらバグを追いかけようとすると、現在のバージョンのDjango(1.5。?)でrequire_debug_falseフィルターが使用できるようになるという非推奨の警告を受けましたmail_adminsハンドラーに必要です。

修正されたコードは次のとおりです。

LOGGING = {
    'version': 1,
    'disable_existing_loggers': False,
    'filters': {
         'require_debug_false': {
             '()': 'django.utils.log.RequireDebugFalse'
         }
     },
    'handlers': {
        # Include the default Django email handler for errors
        # This is what you'd get without configuring logging at all.
        'mail_admins': {
            'class': 'django.utils.log.AdminEmailHandler',
            'level': 'ERROR',
            'filters': ['require_debug_false'],
             # But the emails are plain text by default - HTML is nicer
            'include_html': True,
        },
        # Log to a text file that can be rotated by logrotate
        'logfile': {
            'class': 'logging.handlers.WatchedFileHandler',
            'filename': '/home/username/public_html/djangoprojectname/logfilename.log'
        },
    },
    'loggers': {
        # Again, default Django configuration to email unhandled exceptions
        'django.request': {
            'handlers': ['mail_admins'],
            'level': 'ERROR',
            'propagate': True,
        },
        # Might as well log any errors anywhere else in Django
        'django': {
            'handlers': ['logfile'],
            'level': 'ERROR',
            'propagate': False,
        },
        # Your own app - this assumes all your logger names start with "myapp."
        'myapp': {
            'handlers': ['logfile'],
            'level': 'DEBUG', # Or maybe INFO or WARNING
            'propagate': False
        },
    },
}

'disable_existing_loggers':falseがあり、このハンドラー(およびロガー)でデフォルトのdjangoロギングを複製しているだけなので、mail_adminsハンドラー(およびdjango.requestロガー)が必要かどうか知りたいです。テストしたらアップデートします。
DylanYoung

1

fcgiスクリプトに迷惑な問題が発生しました。ジャンゴが始まる前に発生しました。ロギングの欠如はとても痛いです。とにかく、最初のものが大いに役立ったので、stderrをファイルにリダイレクトしました。

#!/home/user/env/bin/python
sys.stderr = open('/home/user/fcgi_errors', 'a')
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.