| 12
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
 100
 101
 102
 103
 104
 105
 106
 107
 108
 109
 110
 111
 112
 113
 114
 115
 116
 117
 118
 119
 120
 121
 122
 123
 
 | # Guide for migrating to azure-identity from azure-common
The newest Azure SDK libraries (the "client" and "management" libraries
[listed here](https://azure.github.io/azure-sdk/releases/latest/python.html))
use credentials from `azure-identity` to authenticate requests. Older versions
of these libraries typically used credentials from `azure-common`. Credential
types from these two libraries have different APIs, causing clients to raise
`AttributeError` when given a credential from the wrong library. For example, a
client expecting an `azure-identity` credential will raise an error like
`'ServicePrincipalCredentials' object has no attribute 'get_token'` when given a
credential from `azure-common`. A client expecting an `azure-common` credential
will raise an error like
`'ClientSecretCredential' object has no attribute 'signed_session'` when given
an `azure-identity` credential.
This document shows common authentication code using `azure-common`, and its
equivalent using `azure-identity`.
## Service principal authentication
`azure-common` uses `ServicePrincipalCredentials` to authenticate a service principal:
```python
from azure.common.credentials import ServicePrincipalCredentials
credential = ServicePrincipalCredentials(client_id, client_secret, tenant=tenant_id)
```
`azure-identity` uses [`ClientSecretCredential`][client_secret_cred] :
```python
from azure.identity import ClientSecretCredential
credential = ClientSecretCredential(tenant_id, client_id, client_secret)
```
## Authenticating through the Azure CLI
`azure-common` provides the
[`get_client_from_cli_profile`][get_client_from_cli_profile] function to
integrate with the Azure CLI for authentication. This code works with older
versions of `azure-mgmt-resource` such as 10.0.0:
```python
from azure.common.client_factory import get_client_from_cli_profile
from azure.mgmt.resource import SubscriptionClient
subscription_client = get_client_from_cli_profile(SubscriptionClient)
```
`azure-identity` integrates with the Azure CLI through its
[`AzureCliCredential`][cli_cred]. This code works with newer versions of
`azure-mgmt-resource`, starting with 15.0.0:
```python
from azure.identity import AzureCliCredential
from azure.mgmt.resource import SubscriptionClient
credential = AzureCliCredential()
subscription_client = SubscriptionClient(credential)
```
## JSON- and file-based authentication
To encourage best security practices, `azure-identity` does not support JSON- and file-based authentication in the same
way as `azure-common`. `azure-common` provided factory methods like [`get_client_from_json_dict`][client_from_json] and
[`get_client_from_auth_file`][client_from_auth_file] that are no longer available in `azure-identity`.
In `azure-common` you could provide credentials in a JSON dictionary, or from a JSON file:
```python
from azure.common.client_factory import get_client_from_json_dict, get_client_from_auth_file
from azure.mgmt.keyvault import KeyVaultManagementClient
# Provide credentials in JSON:
json_dict = {
    "clientId": "...",
    "clientSecret": "...",
    "subscriptionId": "...",
    "tenantId": "...",
    "activeDirectoryEndpointUrl": "https://login.microsoftonline.com",
    "resourceManagerEndpointUrl": "https://management.azure.com"
}
client = get_client_from_json_dict(KeyVaultManagementClient, json_dict)
# Or, provide credentials from a JSON file:
client = get_client_from_auth_file(KeyVaultManagementClient, "credentials.json")
```
If it's not possible to immediately migrate from file-based authentication, you can still use `azure-identity`. With a
JSON file containing your credentials, you can use [`json.load`][json] to authenticate a service principal with a
[`ClientSecretCredential`][client_secret_cred]:
```python
import json
from azure.identity import ClientSecretCredential
from azure.mgmt.keyvault import KeyVaultManagementClient
with open("credentials.json") as json_file:
    json_dict = json.load(json_file)
credential = ClientSecretCredential(
    tenant_id=json_dict["tenantId"],
    client_id=json_dict["clientId"],
    client_secret=json_dict["clientSecret"],
    authority=json_dict["activeDirectoryEndpointUrl"]
)
client = KeyVaultManagementClient(
    credential,
    json_dict["subscriptionId"],
    base_url=json_dict["resourceManagerEndpointUrl"],
    credential_scopes=["{}/.default".format(json_dict["resourceManagerEndpointUrl"])]
)
```
If storing credentials in a file, be sure to protect access to this file. Make certain that it's excluded by version
control -- for example, by adding the credential file name to your project's `.gitignore` file.
The global documentation for authenticating Python apps on Azure is available [here][authenticate_docs].
[authenticate_docs]: https://learn.microsoft.com/azure/developer/python/sdk/authentication-overview?tabs=cmd
[cli_cred]: https://aka.ms/azsdk/python/identity/docs#azure.identity.AzureCliCredential
[client_from_json]: https://learn.microsoft.com/python/api/azure-common/azure.common.client_factory?view=azure-python#get-client-from-json-dict-client-class--config-dict----kwargs-
[client_from_auth_file]: https://learn.microsoft.com/python/api/azure-common/azure.common.client_factory?view=azure-python#get-client-from-auth-file-client-class--auth-path-none----kwargs-
[client_secret_cred]: https://aka.ms/azsdk/python/identity/docs#azure.identity.ClientSecretCredential
[get_client_from_cli_profile]: https://learn.microsoft.com/python/api/azure-common/azure.common.client_factory?view=azure-python#get-client-from-cli-profile-client-class----kwargs-
[json]: https://docs.python.org/3/library/json.html#json.load
 |