Azure / azure-sdk-for-python

This repository is for active development of the Azure SDK for Python. For consumers of the SDK we recommend visiting our public developer docs at https://learn.microsoft.com/python/azure/ or our versioned developer docs at https://azure.github.io/azure-sdk-for-python.
MIT License
4.59k stars 2.81k forks source link

Azure SDK token POST request on AARCH64 hangs indefinitely. #38077

Open JP-WienEnergie opened 2 hours ago

JP-WienEnergie commented 2 hours ago

When trying to upload blobs to the azure blob storage on a Linux AARCH64 system, token post hangs indefinitely.

The intention was to use the async azure libraries, specifically the DefaultAzureCredential and BlobServiceClient functions. Tested using a python script (below) which should authenticate and upload a blob to the blob storage.

import os
import asyncio
import logging
from azure.identity.aio import DefaultAzureCredential
from azure.storage.blob.aio import BlobServiceClient

# Set up the logger with a single configuration
logging.basicConfig(
    level=logging.DEBUG,  # Set default logging level to DEBUG
    format="%(asctime)s - %(name)s - %(levelname)s - %(message)s",  # Set log message format
    handlers=[logging.StreamHandler()],  # Use StreamHandler for console logging
)

# Create loggers
logger = logging.getLogger("test_AD")  # Logger for this module
azure_logger = logging.getLogger("azure")  # Logger for Azure SDK

class TestAzure:

    def __init__(self):
        # Create an instance of DefaultAzureCredential with Managed Identity excluded
        self.account_name = os.environ.get("AZURE_ACCOUNT_NAME")
        self.client_id = os.environ.get("AZURE_CLIENT_ID")
        self.tenant_id = os.environ.get("AZURE_TENANT_ID")
        self.cert_path = os.environ.get("AZURE_CLIENT_CERTIFICATE_PATH")
        self.azure_credential = DefaultAzureCredential(exclude_managed_identity_credential=True)
        self.account_url = f"https://{self.account_name}.blob.core.windows.net"
        self.container_name = "fileupload"

    async def test_certificate_authentication(self):
        # Fetch account details from environment variables

        # Log the account details (for debugging purposes)
        logger.info(f"Starting token acquisition process.")
        logger.info(f"account_name: {self.account_name}")
        logger.info(f"client_id: {self.client_id}")
        logger.info(f"tenant_id: {self.tenant_id}")
        logger.info(f"cert_path: {self.cert_path}")

        # Attempt to acquire a token for the specified resource
        try:
            logger.debug("Attempting to acquire token for 'https://storage.azure.com/.default'")
            token = await self.azure_credential.get_token("https://storage.azure.com/.default")
            logger.info(f"Acquired token: {token.token}")
        except Exception as e:
            logger.error(f"Failed to acquire token: {e}")

    async def send_blob(self, blob_path):
        """
        Uploads a blob to Azure Blob Storage.

        Args:
            blob_path (str): The local path of the file to upload.
        """
        try:
            # Use async with to ensure proper resource cleanup
            async with BlobServiceClient(
                account_url=self.account_url, credential=self.azure_credential
            ) as blob_service_client:
                # Get container client
                async with blob_service_client.get_container_client(self.container_name) as container_client:
                    # Generate blob name and upload
                    blob_name = os.path.basename(blob_path)
                    logger.info(f"Uploading blob: {blob_name}")

                    # Open file and upload
                    with open(blob_path, mode="rb") as data:
                        await container_client.upload_blob(name=blob_name, data=data, overwrite=True)

                    logger.info(f"Blob {blob_name} uploaded successfully.")

        except Exception as e:
            logger.error(f"Uploading Blob failed for {blob_path}: {e}")

    async def close(self):
        await self.azure_credential.close()

    async def main(self):
        # example dummy file
        blob_path = "test_file.zip"
        await self.send_blob(blob_path)

        await azure_ad_test.close()

# main function
if __name__ == "__main__":
    azure_ad_test = TestAzure()
    asyncio.run(azure_ad_test.main())

The script uses the account name, client ID, tenant ID and azure certificate pem file which contains the certificate and private key. These variables are exported as global ENV variables such that the DefaultAzureCredential can access them.

Once an instance of the DefaultAzureCredential is created (this part is successful), a blob client session is created and subsequently a container client session with the intended container name.

The next step would be to use: container_client.upload_blob function. However before the script gets to this point. During the token request, I get an error message: "no body was attached to the request". And then the program gets stuck indefinitely. These are the logs from the linux AARCH64 system:

Uploading blob: test_file.zip
2024-10-21T23:22:35.927195639Z 2024-10-21 23:22:35,926: <INFO> azure.core.pipeline.policies.http_logging_policy: Request URL: 'https://login.microsoftonline.com/*****/oauth2/v2.0/token'
2024-10-21T23:22:35.927288439Z Request method: 'POST'
2024-10-21T23:22:35.927327095Z Request headers:
2024-10-21T23:22:35.927360023Z 'Content-Type': 'application/x-www-form-urlencoded'
2024-10-21T23:22:35.927392120Z 'User-Agent': 'azsdk-python-identity/1.18.0 Python/3.8.20 (Linux-5.10.120-coreio-aarch64-with-glibc2.34)'
2024-10-21T23:22:35.927423864Z A body is sent with the request

**Note: redacted IDs with ***

There are no further logs after this point, no timeout or exceptions. Just stays there forever.

Using the same script on MacOS, same credentials and inputs, the file upload was a success.

I have created a service request with microsoft, after a call and log review, no solution was found and they suggested I open this ticket.

any idea what's going on? thank-you!

github-actions[bot] commented 2 hours ago

Thanks for the feedback! We are routing this to the appropriate team for follow-up. cc @jalauzon-msft @vincenttran-msft.