---
title: "使用 REMOTE_USER 进行身份验证"
version: 6.1
locale: zh-hans
source: https://docs.djangoproject.com/zh-hans/6.1/howto/auth-remote-user/
canonical: https://djangodocs.dev/zh-hans/6.1/howto/auth-remote-user/
---
# 使用 `REMOTE_USER` 进行身份验证

This document describes how to make use of external authentication sources in
your Django applications. This type of authentication solution is typically
seen on intranet sites, with single sign-on solutions such as IIS and
Integrated Windows Authentication or Apache and [mod\_authnz\_ldap](https://httpd.apache.org/docs/current/mod/mod_authnz_ldap.html), [CAS](https://www.apereo.org/projects/cas),
[WebAuth](https://uit.stanford.edu/service/authentication), [mod\_auth\_sspi](https://sourceforge.net/projects/mod-auth-sspi), etc.

When the web server takes care of authentication it typically provides the
authenticated user as `REMOTE_USER`. In Django, this value is made available
in [`request.META`](/zh-hans/6.1/ref/request-response/#django.http.HttpRequest.META) (as `REMOTE_USER` when
supplied as an environment variable, as in WSGI, or `HTTP_REMOTE_USER` when
supplied via an HTTP header, as in ASGI). Django can be configured to make use
of the `REMOTE_USER` value using the `RemoteUserMiddleware` or
`PersistentRemoteUserMiddleware`, and
[`RemoteUserBackend`](/zh-hans/6.1/ref/contrib/auth/#django.contrib.auth.backends.RemoteUserBackend) classes found in
[`django.contrib.auth`](/zh-hans/6.1/topics/auth/#module-django.contrib.auth).

## 配置

首先，你需要向配置文件的 [`MIDDLEWARE`](/zh-hans/6.1/ref/settings/#std-setting-MIDDLEWARE) 键中，在 [`django.contrib.auth.middleware.AuthenticationMiddleware`](/zh-hans/6.1/ref/middleware/#django.contrib.auth.middleware.AuthenticationMiddleware) 的 **后面** 添加 [`django.contrib.auth.middleware.RemoteUserMiddleware`](/zh-hans/6.1/ref/middleware/#django.contrib.auth.middleware.RemoteUserMiddleware)：

```
MIDDLEWARE = [
    "...",
    "django.contrib.auth.middleware.AuthenticationMiddleware",
    "django.contrib.auth.middleware.RemoteUserMiddleware",
    "...",
]
```

然后，你需要将设置中的 [`AUTHENTICATION_BACKENDS`](/zh-hans/6.1/ref/settings/#std-setting-AUTHENTICATION_BACKENDS) setting 键值由 [`ModelBackend`](/zh-hans/6.1/ref/contrib/auth/#django.contrib.auth.backends.ModelBackend) 替换为 [`RemoteUserBackend`](/zh-hans/6.1/ref/contrib/auth/#django.contrib.auth.backends.RemoteUserBackend)：

```
AUTHENTICATION_BACKENDS = [
    "django.contrib.auth.backends.RemoteUserBackend",
]
```

With this setup, `RemoteUserMiddleware` will detect the username in
`request.META['REMOTE_USER']` (or `request.META['HTTP_REMOTE_USER']` under
ASGI) and will authenticate and auto-login that user
using the [`RemoteUserBackend`](/zh-hans/6.1/ref/contrib/auth/#django.contrib.auth.backends.RemoteUserBackend).

要注意这项设置将导致无法使用默认的 `ModelBackend` 验证。也就是说如果 `REMOTE_USER` 的值没有指定则该用户将无法登录，即使通过 Django 的管理后台。要解决这些问题，把 `'django.contrib.auth.backends.ModelBackend'` 加入 `AUTHENTICATION_BACKENDS` 列表中，则当 `REMOTE_USER` 未指定时，就会回退使用 `ModelBackend`。

Django 的用户管理系统，比如 `contrib.admin` 中的视图函数及 [`createsuperuser`](/zh-hans/6.1/ref/django-admin/#django-admin-createsuperuser) 的管理命令，都没有与远程用户集成。这些接口只工作在数据库中存储的用户上，无论 `AUTHENTICATION_BACKENDS` 为何值。

> **Note**
>
> 因为 `RemoteUserBackend` 继承自 `ModelBackend`, 您仍将拥有在  `ModelBackend` 中实现的所有相同的权限检查。
>
> 具有 [`is_active=False`](/zh-hans/6.1/ref/contrib/auth/#django.contrib.auth.models.User.is_active) 的用户将被禁止验证。你可以使用 [`AllowAllUsersRemoteUserBackend`](/zh-hans/6.1/ref/contrib/auth/#django.contrib.auth.backends.AllowAllUsersRemoteUserBackend) 来允许验证。

如果你的认证机制使用自定义 HTTP 头而非 `REMOTE_USER`，你可以继承 `RemoteUserMiddleware` 并将 `header` 属性设为所需的 `request.META` 键名。例如：

*`mysite/middleware.py`*

```python
 from django.contrib.auth.middleware import RemoteUserMiddleware

 class CustomHeaderRemoteUserMiddleware(RemoteUserMiddleware):
     header = "HTTP_AUTHUSER"
```

这个自定义中间件随后将在 [`MIDDLEWARE`](/zh-hans/6.1/ref/settings/#std-setting-MIDDLEWARE) 设置中替代 [`django.contrib.auth.middleware.RemoteUserMiddleware`](/zh-hans/6.1/ref/middleware/#django.contrib.auth.middleware.RemoteUserMiddleware) 被使用：

```
MIDDLEWARE = [
    "...",
    "django.contrib.auth.middleware.AuthenticationMiddleware",
    "mysite.middleware.CustomHeaderRemoteUserMiddleware",
    "...",
]
```

> **Warning**
>
> `RemoteUserMiddleware` must not be deployed in configurations where a
> client can supply the header. You must be sure that your web server or
> reverse proxy always sets or strips that header based on the appropriate
> authentication checks, never permitting an end user to submit a fake (or
> "spoofed") header value.
>
> Since the HTTP headers `X-Auth-User` and `X-Auth_User` (for example)
> both normalize to the `HTTP_X_AUTH_USER` key in `request.META`, you
> must also check that your web server doesn't allow a spoofed header using
> underscores in place of dashes.
>
> Under WSGI, this warning doesn't apply to `RemoteUserMiddleware` in its
> default configuration with `header = "REMOTE_USER"`, since a key that
> doesn't start with `HTTP_` in `request.META` can only be set by your
> WSGI server, not directly from an HTTP request header.
>
> This warning applies under ASGI in all configurations, because there is
> no equivalent for a WSGI server's ability to place a trusted value in the
> environ. ASGI deployments *must* use a reverse proxy as described above
> when using this middleware.

如果你需要更多控制, 你可以通过继承 [`RemoteUserBackend`](/zh-hans/6.1/ref/contrib/auth/#django.contrib.auth.backends.RemoteUserBackend)  并且覆盖其一个或多个属性和方法来创建你自己的验证后端.

## 仅在登录界面使用 `REMOTE_USER`

`RemoteUserMiddleware` 这个认证中间件 ，它假设HTTP请求的头部 `REMOTE_USER` 在所有认证请求中都存在。这个假设在当通过 `htpasswd` 或者相似的认证机制来做Basic HTTP的认证时才是可行的，但是使用Negotiate (GSSAPI/Kerberos) 或者其它资源密集型的认证方法时就说不过去了，前端HTTP server的认证通常用在仅仅一个或不太多的登录URLs，而且在认证成功后，应用还要自己去维护这个session。

[`PersistentRemoteUserMiddleware`](/zh-hans/6.1/ref/middleware/#django.contrib.auth.middleware.PersistentRemoteUserMiddleware) 就针对这个使用场景提供了支持。除非用户显式地退出登录，它将一直保留已认证的会话。这个中间件可以代替上文中的 [`RemoteUserMiddleware`](/zh-hans/6.1/ref/middleware/#django.contrib.auth.middleware.RemoteUserMiddleware)。
