This is an automated email from the ASF dual-hosted git repository.

potiuk pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/airflow.git


The following commit(s) were added to refs/heads/main by this push:
     new 293f172148b fix sdk configuration to use $AIRFLOW_CONFIG env (#64936)
293f172148b is described below

commit 293f172148b5f78bb4d821b7919cf04873af38cb
Author: Jeongwoo Do <[email protected]>
AuthorDate: Tue Apr 14 18:35:09 2026 +0900

    fix sdk configuration to use $AIRFLOW_CONFIG env (#64936)
    
    * fix sdk configuration to use AIRFLOW_CONFIG env
    
    * fix logic
---
 task-sdk/src/airflow/sdk/configuration.py     | 10 ++++++---
 task-sdk/tests/task_sdk/test_configuration.py | 30 ++++++++++++++++++++++++++-
 2 files changed, 36 insertions(+), 4 deletions(-)

diff --git a/task-sdk/src/airflow/sdk/configuration.py 
b/task-sdk/src/airflow/sdk/configuration.py
index fba300e4a84..4e438a2cbf7 100644
--- a/task-sdk/src/airflow/sdk/configuration.py
+++ b/task-sdk/src/airflow/sdk/configuration.py
@@ -30,6 +30,7 @@ from airflow.sdk import yaml
 from airflow.sdk._shared.configuration.parser import (
     AirflowConfigParser as _SharedAirflowConfigParser,
     configure_parser_from_configuration_description,
+    expand_env_var,
 )
 from airflow.sdk.execution_time.secrets import 
_SERVER_DEFAULT_SECRETS_SEARCH_PATH
 
@@ -99,7 +100,7 @@ def get_sdk_expansion_variables() -> dict[str, Any]:
     SDK only needs AIRFLOW_HOME for expansion. Core specific variables
     (FERNET_KEY, JWT_SECRET_KEY, etc.) are not needed in the SDK.
     """
-    airflow_home = os.environ.get("AIRFLOW_HOME", 
os.path.expanduser("~/airflow"))
+    airflow_home = expand_env_var(os.environ.get("AIRFLOW_HOME", 
os.path.expanduser("~/airflow")))
     return {
         "AIRFLOW_HOME": airflow_home,
     }
@@ -107,8 +108,11 @@ def get_sdk_expansion_variables() -> dict[str, Any]:
 
 def get_airflow_config() -> str:
     """Get path to airflow.cfg file."""
-    airflow_home = os.environ.get("AIRFLOW_HOME", 
os.path.expanduser("~/airflow"))
-    return os.path.join(airflow_home, "airflow.cfg")
+    airflow_config_var = os.environ.get("AIRFLOW_CONFIG")
+    if airflow_config_var is None:
+        airflow_home: str = os.environ.get("AIRFLOW_HOME", 
os.path.expanduser("~/airflow"))
+        return os.path.join(expand_env_var(airflow_home), "airflow.cfg")
+    return expand_env_var(airflow_config_var)
 
 
 class AirflowSDKConfigParser(_SharedAirflowConfigParser):
diff --git a/task-sdk/tests/task_sdk/test_configuration.py 
b/task-sdk/tests/task_sdk/test_configuration.py
index 32ecc7ff3a1..cf512fa4418 100644
--- a/task-sdk/tests/task_sdk/test_configuration.py
+++ b/task-sdk/tests/task_sdk/test_configuration.py
@@ -23,7 +23,7 @@ from unittest import mock
 import pytest
 
 from airflow.sdk._shared.configuration.exceptions import AirflowConfigException
-from airflow.sdk.configuration import conf
+from airflow.sdk.configuration import conf, get_airflow_config
 from airflow.sdk.providers_manager_runtime import ProvidersManagerTaskRuntime
 
 from tests_common.test_utils.config import (
@@ -156,3 +156,31 @@ class TestSDKProviderConfigPriority:
         custom_value = "my_custom.celery_executor"
         with conf_vars({("celery", "celery_app_name"): custom_value}):
             assert conf.get("celery", "celery_app_name") == custom_value
+
+
+class TestGetAirflowConfig:
+    """Tests for get_airflow_config respecting AIRFLOW_CONFIG env var."""
+
+    def test_returns_airflow_config_env_var(self):
+        """get_airflow_config returns AIRFLOW_CONFIG when set."""
+        with mock.patch.dict("os.environ", {"AIRFLOW_CONFIG": 
"/custom/path/airflow.cfg"}):
+            assert get_airflow_config() == "/custom/path/airflow.cfg"
+
+    def test_expands_env_var_in_airflow_config(self):
+        """get_airflow_config expands env vars in AIRFLOW_CONFIG."""
+        with mock.patch.dict(
+            "os.environ", {"AIRFLOW_CONFIG": "$CUSTOM_DIR/airflow.cfg", 
"CUSTOM_DIR": "/resolved"}
+        ):
+            assert get_airflow_config() == "/resolved/airflow.cfg"
+
+    def test_default_fallback_when_airflow_config_not_set(self):
+        """get_airflow_config returns {AIRFLOW_HOME}/airflow.cfg when 
AIRFLOW_CONFIG is absent."""
+        env = {"AIRFLOW_HOME": "/custom/home"}
+        with mock.patch.dict("os.environ", env, clear=True):
+            assert get_airflow_config() == "/custom/home/airflow.cfg"
+
+    def test_expands_env_var_in_airflow_home_fallback(self):
+        """get_airflow_config expands env vars in AIRFLOW_HOME when 
AIRFLOW_CONFIG is absent."""
+        env = {"AIRFLOW_HOME": "$CUSTOM_DIR/airflow", "CUSTOM_DIR": 
"/resolved"}
+        with mock.patch.dict("os.environ", env, clear=True):
+            assert get_airflow_config() == "/resolved/airflow/airflow.cfg"

Reply via email to