中间件

本文档解释了Django附带的所有中间件组件。有关如何使用它们以及如何编写自己的中间件的信息,请参见 middleware usage guide .

可用中间件

缓存中间件

class UpdateCacheMiddleware[源代码]
class FetchFromCacheMiddleware[源代码]

启用站点范围的缓存。如果启用了这些,则只要 CACHE_MIDDLEWARE_SECONDS 设置定义。见 cache documentation .

“通用”中间件

class CommonMiddleware[源代码]

为完美主义者增加了一些便利:

  • 禁止访问中的用户代理 DISALLOWED_USER_AGENTS 设置,它应该是已编译正则表达式对象的列表。

  • 基于执行URL重写 APPEND_SLASHPREPEND_WWW 设置。

    如果 APPEND_SLASHTrue 初始URL没有以斜杠结尾,并且在urlconf中找不到它,然后在末尾附加斜杠来形成新的URL。如果在urlconf中找到这个新的url,那么django会将请求重定向到这个新的url。否则,初始URL会像往常一样被处理。

    例如, foo.com/bar 将被重定向到 foo.com/bar/ 如果没有有效的URL模式 foo.com/bar 但是 do 具有有效的模式 foo.com/bar/ .

    如果 PREPEND_WWWTrue ,缺少前导“www.”的URL将被重定向到具有前导“www”的同一URL。

    这两个选项都是为了规范化URL。其原理是每个URL都应该存在于一个且只有一个的地方。技术上是一个URL foo.com/bar 不同于 foo.com/bar/ --搜索引擎索引器将它们视为单独的URL——所以规范化URL是最佳实践。

  • 设置 Content-Length 非流式响应的头。

CommonMiddleware.response_redirect_class

默认为 HttpResponsePermanentRedirect . 子类 CommonMiddleware 并重写该属性以自定义中间件发出的重定向。

class BrokenLinkEmailsMiddleware[源代码]

GZIP中间件

class GZipMiddleware[源代码]

警告

安全研究人员最近发现,当压缩技术(包括 GZipMiddleware )在一个网站上使用时,该网站可能会受到一些可能的攻击。使用前 GZipMiddleware 在您的网站上,您应该非常仔细地考虑您是否受到这些攻击。如果你在 any 怀疑你是否受到影响,你应该避免使用 GZipMiddleware . 有关详细信息,请参阅 the BREACH paper (PDF)breachattack.com .

压缩理解gzip压缩(所有现代浏览器)的浏览器的内容。

这个中间件应该放在任何其他需要读取或写入响应体的中间件之前,以便随后进行压缩。

如果以下任何一项为真,则不会压缩内容:

  • 内容正文的长度小于200字节。
  • 响应已设置 Content-Encoding 标题。
  • 请求(浏览器)未发送 Accept-Encoding 包含标题 gzip .

如果响应有 ETag 头段,ETag变弱以符合 RFC 7232#section-2.1 .

您可以使用 gzip_page() 装饰符。

条件获取中间件

class ConditionalGetMiddleware[源代码]

处理条件获取操作。如果响应没有 ETag 头,如果需要,中间件会添加一个。如果响应有 ETagLast-Modified 头,请求 If-None-MatchIf-Modified-Since ,响应被替换为 HttpResponseNotModified .

本地中间件

class LocaleMiddleware[源代码]

基于请求中的数据启用语言选择。它为每个用户定制内容。见 internationalization documentation .

LocaleMiddleware.response_redirect_class

默认为 HttpResponseRedirect . 子类 LocaleMiddleware 并重写该属性以自定义中间件发出的重定向。

消息中间件

class MessageMiddleware[源代码]

启用基于cookie和会话的消息支持。见 messages documentation .

安全中间件

警告

如果部署情况允许,通常最好让前端Web服务器执行 SecurityMiddleware . 这样,如果存在Django不提供服务的请求(例如静态媒体或用户上载的文件),它们将具有与Django应用程序请求相同的保护。

class SecurityMiddleware[源代码]

这个 django.middleware.security.SecurityMiddleware 为请求/响应周期提供了几个安全增强。每个都可以通过一个设置单独启用或禁用。

