django 1.8 官方文档翻译:6-6-5 错误报告

简介: 错误报告当你运行一个公开站点时,你应该始终关闭DEBUG 设置。这会使你的服务器运行得更快,也会防止恶意用户看到由错误页面展示的一些应用细节。

错误报告

当你运行一个公开站点时,你应该始终关闭DEBUG 设置。这会使你的服务器运行得更快,也会防止恶意用户看到由错误页面展示的一些应用细节。

但是,运行在 DEBUGFalse的情况下,你不会看到你的站点所生成的错误 – 每个人都只能看到公开的错误页面。你需要跟踪部署的站点上的错误,所以可以配置Django来生成带有错误细节的报告。

报告邮件

服务器错误

DEBUGFalse的时候,无论什么时候代码产生了未处理的异常,并且出现了服务器内部错误(HTTP状态码 500),Django 都会给ADMINS设置中的用户发送邮件。 这会向管理员提供任何错误的及时通知。 ADMINS会得到一份错误的描述,完整的Python traceback,以及HTTP请求和导致错误的详细信息。

注意

为了发送邮件,DJango需要一些设置来告诉它如何连接到邮件服务器。最起码,你需要指定 EMAIL_HOST ,可能需要 EMAIL_HOST_USEREMAIL_HOST_PASSWORD,尽管所需的其他设置可能也依赖于你的邮件服务器的配置。邮件相关设置的完整列表请见 Django设置文档

Django通常从root@localhost发送邮件。但是一些邮件提供商会拒收所有来自这个地址的邮件。修改SERVER_EMAIL设置可以使用不同的发信人地址。

将收信人的邮箱地址放入ADMINS设置中来激活这一行为。

另见

服务器错误邮件使用日志框架来发送,所以你可以通过 自定义你的日志配置自定义这一行为。

404错误

也可以配置Django来发送关于死链的邮件(404”找不到页面”错误)。Django在以下情况发送404错误的邮件:

如果符合这些条件,无论什么时候你的代码产生404错误,并且请求带有referer, Django 都会给MANAGERS中的用户发送邮件。 (It doesn’t bother to email for 404s that don’t have a referer – those are usually just people typing in broken URLs or broken Web ‘bots).

注意

BrokenLinkEmailsMiddleware 必须出现在其它拦截404错误的中间件之前,比如 LocaleMiddleware 或者 FlatpageFallbackMiddleware。把它放在你的MIDDLEWARE_CLASSES设置的最上面。

你可以通过调整IGNORABLE_404_URLS设置,告诉Django停止报告特定的404错误。它应该为一个元组,含有编译后的正则表达式对象。例如:

import re
IGNORABLE_404_URLS = (
    re.compile(r'\.(php|cgi)$'),
    re.compile(r'^/phpmyadmin/'),
)

在这个例子中,任何以.php 或者.cgi结尾URL的404错误都不会报告。任何以/phpmyadmin/开头的URL也不会。

下面的例子展示了如何排除一些浏览器或爬虫经常请求的常用URL:

import re
IGNORABLE_404_URLS = (
    re.compile(r'^/apple-touch-icon.*\.png$'),
    re.compile(r'^/favicon\.ico$'),
    re.compile(r'^/robots\.txt$'),
)

(要注意这些是正则表达式,所以需要在句号前面添加反斜线来对它转义。)

如果你打算进一步自定义django.middleware.common.BrokenLinkEmailsMiddleware 的行为(比如忽略来自web爬虫的请求),你应该继承它并覆写它的方法。

另见

404错误使用日志框架来记录。通常,日志记录会被忽略,但是你可以通过编写合适的处理器和配置日志,将它们用于错误报告。

过滤错误报告

过滤敏感的信息

错误报告对错误的调试及其有用,所以对于这些错误,通常它会尽可能多的记录下相关信息。例如,通常DJango会为产生的异常记录完整的tracebacktraceback 帧的每个局部变量,以及HttpRequest属性

然而,有时特定的消息类型十分敏感,并不适合跟踪消息,比如用户的密码或者信用卡卡号。所以Django提供一套函数装饰器,来帮助你控制需要在生产环境(也就是DEBUGFalse的情况)中的错误报告中过滤的消息:sensitive_variables()sensitive_post_parameters()

sensitive_variables(*variables)[source]

