diff --git a/dvc/fs/azure.py b/dvc/fs/azure.py index fb7132e48..27c9c7d67 100644 --- a/dvc/fs/azure.py +++ b/dvc/fs/azure.py @@ -117,8 +117,21 @@ class AzureFileSystem(ObjectFSWrapper): login_info["client_id"] = config.get("client_id") login_info["client_secret"] = config.get("client_secret") - if not any( + if not (login_info["account_name"] or login_info["connection_string"]): + raise AzureAuthError( + "Authentication to Azure Blob Storage requires either " + "account_name or connection_string.\nLearn more about " + "configuration settings at " + + format_link("https://man.dvc.org/remote/modify") + ) + + any_secondary = any( value for key, value in login_info.items() if key != "account_name" + ) + if ( + login_info["account_name"] + and not any_secondary + and not config.get("allow_anonymous_login") ): login_info["credential"] = DefaultAzureCredential( exclude_interactive_browser_credential=False diff --git a/tests/unit/fs/test_azure.py b/tests/unit/fs/test_azure.py index cd79c898f..cf74a32d9 100644 --- a/tests/unit/fs/test_azure.py +++ b/tests/unit/fs/test_azure.py @@ -3,7 +3,7 @@ from concurrent.futures import ThreadPoolExecutor import pytest -from dvc.fs.azure import AzureFileSystem, _temp_event_loop +from dvc.fs.azure import AzureAuthError, AzureFileSystem, _temp_event_loop from dvc.path_info import PathInfo container_name = "container-name" @@ -67,3 +67,66 @@ def test_temp_event_loop(): future = executor.submit(wrapped_procedure) assert future.result() == "yeey" + + +def test_azure_login_methods(): + def get_login_method(config): + fs = AzureFileSystem(**config) + # pylint: disable=pointless-statement + return fs.login_method + + with pytest.raises(AzureAuthError): + get_login_method({}) + + assert ( + get_login_method({"connection_string": "test"}) == "connection string" + ) + assert get_login_method({"account_name": "test"}).startswith( + "default credentials" + ) + assert ( + get_login_method( + {"account_name": "test", "allow_anonymous_login": True} + ) + == "anonymous login" + ) + + with pytest.raises(AzureAuthError): + get_login_method( + {"tenant_id": "test", "client_id": "test", "client_secret": "test"} + ) + + assert ( + get_login_method( + { + "account_name": "test", + "tenant_id": "test", + "client_id": "test", + "client_secret": "test", + } + ) + == "AD service principal" + ) + + assert ( + get_login_method({"account_name": "test", "account_key": "test"}) + == "account key" + ) + assert ( + get_login_method({"account_name": "test", "sas_token": "test"}) + == "SAS token" + ) + assert ( + get_login_method( + { + "connection_string": "test", + "account_name": "test", + "sas_token": "test", + } + ) + == "connection string" + ) + assert ( + get_login_method({"connection_string": "test", "sas_token": "test"}) + == "connection string" + )