1

I'm writing an Azure Function app in Python that needs to access an API: https://service.flow.microsoft.com/ I keep getting a 401 Unauthorized response. I can access other resources using this same configuration, such as https://contoso.crm.dynamics.com, which leads me to believe the ServiceURL, ClientID, and ClientSecret are all correct. The app has the required permissions in Azure AD.

authContext = AuthenticationContext(os.environ["ServiceUrl"])
token = authContext.acquire_token_with_client_credentials(
    "https://service.flow.microsoft.com/", os.environ["ClientID"], os.environ["ClientSecret"])

headers = {
    "Authorization": "Bearer " + token["accessToken"],
    "OData-MaxVersion": "4.0",
    "OData-Version": "4.0",
    "Accept": "application/json"
}

apiUrl = f"https://api.flow.microsoft.com/providers/Microsoft.ProcessSimple/environments/{flow['environmentid']}/flows/{flow['RowKey']}/runs?api-version=2016-11-01&$orderby=startTime"

response = request("GET", apiUrl, headers=headers)

API Permissions in AD:

Tried using the common tenant ID in the service URL, still failed. I am able to connect using the common tenant ID and a user authentication flow in a local setting, but that is not possible when this is run serverless in Azure. I also tried playing with MSAL but couldn't get that to work either.

jb0070
  • 11
  • 1

1 Answers1

0

Please try to change the Authorization level to Anonymous. "authLevel": "anonymous"

Check for iss claim i.e; issuer url in token after decoding , see if it is v1 endpoint and change the same in the manifest accesstokenacceptedversion to 1.else if it is v2 change to v2. Also check for the aud i.e audience claim which has to match the client id .

To call the Azure REST API, you need to add a scope for api. In portal if have given api permission something like user_impersonation and exposed an api to that permission.

Ex: api://<clientId>/user_impersonation (appIdUri/scope) Your scope can be scope = api://<clientId>/user_impersonation or you can try api://<clientId>/.default

If the api is graph api , scope can be https://graph.microsoft.com/.default

Ex : python-azure-identity-clientsecretcredential

scope = "https://graph.microsoft.com/.default"
token = credential.get_token(scope)

References:

  1. python 3.x - How to properly use "get_token" of "ManagedIdentityCredential" of azure identity - Stack Overflow
  2. GitHub - Azure-Samples Python Azure Function Web API secured by Azure AD / Python Azure code sample | Microsoft Docs
  3. c# - Azure Function with AD auth results in 401 Unauthorized when using Bearer tokens - Stack Overflow
kavyaS
  • 8,026
  • 1
  • 7
  • 19