Nginx的auth_request模块不执行鉴权,而是通过子请求将决策权交由外部服务:返回200即放行,401/403则拦截;需配置internal保护/auth入口、关闭请求体传输、透传X-Original-URI/Authorization等头,并用auth_request_set提取响应头供后端使用。

Nginx 的 auth_request 模块不是自己做鉴权,而是把“能不能进”这个决定权,交给一个你指定的外部服务。它发起一次内部子请求(subrequest),等那个服务返回 200 就放行,返回 401 或 403 就直接拦住——整个过程对原始请求透明,也不碰业务代码。
核心就三点:转发、判断、透传。
必须声明 internal 的认证入口
比如你写了个 /auth 接口供 Nginx 调用,它必须被标记为内部地址:
location = /auth {
internal;
proxy_pass http://auth-service;
proxy_pass_request_body off;
proxy_set_header Content-Length "";
proxy_set_header X-Original-URI $request_uri;
proxy_set_header X-Original-Method $request_method;
proxy_set_header Authorization $http_authorization;
}-
internal是安全底线:没有它,攻击者可以直接curl GET /auth?user=a&pwd=b爆破或探测。 - 关掉请求体(
proxy_pass_request_body off)是常规做法,除非你的认证服务明确需要解析原始 body。 -
X-Original-*和Authorization这些头,是让认证服务知道“谁、想访问哪、用什么凭证”。
在目标接口启用 auth_request
要保护某个路径,只需加一行指令:
location /api/ {
auth_request /auth;
proxy_pass http://backend;
}- 请求打到
/api/xxx,Nginx 会先悄悄发个子请求去/auth。 - 只有
/auth返回 200,才会继续把原请求转发给后端。 - 如果返回 401,Nginx 默认返回 401;你也可以用
error_page 401 =302 /login自动跳转。
提取并透传用户身份信息
认证服务验证通过后,可以在响应头里附带信息,比如:
HTTP/1.1 200 OK X-Auth-User: alice X-Auth-Groups: dev,admin
Nginx 能用 auth_request_set 拿到这些值:
auth_request_set $user $upstream_http_x_auth_user; auth_request_set $groups $upstream_http_x_auth_groups; proxy_set_header X-User $user; proxy_set_header X-Groups $groups;
后端服务就能直接读这些 header 做审计、路由或二次校验,不用再自己解析 token 或查 LDAP。
认证服务该做什么
Nginx 不管你怎么验,只认状态码。所以你的 /auth 后端要完成这些事:
- 解析
Authorization头(Bearer token)、Cookie 或自定义凭证 - 对接 LDAP(bind 验证、组查询)、OAuth2 introspect、JWT 解析、Keycloak 校验等
- 判断权限(比如
/api/admin/要求admin角色) - 成功返回 200 + 用户相关 header;失败返回 401(未登录)或 403(无权限)
常见实现方式包括:
- 用 Flask/FastAPI 写轻量
/auth接口 - 复用 nginx-auth-ldap 这类现成 daemon
- 直接对接 Keycloak 的
/token/introspect或 IDaaS 的校验端点
不复杂但容易忽略

















