bigywater.tech
Django · 129

生产环境 DEBUG=False 的影响

「生产环境一定要关 DEBUG」是常识,但关掉之后具体少了什么、多了什么?这篇把同一个项目在 DEBUG=True 和 False 下的 404 / 500 页面、SQL 记录、错误邮件和 runserver 的静态文件行为逐项对比。

51454 → 145 字节
同一个 500 错误:DEBUG=True 的技术页面 vs DEBUG=False 的通用页面
card_number
DEBUG=True 的 500 页面会展示局部变量,@sensitive_variables 此时也不起作用
邮件
DEBUG=False 时 500 给 ADMINS 发邮件,DEBUG=True 不发

404 / 500 页面

实测 · 本机执行输出
  DEBUG=True  不存在的路径                                   → 404  页面   2674 字节  标题: Page not found at /nope/  含 card_number 的值: False  含异常文本: False
  DEBUG=True  视图抛异常(局部变量 card_number)                  → 500  页面  51454 字节  标题: RuntimeError at /boom/  含 card_number 的值: True  含异常文本: True
  DEBUG=True  同上,@sensitive_variables("card_number")   → 500  页面  56167 字节  标题: RuntimeError at /boom_sensitive/  含 card_number 的值: True  含异常文本: True
  DEBUG=False 不存在的路径                                   → 404  页面    179 字节  标题: Not Found  含 card_number 的值: False  含异常文本: False
  DEBUG=False 视图抛异常(局部变量 card_number)                  → 500  页面    145 字节  标题: Server Error (500)  含 card_number 的值: False  含异常文本: False
  DEBUG=False 同上,@sensitive_variables("card_number")   → 500  页面    145 字节  标题: Server Error (500)  含 card_number 的值: False  含异常文本: False

DEBUG=True 的技术页面对开发很有用,但它会把源码片段、局部变量、请求信息都展示出来,对外暴露就是信息泄漏。

设置页的脱敏

实测 · 本机执行输出
  页面里有 SECRET_KEY 这个名字: True  | 含密钥原文: False  | 含 ********************: True
  页面里有「Settings」表: True  | 含 ALLOWED_HOSTS 原值: True  | 含数据库文件路径: True

Django 会把名字里有 KEY、SECRET、PASSWORD 等字样的设置脱敏,但其它设置(主机列表、路径)照样显示;局部变量更不会自动脱敏,要在 DEBUG=False 的错误报告里用 @sensitive_variables 才生效。

SQL 记录

实测 · 本机执行输出
  DEBUG=True  视图里做 50 次查询后 len(connection.queries) = 50
  DEBUG=False 视图里做 50 次查询后 len(connection.queries) = 0

DEBUG=True 时每条 SQL 都留在内存里的 connection.queries,长时间运行的进程里会一直增长(本文只量了条数,没有量内存)。

错误邮件

实测 · 本机执行输出
  DEBUG=True  /boom/             邮件数 0  主题 []  正文含 card_number 的值: False
  DEBUG=True  /boom_sensitive/   邮件数 0  主题 []  正文含 card_number 的值: False
  DEBUG=False /boom/             邮件数 1  主题 ['[Django] ERROR (EXTERNAL IP): Internal Server Er']  正文含 card_number 的值: False
  DEBUG=False /boom_sensitive/   邮件数 1  主题 ['[Django] ERROR (EXTERNAL IP): Internal Server Er']  正文含 card_number 的值: False

静态文件与 check --deploy

实测 · 本机执行输出
  runserver DEBUG=True                 GET /static/hello.txt → 200
  runserver DEBUG=False                GET /static/hello.txt → 404
  runserver DEBUG=False + --insecure   GET /static/hello.txt → 200
   [('security.W018', 'You should not have DEBUG set to True in deployment.')]

DEBUG=False 后 runserver 不再提供静态文件,生产环境本来就该由 nginx / WhiteNoise / CDN 提供(第 132 篇)。

分步演示

DEBUG=False 的影响
本步的对象

    本文用到的工具与边界

    • 本机 macOS 27 / Python 3.14.7 / Django 6.1.1(默认用 SQLite,其它数据库会在文中注明),用 django.test.Client 或真实的本机服务器进程实测;计时用 time.perf_counter,数字每次运行会有小幅抖动。SQLite;Client(raise_request_exception=False);邮件用 locmem 后端 + setup_test_environment;runserver 用 --noreload 在本机 9543 端口
    • 没有验证:自定义 404.html / 500.html 模板、HTML 版错误邮件(AdminEmailHandler 的 include_html)、Sentry 等第三方错误追踪(第 135 篇)、DEBUG=True 时 queries_log 的内存增长量、DEBUG 对模板缓存的影响(第 82 篇已测)
    京ICP备2026067502号-1京公网安备11010502063487号