Airflow2配置基于OAUTH2协议的Microsoft Azure SSO详细文档


参考文档:
通过 Azure AD 应用程序代理远程访问本地应用程序
The reply URL specified in the request does not match the reply URLs configured for the application

为什么要配置Azure sso?
原因:
客户要求为EMR集群核心组件配置基于Microsoft Azure的SSO,通过Azure AD应用程序代理远程访问EMR集群本地应用程序
客户提出该要求主要出于两点考虑:

  1. 安全性
    客户和我们是跨国的,我们都需要访问EMR集群里的本地应用程序,如果不采用类似Azure AD这种应用程序代理的方式,可能需要开通公网代理访问,这样风险极大.
  2. 便捷性
    EMR集群组件繁多,每个组件都有自己独立的账户认证体系,用户访问应用时,需要记录多个账户名密码,极其不便.

一. 方案选型

在网上搜寻关于airflow配置sso的现成案例,主要遇到两个问题:

  1. 介绍详细的版本不匹配
  2. 版本匹配的说的又很笼统

相关的资料很有限,大部分坑只能自己踩

Azure AD支持的身份验证方式主要有以下三种:

LDAP
SAML
OAUTH2

其中: 客户内部不使用LDAP
而airflow2版本目前全部基于flask-appbuilder来做身份验证和鉴权,
flask-appbuilder目前不支持SAML,所以改动起来工作量比较大
基于以上考虑,使用基于OAUTH2的身份认证协议来进行airflow单点登录配置

二. 单点登录配置

2.1 Airflow配置ssl登录

为什么要配置ssl登录?而不是采用默认的登录方式?
原因:
airflow安装后,默认使用http协议访问
而Azure AD配置基于OAUTH2的应用程序代理时,需要配置重定向url
重定向url要求填写为https
如下图:
在这里插入图片描述
配置https方式登录,需要提供相关证书.(airflow webserver服务节点)
我们当时采用的是运维同事帮忙申请的经过认证的证书
当然也可以使用自签名的免费证书,不过登录的时候会有提示,忽略就好了
可在该网站生成免费的https证书:
FreeSSL.cn
证书生成后,需要将key和cert文件上传至webserver服务器本地目录下

之后,需要修改airflow.cfg文件,根据https证书上传路
在这里插入图片描述
配置web_server_ssl_key ,web_server_ssl_cert两个参数的值,
以下为一个示例:

