I am trying to authenticate azure using ADAL, I am following azure docs
https://learn.microsoft.com/en-us/python/azure/python-sdk-azure-authenticate?view=azure-python
I am getting error
msrest.exceptions.AuthenticationError: Get Token request returned http error: 401 and server response: {"error":"invalid_client","error_description":"AADSTS70002: Error validating credentials. AADSTS50012: Invalid client secret is provided.\r\nTrace ID: be8e6b37-71dc-4a03-a6d5-8c1ea0c91900\r\nCorrelation ID: 0c1cb916-3250-4176-be9e-d951b8ec7203\r\nTimestamp: 2018-12-21 11:03:22Z","error_codes":[70002,50012],"timestamp":"2018-12-21 11:03:22Z","trace_id":"be8e6b37-71dc-4a03-a6d5-8c1ea0c91900","correlation_id":"0c1cb916-3250-4176-be9e-d951b8ec7203"}
I am sure that i am using correct TENANT_ID CLIENT and KEY.
Here is my code from docs
import adal
from msrestazure.azure_active_directory import AdalAuthentication
from msrestazure.azure_cloud import AZURE_PUBLIC_CLOUD
from azure.mgmt.compute import ComputeManagementClient
# Tenant ID for your Azure Subscription
TENANT_ID = 'bef06fb1-f1d7-4b31-9a96-xxfx5xx5xbx2x7'
# Your Service Principal App ID
CLIENT = '8ce61571-35c4-43ce-94ae-7xx1xex2x5x9'
# Your Service Principal Password
KEY = 'SoafGHAvu2EyTdSvxWQo/1XnlKRoaf89eDuuQiCnptc='
subscription_id = '020dd0e6-f63c-4e76-825c-02faad1d8d18'
LOGIN_ENDPOINT = AZURE_PUBLIC_CLOUD.endpoints.active_directory
RESOURCE = AZURE_PUBLIC_CLOUD.endpoints.active_directory_resource_id
context = adal.AuthenticationContext(LOGIN_ENDPOINT + '/' + TENANT_ID)
credentials = AdalAuthentication(
context.acquire_token_with_client_credentials,
RESOURCE,
CLIENT,
KEY
)
client = ComputeManagementClient(credentials, subscription_id)
vmlist = client.virtual_machines.list_all()
for vm in vmlist:
print(vm.name)
`
I can reproduce your issue on my side, I think you did not give the role to your service principal at the subscription scope.
To fix the issue, you could try to navigate to your subscription -> Access control (IAM) -> Add role assignment -> Add a Owner role(for example) to your service principal.
Then it will work fine.
For more details about Azure RBAC, refer to this link.
Related
We are working on our dev environment around Azure ML and Python.
As part of this, we are using azure-identity (DefaultAzureCredential) for authorization. This is going to either match a CLI credential or a "VSCode-logged-in" credential.
We would programatically like to know which user (identified by email address or ID) is currently present. How would we do this?
from azure.identity import DefaultAzureCredential
credential = DefaultAzureCredential()
token = credential.get_token("https://management.azure.com/", scopes=["user.read"])
current_user_id = ???
Update 1
As suggested by #xyan I can deconstruct the token to retrieve information about user accounts:
import json
import base64
from azure.identity import DefaultAzureCredential
credential = DefaultAzureCredential()
token = credential.get_token("https://management.azure.com/", scopes=["user.read"])
base64_meta_data = token.token.split(".")[1].encode("utf-8") + b'=='
json_bytes = base64.decodebytes(base64_meta_data)
json_string = json_bytes.decode("utf-8")
json_dict = json.loads(json_string)
current_user_id = json_dict["upn"]
print(f"{current_user_id=}")
This works for user accounts, but not for service principals. In that case, it fails retrieving the token:
DefaultAzureCredential failed to retrieve a token from the included credentials.
Attempted credentials:
EnvironmentCredential: Authentication failed: ClientApplication.acquire_token_silent_with_error() got multiple values for argument 'scopes'
What would be a proper scope that could retrieve upn/oid for various types of clients?
You can try parse the token to get the client id, tenant id information.
Sample code:
https://github.com/Azure/azure-sdk-for-python/blob/main/sdk/identity/azure-identity/azure/identity/_internal/decorators.py#L38.
(I work in the Azure SDK team in Microsoft)
I am trying to access a storage queue programatically with python but peeking at the messages fails with an Auth error:
azure.core.exceptions.HttpResponseError: This request is not authorized to perform this operation using this permission.
RequestId:xxxx
Time:2020-12-10T08:03:46.1919000Z
ErrorCode:AuthorizationPermissionMismatch
Error:None
My code looks like this:
from azure.storage.queue import (
QueueClient, TextBase64DecodePolicy
)
from azure.identity import AzureCliCredential
credential = AzureCliCredential()
DEFAULT_SUBSCRIPTION_ID = "xxx"
DEFAULT_POISON_QUEUE_NAME = "webjobs-blobtrigger-poison"
storage_account_name = "stxxx"
url = f"https://{storage_account_name}.queue.core.windows.net/{DEFAULT_POISON_QUEUE_NAME}"
client = QueueClient.from_queue_url(url, credential, message_decode_policy=TextBase64DecodePolicy())
properties = queue_client.get_queue_properties()
count = properties.approximate_message_count # works?!?
messages = queue_client.peek_messages(count) # exception
Note the storage account was created through terraform and has no special config
According to the code you provide, you want to use Azure AD token to peek messages from Azure queue storage. If so, you need to assign some special Azure RABC role(Storage Queue Data Contributor, Storage Queue Data Reader and Storage Queue Data Message Processor) to the user or service principal you use to login in Azure CLI. For more details, please refer to here and here.
For example
Assign Storage Queue Data Reader role to the user or service principal
az role assignment create \
--role "Storage Queue Data Reader" \
--assignee <email> \
--scope "/subscriptions/<subscription>/resourceGroups/<resource-group>/providers/Microsoft.Storage/storageAccounts/<storage-account>"
Sign out and log in again with Azure CLI
az logout
az login
az account set -s '<your subscription Id >'
code
from azure.storage.queue import QueueClient, TextBase64DecodePolicy
from azure.identity import AzureCliCredential
credential = AzureCliCredential()
DEFAULT_POISON_QUEUE_NAME = "myqueue"
storage_account_name = "andyprivate"
url = f"https://{storage_account_name}.queue.core.windows.net/{DEFAULT_POISON_QUEUE_NAME}"
client = QueueClient.from_queue_url(
url, credential, message_decode_policy=TextBase64DecodePolicy())
properties = client .get_queue_properties()
count = properties.approximate_message_count
print(count)
messages = client.peek_messages(count)
for message in messages:
print("Message: " + message.content)
I am currently attempting to authenticate to Azure using the azure-mgmt-support MicrosoftSupport client and am receiving the following error:
AdalError: Get Token request returned http error: 400 and server response: {"error":"unauthorized_client","error_description":"AADSTS700016: Application with identifier 'xxx' was not found in the directory 'management.core.windows.net'. This can happen if the application has not been installed by the administrator of the tenant or consented to by any user in the tenant. You may have sent your authentication request to the wrong tenant.
I have double checked and am definitely using the correct client_id and tenant_id. What am I missing here? My code below:
from azure.mgmt.support import MicrosoftSupport
from msrestazure.azure_active_directory import ServicePrincipalCredentials
sub_id = 'xxx'
sp_creds = ServicePrincipalCredentials(client_id='xxx', secret='xxx')
SupportClient = MicrosoftSupport(sp_creds, sub_id)
After a short walk and another look at the documentation, and I spotted my error - I was missing the tenant_id from the ServicePrincipalCredentials object. It's not obvious from the SDK specification or error message that this is what was missing as the only required variables are client_id and secret, however when I looked at this example in the documentation I realised it was missing (pasting code below for posterity, in case docs page changes).
import os
from azure.mgmt.resource import SubscriptionClient
from azure.common.credentials import ServicePrincipalCredentials
# Retrieve the IDs and secret to use with ServicePrincipalCredentials
subscription_id = os.environ["AZURE_SUBSCRIPTION_ID"]
tenant_id = os.environ["AZURE_TENANT_ID"]
client_id = os.environ["AZURE_CLIENT_ID"]
client_secret = os.environ["AZURE_CLIENT_SECRET"]
credential = ServicePrincipalCredentials(tenant=tenant_id, client_id=client_id, secret=client_secret)
subscription_client = SubscriptionClient(credential)
subscription = next(subscription_client.subscriptions.list())
print(subscription.subscription_id)
I'm looking for a way to get access token from a client profile when working with Azure using Python.
from azure.common.client_factory import get_client_from_cli_profile
from azure.mgmt.compute import ComputeManagementClient
client = get_client_from_cli_profile(ComputeManagementClient)
From the code I get the client profile context but how can I get access token from it?
I could find the method to get the access token from a client profile, to get the access token, you could use the adal, use which method depends on your requirement.
For example, I get the access token of a service principal with the client credentials to access the Azure Management REST API, the given resource is https://management.azure.com/.
import adal
# Tenant ID for your Azure Subscription
TENANT_ID = 'xxxxxxx'
# Your Service Principal App ID
CLIENT = 'xxxxxxx'
# Your Service Principal Password
KEY = 'xxxxxxx'
subscription_id = 'xxxxxxx'
authority_url = 'https://login.microsoftonline.com/'+TENANT_ID
context = adal.AuthenticationContext(authority_url)
token = context.acquire_token_with_client_credentials(
resource='https://management.azure.com/',
client_id=CLIENT,
client_secret=KEY
)
print(token["accessToken"])
I want to list azure security center alerts using the python SDK.
I found this package:
https://pypi.org/project/azure-mgmt-security/
It must be included in the microsoft documentation:
https://learn.microsoft.com/en-gb/python/azure/?view=azure-python
https://github.com/Azure/azure-sdk-for-python
but I can not find any reference or example.
Does anyone know where I can find this information?
Best regards.
I can just give a rough reference.
After install the package azure-mgmt-security, you should use List method in the package, source code is here.
Here is the the doc on how to authentication.
Here is doc on how to get tenantId / client_id / key.
Here is my code:
from azure.mgmt.security import SecurityCenter
from azure.common.credentials import ServicePrincipalCredentials
subscription_id = "xxxx"
# Tenant ID for your Azure subscription
TENANT_ID = '<Your tenant ID>'
# Your service principal App ID
CLIENT = '<Your service principal ID>'
# Your service principal password
KEY = '<Your service principal password>'
credentials = ServicePrincipalCredentials(
client_id = CLIENT,
secret = KEY,
tenant = TENANT_ID
)
client = SecurityCenter(credentials=credentials,subscription_id=subscription_id,asc_location="centralus")
client.alerts.list()
Also, you can use List Alerts api with a http request in python.
As of today, February 2021, Microsoft again changed the way credentials are instantiated. Here is the current one:
from azure.identity import DefaultAzureCredential
# Acquire a credential object for the app identity. When running in the cloud,
# DefaultAzureCredential uses the app's managed identity (MSI) or user-assigned service principal.
# When run locally, DefaultAzureCredential relies on environment variables named
# AZURE_CLIENT_ID, AZURE_CLIENT_SECRET, and AZURE_TENANT_ID.
credential = DefaultAzureCredential()
And it also changed the SecurityCenter signature, the credentials parameter was renamed to credential without the "s".
Full documentation here.