HTTP严格传输安全

对于只能通过https访问的站点,可以通过设置 "Strict-Transport-Security" header . 这减少了您受到一些中间层(MITM)的SSL剥离攻击的风险。

SecurityMiddleware 如果设置 SECURE_HSTS_SECONDS 设置为非零整数值。

启用HST时,最好先使用较小的值进行测试,例如, SECURE_HSTS_SECONDS = 3600 一个小时。每次Web浏览器从您的站点看到HSTS头,它都会拒绝在给定的时间段内与您的域进行不安全的通信(使用HTTP)。一旦您确认所有资产在您的网站上得到安全服务(即HST没有破坏任何东西),最好增加此值,以保护不经常访问的用户(通常为31536000秒,即1年)。

此外,如果设置 SECURE_HSTS_INCLUDE_SUBDOMAINS 设置为 TrueSecurityMiddleware 将添加 includeSubDomains 指示 Strict-Transport-Security 标题。建议这样做(假设所有子域都是以https的方式提供服务的),否则您的站点仍然可能由于与子域的不安全连接而受到攻击。

如果您希望将站点提交到 browser preload list 设置 SECURE_HSTS_PRELOAD 设置为 True . 它附加了 preload 指示 Strict-Transport-Security 标题。

警告

HSTS策略适用于整个域,而不仅仅是设置头的响应的URL。因此,仅当整个域仅通过HTTPS提供服务时才应使用它。

正确遵守hsts头的浏览器将拒绝允许用户绕过警告并连接到具有过期、自签名或其他无效SSL证书的站点。如果您使用HST,请确保您的证书状态良好,并保持这种状态!

注解

如果部署在负载均衡器或反向代理服务器之后,并且 Strict-Transport-Security 没有将头添加到响应中,这可能是因为Django没有意识到它在安全连接上;您可能需要设置 SECURE_PROXY_SSL_HEADER 设置。

X-Content-Type-Options: nosniff

一些浏览器将尝试猜测其获取的资产的内容类型,覆盖 Content-Type 标题。虽然这有助于显示服务器配置不正确的站点,但也可能带来安全风险。

如果你的网站提供用户上传的文件,恶意用户可以上传一个精心制作的文件,当你期望它是无害的时,浏览器会将其解释为HTML或javascript。

为了防止浏览器猜测内容类型并强制它始终使用 Content-Type 头,你可以通过 X-Content-Type-Options: nosniff 标题。 SecurityMiddleware 如果 SECURE_CONTENT_TYPE_NOSNIFF 设置是 True .

请注意,在大多数部署情况下,Django不参与为用户上载的文件提供服务,此设置不会帮助您。例如,如果 MEDIA_URL 直接由前端Web服务器(nginx、apache等)提供服务,然后您需要在这里设置这个头文件。另一方面,如果您正在使用django执行诸如需要授权才能下载文件之类的操作,并且无法使用Web服务器设置头,则此设置将非常有用。

X-XSS-Protection: 1; mode=block

有些浏览器能够阻止似乎是 XSS attack . 它们通过在页面的get或post参数中查找javascript内容来工作。如果在服务器的响应中重播javascript,则会阻止页面呈现,并显示错误页面。

这个 X-XSS-Protection header 用于控制XSS筛选器的操作。

要在浏览器中启用XSS过滤器并强制它始终阻止可疑的XSS攻击,可以通过 X-XSS-Protection: 1; mode=block 标题。 SecurityMiddleware 如果 SECURE_BROWSER_XSS_FILTER 设置是 True .

警告

浏览器XSS过滤器是一种有用的防御措施,但不能完全依赖于它。它无法检测所有的XSS攻击,并且不是所有的浏览器都支持头部。确保你还在 validating and sanitizing 防止XSS攻击的所有输入。

SSL重定向

如果您的站点同时提供HTTP和HTTPS连接,那么默认情况下,大多数用户最终都会得到一个不安全的连接。为了获得最佳安全性,您应该将所有HTTP连接重定向到HTTPS。

如果你设置 SECURE_SSL_REDIRECT 设置为真, SecurityMiddleware 将永久(HTTP 301)重定向所有HTTP连接到HTTPS。

