Django 处理 404 的逻辑流程
Django 处理 404 的完整逻辑流程(结合自定义 NotfoundView 和 handler404 配置):
1. 用户访问 URL
- 用户在浏览器输入一个 URL,比如:
https://quillnk.com/abc/xyz
- Nginx 收到请求,转发到
uWSGI → Django。
2. Django URL 路由匹配
-
Django 根据
urls.py中的路由表,逐条尝试匹配。 -
如果没有任何路由匹配,就会触发 404 错误。
3. Django 调用 handler404
-
默认情况下,Django 会调用内置的
django.views.defaults.page_not_found,返回一个简单的404 Not Found页面。 -
但在 urls.py 里配置了:
handler404 = NotfoundView.as_error_view()
- 所以 Django 会调用你自定义的
NotfoundView。
4. 执行 NotfoundView.aserrorview() 包装函数
-
as_error_view()会把类视图NotfoundView转换成一个函数,符合 Django 要求的(request, exception)签名。 -
Django 会调用这个函数,并传入:
-
request:当前请求对象 -
exception:触发 404 的异常对象(通常用不到)
-
5. 渲染自定义 404 页面
-
NotfoundView继承自TemplateView,最终调用get_context_data()构造模板上下文:-
breadcrumbs(PC 端面包屑) -
breadcrumbs_mobile(移动端面包屑)
-
-
使用
template_name = 'blog/404.html'渲染页面。
6. 确保返回 404 状态码
- 在
wrapped_view内部:
if not isinstance(response, HttpResponseNotFound):
response.status_code = 404
- 确保返回的
HttpResponse状态码是 404。
7. 浏览器最终收到响应
-
用户看到的是 你自定义的 404 页面,而不是默认的
"Not Found"。 -
响应头中的状态码是
404,搜索引擎和前端应用可以正确识别。
完整流程总结
-
请求进来 → Nginx → uWSGI → Django
-
Django 路由表无匹配 → 触发 404
-
Django 调用
handler404→ 进入NotfoundView.as_error_view() -
NotfoundView渲染blog/404.html模板 -
返回
HttpResponse,状态码设为404 -
浏览器显示自定义 404 页面