如果你的代码中一个函数(视图或者常规的回调)使用可能含有敏感信息的局部变量,你可能需要使用sensitive_variables 装饰器,来阻止错误报告包含这些变量的值。

from django.views.decorators.debug import sensitive_variables

@sensitive_variables('user', 'pw', 'cc')
def process_info(user):
    pw = user.pass_word
    cc = user.credit_card_number
    name = user.name
    ...

在上面的例子中,user, pwcc 变量的值会在错误报告中隐藏并且使用星号(****) 来代替,虽然name 变量的值会公开。

要想有顺序地在错误报告中隐藏一个函数的所有局部变量,不要向sensitive_variables 装饰器提供任何参数:

@sensitive_variables()
def my_function():
    ...

使用多个装饰器的时候

如果你想要隐藏的变量也是一个函数的参数(例如,下面例子中的user),并且被装饰的函数有多个装饰器,你需要确保将@sensitive_variables 放在装饰器链的顶端。这种方法也会隐藏函数参数,尽管它通过其它装饰器传递:

@sensitive_variables('user', 'pw', 'cc')
@some_decorator
@another_decorator
def process_info(user):
    ...

sensitive_post_parameters(*parameters)[source]

如果你的代码中一个视图接收到了可能带有敏感信息的,带有POST 参数HttpRequest对象,你可能需要使用sensitive_post_parameters  装饰器,来阻止错误报告包含这些参数的值。

from django.views.decorators.debug import sensitive_post_parameters

@sensitive_post_parameters('pass_word', 'credit_card_number')
def record_user_profile(request):
    UserProfile.create(user=request.user,
                       password=request.POST['pass_word'],
                       credit_card=request.POST['credit_card_number'],
                       name=request.POST['name'])
    ...

在上面的例子中,pass_wordcredit_card_number POST参数的值会在错误报告中隐藏并且使用星号(****) 来代替,虽然name变量的值会公开。

要想有顺序地在错误报告中隐藏一个请求的所有POST 参数,不要向sensitive_post_parameters  装饰器提供任何参数:

@sensitive_post_parameters()
def my_view(request):
    ...

所有POST参数按顺序被过滤出特定django.contrib.auth.views 视图的错误报告(login, password_reset_confirm, password_change, add_viewauth中的user_change_password),来防止像是用户密码这样的敏感信息的泄露。

自定义错误报告

所有sensitive_variables()  和 sensitive_post_parameters()分别用敏感变量的名字向被装饰的函数添加注解,以及用POST敏感参数的名字向HttpRequest对象添加注解,以便在错误产生时可以随后过滤掉报告中的敏感信息。Django的默认错误包告过滤器django.views.debug.SafeExceptionReporterFilter会完成实际的过滤操作。
产生错误报告的时候,这个过滤器使用装饰器的注解来将相应的值替换为星号 (****) 。如果你希望为你的整个站点覆写或自定义这一默认的属性,你需要定义你自己的过滤器类,并且通过DEFAULT_EXCEPTION_REPORTER_FILTER 设置来让Django使用它。

DEFAULT_EXCEPTION_REPORTER_FILTER = 'path.to.your.CustomExceptionReporterFilter'

你也可能会以更精细的方式来控制在提供的视图中使用哪种过滤器,通过设置 HttpRequestexception_reporter_filter属性。

def my_view(request):
    if request.user.is_authenticated():
        request.exception_reporter_filter = CustomExceptionReporterFilter()
    ...

你的自定义过滤器类需要继承自 django.views.debug.SafeExceptionReporterFilter,并且可能需要覆写以下方法:

class SafeExceptionReporterFilter[source]

SafeExceptionReporterFilter.``is_active(request)[source]

如果其它方法中操作的过滤器已激活,返回True。如果 DEBUGFalse,通常过滤器是激活的。

SafeExceptionReporterFilter.``get_request_repr(request)

Returns the representation string of the request object, that is, the value that would be returned by repr(request), except it uses the filtered dictionary of POST parameters as determined by SafeExceptionReporterFilter.get_post_parameters().

SafeExceptionReporterFilter.``get_post_parameters(request)[source]

返回过滤后的POST参数字典。通常它会把敏感参数的值以星号 (****)替换。

SafeExceptionReporterFilter.``get_traceback_frame_variables(request, tb_frame)[source]

返回过滤后的,所提供traceback帧的局部变量的字典。通常它会把敏感变量的值以星号 (****)替换。

另见