注解

出于性能原因,最好在Django之外、前端负载均衡器或反向代理服务器(如 nginx . SECURE_SSL_REDIRECT 用于不可选择的部署情况。

如果 SECURE_SSL_HOST 设置有一个值,所有重定向都将发送到该主机,而不是最初请求的主机。

如果您的站点上有几个页面应该可以通过HTTP访问,而不是重定向到HTTPS,则可以列出正则表达式以匹配 SECURE_REDIRECT_EXEMPT 设置。

注解

如果您部署在负载均衡器或反向代理服务器之后,Django似乎无法确定请求何时已经安全,则可能需要设置 SECURE_PROXY_SSL_HEADER 设置。

会话中间件

class SessionMiddleware[源代码]

启用会话支持。见 session documentation .

站点中间件

class CurrentSiteMiddleware[源代码]

添加 site 表示当前站点到每个传入站点的属性 HttpRequest 对象。见 sites documentation .

身份验证中间件

class AuthenticationMiddleware

添加 user 属性,表示当前登录的用户,指向每个传入的 HttpRequest 对象。见 Authentication in Web requests .

class RemoteUserMiddleware

使用Web服务器提供的身份验证的中间件。见 身份验证使用 REMOTE_USER 有关用法的详细信息。

class PersistentRemoteUserMiddleware

当仅在登录页面上启用时,用于使用Web服务器的中间件提供了身份验证。见 使用 REMOTE_USER 仅在登录页上 有关用法的详细信息。

CSRF保护中间件

class CsrfViewMiddleware[源代码]

通过将隐藏的表单字段添加到发布表单并检查请求的正确值,添加对跨站点请求伪造的保护。见 Cross Site Request Forgery protection documentation .

X-Frame-Options 中间件

class XFrameOptionsMiddleware[源代码]

简单的 clickjacking protection via the X-Frame-Options header .

中间件排序

以下是有关各种django中间件类排序的一些提示:

  1. SecurityMiddleware

    如果您要打开SSL重定向,那么应该接近列表的顶部,因为这样可以避免运行其他一些不必要的中间件。

  2. UpdateCacheMiddleware

    在那些修改 Vary 页眉 (SessionMiddlewareGZipMiddlewareLocaleMiddleware

  3. GZipMiddleware

    在任何可能更改或使用响应主体的中间件之前。

    UpdateCacheMiddleware 修改 Vary 标题。

  4. SessionMiddleware

    在任何可能引发异常以触发错误视图的中间件(例如 PermissionDenied )如果你在使用 CSRF_USE_SESSIONS .

    UpdateCacheMiddleware 修改 Vary 标题。

  5. ConditionalGetMiddleware

    在任何可能更改响应的中间件之前(它设置 ETag 标题)。

    GZipMiddleware 所以它不能计算 ETag gzip内容的标题。

  6. LocaleMiddleware

    最上面的一个,之后 SessionMiddleware (使用会话数据)和 UpdateCacheMiddleware (修改 Vary 标题)。

  7. CommonMiddleware

    在任何可能更改响应的中间件之前(它设置 Content-Length 标题)。以前出现的中间件 CommonMiddleware 并更改响应必须重置 Content-Length .

    接近顶部:当 APPEND_SLASHPREPEND_WWW 设置为 True .

    SessionMiddleware 如果你在用 CSRF_USE_SESSIONS .

  8. CsrfViewMiddleware

    在任何假设已经处理了CSRF攻击的视图中间件之前。

    SessionMiddleware 如果你在用 CSRF_USE_SESSIONS .

  9. AuthenticationMiddleware

    SessionMiddleware :使用会话存储。

  10. MessageMiddleware

    SessionMiddleware :可以使用基于会话的存储。

  11. FetchFromCacheMiddleware

    在任何修改 Vary header:这个header用于为缓存哈希键选择一个值。

  12. FlatpageFallbackMiddleware

    应该接近底部,因为它是中间件的最后一种手段。

  13. RedirectFallbackMiddleware

    应该接近底部,因为它是中间件的最后一种手段。