在 Kubernetes Ingress 中配置全局 OAuth2 Proxy 鉴权,推荐将 oauth2-proxy 部署为独立服务并通过 Ingress 注解指向认证地址,适用于 Nginx Ingress Controller 环境。配置错误可能导致所有用户无法访问服务,需预先验证回调地址和 Cookie 域名。
先说结论:通过 Ingress 注解将未认证请求重定向到 oauth2-proxy 服务是实现全局鉴权的标准方案,适合保护无内置认证的内部 Web 应用。
- 适合:Nginx Ingress Controller 集群,需保护多个无认证服务的场景。
- 先准备:在身份提供商(GitHub/GitLab/Google)创建 OAuth 应用并获取 Client ID 和 Secret。
- 验收:访问受保护域名应跳转登录页,认证成功后携带 Cookie 访问后端服务。
命令速用版
生成 32 字节 Cookie 加密密钥,用于保护会话信息:
python -c 'import os,base64; print(base64.urlsafe_b64encode(os.urandom(32)).decode())'使用 Helm 快速部署 oauth2-proxy 示例:
helm repo add oauth2-proxy https://oauth2-proxy.github.io/oauth2-proxy
helm install oauth2-proxy oauth2-proxy/oauth2-proxy -n auth-system `--create-namespace`为什么会这样
OAuth2 Proxy 作为反向代理拦截请求,在用户和上游服务之间建立认证层。未认证请求被重定向到身份提供商登录页,认证成功后 Proxy 生成加密 Cookie 并转发请求至后端。这种架构无需修改应用代码,仅在入口层统一管控访问权限,适合 Kubernetes 中微服务众多且无法逐一改造认证逻辑的场景。
分步处理
步骤 1:配置身份提供商
在 GitHub、GitLab 或 Google Cloud Console 创建 OAuth 应用。回调 URL 必须配置为https://<应用域名>/oauth2/callback,范围选择openid、profile和email。记录生成的 Client ID 和 Client Secret。
步骤 2:部署 OAuth2 Proxy
创建 Kubernetes Secret 存储认证凭据和 Cookie 密钥。部署 oauth2-proxy 时指定`--cookie-secret`、`--client-id`、`--client-secret`和`--provider`参数。建议将私有服务分组到同一子域(如*.int.your_domain),以便认证 Cookie 在子域间共享。
步骤 3:配置 Ingress 注解
在需要保护的 Ingress 资源中添加注解,指向 oauth2-proxy 服务地址。关键注解包括nginx.ingress.kubernetes.io/auth-url和nginx.ingress.kubernetes.io/auth-signin。确保 Ingress 规则中的 Host 与 OAuth 应用配置的回调域名一致。
步骤 4:启用 HTTPS
OAuth2 流程强制要求 HTTPS。配置 Cert-Manager 或手动导入 TLS 证书,确保 Ingress 的tls部分已正确设置,否则浏览器会阻止认证回调。
怎么验证是否生效
使用curl命令访问受保护域名,未携带 Cookie 时应返回 302 重定向到身份提供商登录页。登录成功后,检查浏览器开发者工具中的 Application 标签,确认存在_oauth2_proxyCookie。查看 oauth2-proxy Pod 日志,应看到Authenticated user相关记录且无 403 报错。
常见坑
Cookie 域名配置错误会导致认证成功后无法访问子服务。若服务分布在不同子域,需在 oauth2-proxy 配置中设置cookie-domain为父域名。回调地址不匹配是常见失败原因,OAuth 提供商后台配置的 Redirect URI 必须与 Ingress 访问地址完全一致,包括协议头和路径。未启用 HTTPS 会导致浏览器拦截回调请求,认证流程中断。
常见问题
Cookie 密钥长度有什么要求?
必须至少 16 字节,推荐使用 32 字节随机字符串。使用 Python 或 OpenSSL 生成 Base64 编码的随机值可确保安全性,过短的密钥会导致启动报错。
如何实现全局默认鉴权?
在 Nginx Ingress Controller 的 ConfigMap 中配置global-auth-url和global-auth-signin。此配置会对集群所有 Ingress 生效,无需逐个添加注解,但需确保所有服务都兼容 OAuth2 跳转。
注销登录如何清除 Cookie?
访问 oauth2-proxy 的/oauth2/sign_out端点可清除本地会话 Cookie。若需完全注销身份提供商会话,需额外配置`--provider-display-name`并支持 OIDC logout 端点。
参考来源
- DigitalOcean Community, How to Set Up an Nginx Ingress with Cert-Manager on DigitalOcean Kubernetes
- oauth2-proxy project, Official GitHub Repository (https://github.com/oauth2-proxy/oauth2-proxy)
- Community Tutorials, Kubernetes Ingress Nginx OAuth2 Gitlab Implementation