Prometheus、Alertmanager 这类系统天生缺乏完善的登录功能,一旦把地址暴露在内网,任何人都能肆无忌惮地查看全部数据,甚至能在 Alertmanager 里随意静默告警。面对这种无法原生支持 OIDC 或 SAML 的“裸奔”系统,authentik 统一身份认证 给出了它的杀手锏:代理认证(Proxy Authentication)。
它就像是在这些系统前面强行立了一道“防盗门”:员工在防盗门外依然可以通过飞书流畅扫码,而防盗门内的系统甚至完全不知道 authentik 的存在,一行代码都不用改。
本篇我们将拆解代理认证的三种部署模式、Nginx 的 auth_request 究竟是如何与 authentik 配合的,以及那些最容易被忽略、极易导致防盗门形同虚设的安全前提。内容基于 authentik 2026.8 的官方文档。
TL;DR
- 代理认证只管“能不能进”:不管进去之后能做什么。需要区分角色的系统优先用 OIDC。
- 已有 Nginx 就选 Forward auth (single application):配合内置 outpost,不用额外部署组件;记得把应用加到内置 outpost 上。
- 门禁在 Nginx 上:Nginx 用
auth_request问 outpost 放不放行,前提是后端只能经由 Nginx 访问。 - 后端信任的用户信息头只能由 Nginx 设置:不要删改官方模板里覆盖
X-authentik-*头的配置。 - 服务器之间的调用不要走代理认证:Grafana 查 Prometheus 用内网地址直连。
Table of contents
Open Table of contents
1. 代理认证解决什么问题
它的核心任务非常明确:在那些完全没有登录功能的系统面前,强行立一道必须验证身份的防盗门。员工想要访问,必须先被引导到 authentik 走完登录流程并验证应用绑定权限,通过后才能看到页面。
切记:它只管“能不能进”,不管“进去之后能干嘛”。 以 Prometheus 为例,它本来就没有角色概念,经过代理认证放行的人,全都是一样的权限。如果你的系统需要区分“管理员 / 只读用户”,请务必优先使用 OIDC。
2. 部署的三种模式
代理认证支持三种模式,适用于不同的网络拓扑:
| 模式 | 流量怎么走 | 适用场景 |
|---|---|---|
| Proxy | authentik Outpost 自己充当反向代理服务器,直接把流量转给后端。 | 极其简单的单机部署,前面没有挂 Nginx 等反向代理时。 |
| Forward Auth (Single App) | 现有的 Nginx 继续做反向代理,但在转发每个请求前,先发个子请求去问 Outpost 能不能放行。 | 企业最常用。每个应用可以单独在后台配置访问规则。 |
| Forward Auth (Domain Level) | 机制同上,但 authentik 里只配一个 Provider 来保护同一父域名下的所有应用。 | 偷懒做法。缺点是你无法给不同应用配置不同的访问规则。 |
实战建议:在企业架构里,几乎总是有现成的 Nginx/Ingress。因此闭眼选 Forward Auth (Single App),并配合跑在 Server 里的内置 Outpost(Embedded Outpost),连额外的组件都不用部署。 唯一的踩坑点是:创建完 Provider 和 Application 后,记得去 Outposts 页面,把新应用挂载到内置的 Outpost 上,否则你访问时只会得到一个“找不到应用”的无情报错。
3. 访问时到底发生了什么
在 Forward Auth 模式下,真正的“门卫”其实是 Nginx,而 authentik 只是“裁判”:
一句话总结:门禁卡卡在 Nginx 上,Outpost 只负责回答“Yes or No”。
Nginx 侧靠的是 auth_request 模块:每收到一个请求,它会先扣下不发,而是向 /outpost.goauthentik.io/auth/nginx 发送一个子请求。如果 Outpost 返回 2xx(验证通过),Nginx 就放行流量到 Prometheus;如果返回 401,Nginx 就把用户强行重定向去登录。auth_request 的底层机制可以对照 Nginx 配置实践,具体的配置片段请务必直接抄官方文档的模板。
有意思的是,代理认证内部其实也是在跑 OIDC 协议。你可以把 Outpost 理解为 authentik 内部的一个隐藏 OIDC 客户端,只是这一切对 Prometheus 完全透明。
4. Nginx 传给后端的“小抄”
验证通过后,Nginx 会把用户信息以 HTTP Header 的形式附加在请求里发给后端:
| 请求头 | 里面装了什么 |
|---|---|
X-authentik-username | 用户名 |
X-authentik-email | 邮箱地址 |
X-authentik-name | 用户姓名 |
X-authentik-groups | 所属组的列表,用竖线(|)分隔 |
X-authentik-entitlements | 在这个应用里的特有权益,竖线分隔 |
X-authentik-uid | 用户 ID 的哈希值 |
有些系统其实是有登录功能的,并且支持“按 HTTP Header 自动登录”(例如 Grafana 的 Auth Proxy 模式)。你可以利用代理认证直接把用户名和组传过去,实现免密免扫码直接进系统。当然,如果那个系统同时支持 OIDC,还是那句话:能用 OIDC 就用 OIDC。
5. 防盗门不要建在旷野上(安全要点)
代理认证是最容易在网络配置上漏风的一种协议,下面这几条原则千万不能破:
- 后端必须“只认 Nginx”。 代理认证仅仅保护那些经过 Nginx的流量。如果你的 Prometheus 监听了
0.0.0.0,在内网只要有人直接用 IP 加端口访问,就能完美绕过这道防盗门。必须让后端只监听127.0.0.1,或者利用安全组 / NetworkPolicy 限制它只接受来自 Nginx 的流量。 - 别让黑客伪造身份。 后端之所以敢信任
X-authentik-username,是因为它坚信这个 Header 是 Nginx 塞进去的。如果在官方配置模板里,你把覆盖X-authentik-*请求头的指令删了,恶意用户就可以自己在请求里加上这些 Header 来伪装成超级管理员。 - 机器之间的调用别走前门。 比如 Grafana 去查 Prometheus 的数据,或者 Prometheus 把告警推给 Alertmanager,这些都是冷冰冰的代码发出的请求,它们是不可能弹个飞书二维码来扫的。机器间通信必须用内网地址直连,绝对不要去走套了代理认证的公网域名。
- 免登录路径别写错。 像
/health这种健康检查接口是必须免登录的。你需要在 Provider 的 Unauthenticated Paths 里把它用正则写上(比如^/-/healthy$)。如果你正则写错了,系统不会报错,只会在 Outpost 的日志里悄悄记一条警告,结果就是健康检查探针会被拦在门外,导致 Pod 不断被重启。 - 如何退出登录:访问
https://<你的应用域名>/outpost.goauthentik.io/sign_out。
6. 排障指南:那些常见的报错
| 现象 | 最可能的原因 |
|---|---|
| 浏览器在登录页和应用之间无限疯狂跳转 | Provider 里的 External host 配置和浏览器地址栏里的实际 URL 不完全一致(比如差了个 HTTPS、端口号不对等),导致 Cookie 写不进去。 |
| 打开页面后报 404 或“找不到应用” | 最常见的新手坑:新应用建好了,但没加到 Outpost 的配置里。 |
Nginx 报错 upstream sent too big header | 某个用户的组或权限太多了,导致 HTTP Header 超过了 Nginx 的默认大小限制。去 Nginx 里加大 proxy_buffers 和 proxy_buffer_size 即可。 |
| Grafana 里的 Prometheus 数据源报错 | 数据源地址错填了套着代理认证的公网域名。请改成 Kubernetes 集群内部的 DNS 地址(比如 http://prometheus:9090)。 |
7. 生产环境的取舍与防坑经验
别拿它当权限系统用。 再次强调,给 Alertmanager 套上代理认证,只是为了不让全网的人看到告警;但只要是有权限登进去的研发,全都可以随手静默掉生产告警。对于真正需要精细化控制“只读 / 可操作”的场景,要么给它套个支持 OIDC 的马甲(比如通过 Grafana 来看告警),要么在 Nginx 层面用 location 规则把 POST/PUT 方法再单独卡死。
离职禁用后,会话不会像变魔术一样立刻消失。 员工被禁用后,authentik 确实会立刻拦截他的新登录;但是,Outpost 已经写在员工浏览器里的 Cookie,在过期前依然是合法的“门禁卡”。如果是应对紧急安全事件,必须在 authentik 后台主动清除该用户的会话,并自己实际访问一次确认它真的失效了(完整的离职处理见 架构与接入方式选型)。
防盗门和身份中心是同生共死的关系。 既然用了内置 Outpost,它就是跟着 authentik Server 跑的。一旦 authentik 宕机,所有挂了代理认证的页面全部都会报 500 无法访问。这里面最致命的是,连你用来排障的 Prometheus 和 Alertmanager 也一起打不开了!所以,对于监控链路本身,必须预留一条不依赖 authentik 的本地直连通道(比如只对跳板机网段开放的内部 IP 地址)。