vi airflow.cfg
#当web_server_ssl_key,web_server_ssl_cert均不为空时,ssl生效
web_server_ssl_key = /opt/modules/airflow/cert/*.com.key
web_server_ssl_cert = /opt/modules/airflow/cert/*.com_bundle.pem


配置结束之后,重启airflow webserver,之后airflow会切换为https访问

2.2 Azure配置Airflow代理

首先使用微软账号登录以下网站:
https://portal.azure.com
在主页中选择Azure Active Directory
在这里插入图片描述

2.2.1 企业应用程序配置

选择Enterprise applications–>New application,根据界面提示创建新的企业应用程序
在这里插入图片描述

需要注意Application proxy配置:

在这里插入图片描述

1. Internal Url值为airflow配置ssl之后的内网地址
2. Translate URLs In Headers以及Application Body两个配置项都要选择no,否则会出现airflow界面访问异常的情况
为什么要这样配置请参考问题3.4

2.2.2 应用程序注册配置

界面选择App registrations–>New registration,注册应用程序,之后按照界面提示配置即可
在这里插入图片描述
需要注意如下配置:
Overview
在这里插入图片描述

overview这里,需要注意以下两个配置:
Application (client) ID, Directory (tenant) ID 客户端id及租户id后续配置airflow的时候需要用到

Authentication
在这里插入图片描述

这里需要注意以下配置:
重定向url里需要配置两个值
一个是企业应用程序的主页url
一个是在主页url后面添加/oauth-authorized/azure 
为什么要这样配置请参考问题3.3

certificates & secrets
在这里插入图片描述
这里需要生成一个新的秘钥,并拿到秘钥的value值,后续配置airflow的时候需要用到

2.3 airflow webserver.py配置

需要修改websever.py相关配置,以下是一个实例demo
需要替换以下值:
{your_clientid}替换为2.2.2中提到的Application (client) ID
{your_tenant_id}替换为2.2.2中提到的Directory (tenant) ID
{your_secret_value}替换为2.2.2中提到的生成秘钥的value

import os

from flask_appbuilder.security.manager import AUTH_OAUTH

CSRF_ENABLED = True
AUTH_TYPE = AUTH_OAUTH
# 这里一定要配置创建用户,否则首次登录的时候会出现无限重定向最后访问失败的问题
AUTH_USER_REGISTRATION = True
AUTH_USER_REGISTRATION_ROLE = "Admin"
OAUTH_PROVIDERS = [{
    "name": "azure",
    "icon": "fa-windows",
    "token_key": "access_token",
    'remote_app': {
         # 该设置与应用程序id一致
        'client_id':'{your_clientid}', 
		    # 该设置与证书和密码中的客户端密码值一致
        'client_secret':'{your_secret_value}',
		    # 该设置为https://login.microsoftonline.com/{租户id}/oauth2
        "base_url": "https://login.microsoftonline.com/{your_tenant_id}/oauth2",
        'client_kwargs':{
            'scope': 'User.read email openid profile basic users name preferred_username upn',
			      # 该值设置为应用程序id
            "resource": '{your_clientid}',
        },
        "request_token_url": None,
		    # 该值为https://login.microsoftonline.com/{租户id}/oauth2/token
        "access_token_url": "https://login.microsoftonline.com/{your_tenant_id}/oauth2/token",
		    # 该值为https://login.microsoftonline.com/{租户id}/oauth2/authorize
        "authorize_url": "https://login.microsoftonline.com/{your_tenant_id}/oauth2/authorize",
    }
}
]

配置结束之后,重启airflow webserver
之后通过企业应用程序里配置的主页url即可访问airflow

2.4 通过azure代理访问airflow

访问如下网站,在这里能够看到你的微软应用,如下图:
https://myapplications.microsoft.com/
在这里插入图片描述
选择airflow对应的应用,即可访问,如下图,配置完成!
在这里插入图片描述

三. airflow配置sso踩过的坑及解决方案

犹记得当时配置的时候很是痛苦,碰到了很多奇怪的问题,踩了很多坑.
不过因为当时时间紧迫,有些问题没来的及详细记录.
时间过去比较久了,只能尽可能的把有记录的坑分享一下,希望后续大家不要遇到类似的问题能快速解决

3.1 BadGateway:This corporate app can’t be accessed.

在这里插入图片描述
该问题很基础:
基本排查方向就两个

  1. airflow webserver是否正常启动
  2. 配置的代理主页url是否有误

3.2 Ariflow界面访问报错: invalid client secret is provided

在这里插入图片描述
原因:
提供的秘钥错误,应该提供的是秘钥的值(value),这里很容易配置成秘钥的id,导致无法访问

与该问题类似的错误还有客户端id或者租户ID的值配置成对象ID,导致airflow无法访问.
特别是英文不好的同学! 这里需要细心一点!

3.3 代理访问报错: The reply URL specified in the request does not match the reply URLs configured for the application

在这里插入图片描述

该问题是一个比较经典的问题
原因:
当我们访问airflow配置的外网代理地址时,会进行重定向.
而在配置应用程序注册时,也有一个重定向url的配置,如果两个配置不匹配,就会抛出这个错误.
重定向url的正确配置,我们可以通过截取浏览器的url值解析出来
确保我们配置的重定向url与实际跳转的url一致即可

注意:
这里会遇到一个奇怪的问题,
当我配置的重定向url是外网代理的主页地址时,报错会指向: {主页url{/oauth-authorized/azure
当我配置的重定向url是 {主页url{/oauth-authorized/azure,报错又会指向主页地址
最终,我将两个地址都添加到重定向url配置解决了这个问题.

该问题详细的解决方案可参考如下官方文档,有很详细的视频讲解:

The reply URL specified in the request does not match the reply URLs configured for the application

3.4 Airflow访问报错: CSRF Warning! State not equal in request and response.

界面上具体报错如下:

Something bad has happened.
Please consider letting us know by creating a bug report using GitHub.

Python version: 3.7.5
Airflow version: 2.1.1
-------------------------------------------------------------------------------
Traceback (most recent call last):
  File "/home/beebird/.local/lib/python3.7/site-packages/flask/app.py", line 2447, in wsgi_app
    response = self.full_dispatch_request()
  File "/home/beebird/.local/lib/python3.7/site-packages/flask/app.py", line 1952, in full_dispatch_request
    rv = self.handle_user_exception(e)
  File "/home/beebird/.local/lib/python3.7/site-packages/flask/app.py", line 1821, in handle_user_exception
    reraise(exc_type, exc_value, tb)
  File "/home/beebird/.local/lib/python3.7/site-packages/flask/_compat.py", line 39, in reraise
    raise value
  File "/home/beebird/.local/lib/python3.7/site-packages/flask/app.py", line 1950, in full_dispatch_request
    rv = self.dispatch_request()
  File "/home/beebird/.local/lib/python3.7/site-packages/flask/app.py", line 1936, in dispatch_request
    return self.view_functions[rule.endpoint](**req.view_args)
  File "/home/beebird/.local/lib/python3.7/site-packages/flask_appbuilder/security/views.py", line 695, in oauth_authorized
    resp = self.appbuilder.sm.oauth_remotes[provider].authorize_access_token()
  File "/home/beebird/python3.7/lib/python3.7/site-packages/authlib/integrations/flask_client/remote_app.py", line 74, in authorize_access_token
    params = self.retrieve_access_token_params(flask_req, request_token)
  File "/home/beebird/python3.7/lib/python3.7/site-packages/authlib/integrations/base_client/base_app.py", line 143, in retrieve_access_token_params
    params = self._retrieve_oauth2_access_token_params(request, params)
  File "/home/beebird/python3.7/lib/python3.7/site-packages/authlib/integrations/base_client/base_app.py", line 126, in _retrieve_oauth2_access_token_params
    raise MismatchingStateError()
authlib.integrations.base_client.errors.MismatchingStateError: mismatching_state: CSRF Warning! State not equal in request and response.

该问题是折磨我最久的一个问题,一度让我怀疑人生,除了界面上的报错之外
截取浏览器的访问请求,发现其一直在几个页面循环跳转,最终因为重定向次数过多,导致访问失败,然后在界面上抛出上面的问题
在这里插入图片描述
共有以下几个可能原因:

  1. webserver_config.py配置问题
    webserver_config.py需要添加类似配置,保证当用户首次登录的时候能够在airflow创建用户
AUTH_USER_REGISTRATION = True
AUTH_USER_REGISTRATION_ROLE = "Admin"
  1. 企业应用程序代理配置中,Translate URLs In Headers以及Application Body两个配置项没有都选择no
    这里一定要都选择no

在这里插入图片描述
3. 访问用户的权限问题
对该应用的权限为Member才能够访问airflow,否则也会报上面的问题

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值