diff --git a/src/azure-cli/HISTORY.rst b/src/azure-cli/HISTORY.rst index e343be21a1a..7113bc6d0cd 100644 --- a/src/azure-cli/HISTORY.rst +++ b/src/azure-cli/HISTORY.rst @@ -9,6 +9,10 @@ Release History * vmss update: Add --enable-terminate-notification and --terminate-notification-time parameters to support terminate scheduled event configurability. * Update azure-mgmt-compute version to 7.0.0. +**Key Vault** + +* Fix #8840: When using tenant domain name in `az login -t`, `keyvault create` fails. Tenant domain name is now resolved to GUID if it is not. + **Monitor** * monitor metrics alert create: Fix #9901. Support special character `:` in `--condition` argument. diff --git a/src/azure-cli/azure/cli/command_modules/ams/_utils.py b/src/azure-cli/azure/cli/command_modules/ams/_utils.py index dfb1d34406b..eb1613de5b6 100644 --- a/src/azure-cli/azure/cli/command_modules/ams/_utils.py +++ b/src/azure-cli/azure/cli/command_modules/ams/_utils.py @@ -22,8 +22,7 @@ def _is_guid(guid): uuid.UUID(guid) return True except ValueError: - pass - return False + return False def parse_duration(str_duration): diff --git a/src/azure-cli/azure/cli/command_modules/profile/__init__.py b/src/azure-cli/azure/cli/command_modules/profile/__init__.py index 6f9891bbe00..1a804788281 100644 --- a/src/azure-cli/azure/cli/command_modules/profile/__init__.py +++ b/src/azure-cli/azure/cli/command_modules/profile/__init__.py @@ -8,6 +8,7 @@ from azure.cli.core.commands.parameters import get_enum_type from azure.cli.command_modules.profile._format import transform_account_list +from ._validators import validate_tenant import azure.cli.command_modules.profile._help # pylint: disable=unused-import cloud_resource_types = ["oss-rdbms", "arm", "aad-graph", "ms-graph", "batch", "media", "data-lake"] @@ -47,7 +48,7 @@ def load_arguments(self, command): c.argument('password', options_list=['--password', '-p'], help="Credentials like user password, or for a service principal, provide client secret or a pem file with key and public certificate. Will prompt if not given.") c.argument('service_principal', action='store_true', help='The credential representing a service principal.') c.argument('username', options_list=['--username', '-u'], help='user name, service principal, or managed service identity ID') - c.argument('tenant', options_list=['--tenant', '-t'], help='The AAD tenant, must provide when using service principals.') + c.argument('tenant', options_list=['--tenant', '-t'], help='The AAD tenant, must provide when using service principals.', validator=validate_tenant) c.argument('allow_no_subscriptions', action='store_true', help="Support access tenants without subscriptions. It's uncommon but useful to run tenant level commands, such as 'az ad'") c.ignore('_subscription') # hide the global subscription parameter c.argument('identity', options_list=('-i', '--identity'), action='store_true', help="Log in using the Virtual Machine's identity", arg_group='Managed Service Identity') diff --git a/src/azure-cli/azure/cli/command_modules/profile/_validators.py b/src/azure-cli/azure/cli/command_modules/profile/_validators.py new file mode 100644 index 00000000000..0c0be06fb37 --- /dev/null +++ b/src/azure-cli/azure/cli/command_modules/profile/_validators.py @@ -0,0 +1,37 @@ +# -------------------------------------------------------------------------------------------- +# Copyright (c) Microsoft Corporation. All rights reserved. +# Licensed under the MIT License. See License.txt in the project root for license information. +# -------------------------------------------------------------------------------------------- + +import uuid + +from azure.cli.core.util import should_disable_connection_verify +from knack.log import get_logger + +logger = get_logger(__name__) + + +def _is_guid(guid): + try: + uuid.UUID(guid) + return True + except ValueError: + return False + + +def validate_tenant(cmd, namespace): + """ + Make sure tenant is a GUID. If domain name is provided, resolve to GUID. + https://docs.microsoft.com/en-us/azure/active-directory/develop/v2-protocols-oidc#fetch-the-openid-connect-metadata-document + """ + if not _is_guid(namespace.tenant): + import requests + active_directory_endpoint = cmd.cli_ctx.cloud.endpoints.active_directory + url = '{}/{}/.well-known/openid-configuration'.format(active_directory_endpoint, namespace.tenant) + metadata = requests.get(url, verify=not should_disable_connection_verify()).json() + + # Example issuer: https://sts.windows.net/72f988bf-86f1-41af-91ab-2d7cd011db47/ + tenant_id = metadata['issuer'].split("/")[3] + + logger.warning('Resolve tenant domain name %s to GUID %s', namespace.tenant, tenant_id) + namespace.tenant = tenant_id diff --git a/src/azure-cli/azure/cli/command_modules/role/custom.py b/src/azure-cli/azure/cli/command_modules/role/custom.py index 4e4ad8418be..77bbc5591f4 100644 --- a/src/azure-cli/azure/cli/command_modules/role/custom.py +++ b/src/azure-cli/azure/cli/command_modules/role/custom.py @@ -1661,8 +1661,7 @@ def _is_guid(guid): uuid.UUID(guid) return True except ValueError: - pass - return False + return False def _get_object_stubs(graph_client, assignees):