你也可以通过编写自定义的exception middleware来建立自定义的错误报告。如果你编写了自定义的错误处理器,模拟Django内建的错误处理器,只在DEBUGFalse时报告或记录错误是个好主意。

译者:Django 文档协作翻译小组,原文:Tracking code errors by email

本文以 CC BY-NC-SA 3.0 协议发布,转载请保留作者署名和文章出处。

Django 文档协作翻译小组人手紧缺,有兴趣的朋友可以加入我们,完全公益性质。交流群:467338606。

相关实践学习
日志服务之使用Nginx模式采集日志
本文介绍如何通过日志服务控制台创建Nginx模式的Logtail配置快速采集Nginx日志并进行多维度分析。
相关文章
|
算法 调度 Python
django 1.8 官方文档翻译: 3-1-1 URL调度器
URL调度器 简洁、优雅的URL 模式在高质量的Web 应用中是一个非常重要的细节。Django 允许你任意设计你的URL,不受框架束缚。
880 0
|
API Python 调度
django 1.8 官方文档翻译: 3-4-1 基于类的视图
基于类的视图 视图是一个可调用对象,它接收一个请求然后返回一个响应。这个可调用对象可以不只是函数,Django 提供一些可以用作视图的类。
752 0
|
前端开发 Python
django 1.8 官方文档翻译: 3-4-3 使用基于类的视图处理表单
使用基于类的视图处理表单 表单的处理通常有3 个步骤: 初始的的GET (空白或预填充的表单) 带有非法数据的POST(通常重新显示表单和错误信息) 带有合法数据的POST(处理数据并重定向) 你自己实现这些功能经常导致许多重复的样本代码(参见在视图中使用表单)。
920 0
|
Python 网络架构 前端开发
django 1.8 官方文档翻译: 3-2-1 内建的视图
内建的视图 有几个Django 的内建视图在编写视图 中讲述,文档的其它地方也会有所讲述。 开发环境中的文件服务器 static.serve(request, path, document_root, show_indexes=False) 在本地的开发环境中,除了你的项目中的静态文件,可能还有一些文件,出于方便,你希望让Django 来作为服务器。
1048 0
|
缓存 Python 安全
django 1.8 官方文档翻译: 3-1-4 视图装饰器
视图装饰器 Django为视图提供了数个装饰器,用以支持相关的HTTP服务。 允许的HTTP 方法 django.views.decorators.http 包里的装饰器可以基于请求的方法来限制对视图的访问。
963 0
|
Web App开发 缓存 安全
django 1.8 官方文档翻译: 3-6-2 内建的中间件
Django 文档协作翻译小组人手紧缺,有兴趣的朋友可以加入我们,完全公益性质。 交流群:467338606 网站:http://python.usyiyi.cn/django/index.html 中间件 这篇文档介绍了Django自带的所有中间件组件。
1211 0
|
Python
django 1.8 官方文档翻译: 4-2-4 人性化
Django 文档协作翻译小组人手紧缺,有兴趣的朋友可以加入我们,完全公益性质。 交流群:467338606 网站:http://python.usyiyi.cn/django/index.html django.contrib.humanize 一系列Django的模板过滤器,有助于向数据添加“人文关怀”。
774 0
|
数据库 Python 开发者
django 1.8 官方文档翻译: 3-4-2 内建显示视图
Django 文档协作翻译小组人手紧缺,有兴趣的朋友可以加入我们,完全公益性质。 交流群:467338606 网站:http://python.usyiyi.cn/django/index.html 基于类的内建通用视图 编写Web应用可能是单调的,因为你需要不断的重复某一种模式。
734 0
|
中间件 Python
django 1.8 官方文档翻译: 3-6-1 中间件概览
Django 文档协作翻译小组人手紧缺,有兴趣的朋友可以加入我们,完全公益性质。 交流群:467338606 网站:http://python.usyiyi.cn/django/index.html 中间件 中间件是一个介入Django的请求和响应的处理过程中的钩子框架。
1027 2
|
SQL 测试技术 数据库
django 1.8 官方文档翻译: 2-6-3 提供初始数据
Django 文档协作翻译小组人手紧缺,有兴趣的朋友可以加入我们,完全公益性质。 交流群:467338606 网站:http://python.usyiyi.cn/django/index.html 为模型提供初始数据 当你首次建立一个应用的时候,为你的数据库预先安装一些硬编码的数据,是很有用处的。
995 0