diff --git a/src/azure-cli-core/azure/cli/core/_profile.py b/src/azure-cli-core/azure/cli/core/_profile.py index 8df59ee2bc4..73b2ad72ddb 100644 --- a/src/azure-cli-core/azure/cli/core/_profile.py +++ b/src/azure-cli-core/azure/cli/core/_profile.py @@ -103,22 +103,17 @@ def _attach_token_tenant(subscription, tenant, tenant_id_description=None): """Attach the token tenant information to the subscription. CLI uses tenant_id to know which token should be used to access the subscription. - This function supports multiple APIs: - - v2016_06_01: Subscription doesn't have tenant_id - - v2022_12_01: - - Subscription has tenant_id representing the home tenant ID, mapped to home_tenant_id - - TenantIdDescription has default_domain, mapped to tenant_default_domain - - TenantIdDescription has display_name, mapped to tenant_display_name + - Subscription has tenant_id representing the home tenant ID, mapped to home_tenant_id + - TenantIdDescription has default_domain, mapped to tenant_default_domain + - TenantIdDescription has display_name, mapped to tenant_display_name """ - if hasattr(subscription, "tenant_id"): - setattr(subscription, 'home_tenant_id', subscription.tenant_id) + setattr(subscription, 'home_tenant_id', subscription.tenant_id) setattr(subscription, 'tenant_id', tenant) - # Attach tenant_default_domain, if available - if tenant_id_description and hasattr(tenant_id_description, "default_domain"): + if tenant_id_description: + # Attach tenant_default_domain setattr(subscription, 'tenant_default_domain', tenant_id_description.default_domain) - # Attach display_name, if available - if tenant_id_description and hasattr(tenant_id_description, "display_name"): + # Attach display_name setattr(subscription, 'tenant_display_name', tenant_id_description.display_name) @@ -948,18 +943,16 @@ def _transform_subscription_for_multiapi(s, s_dict): :param s: subscription object :param s_dict: subscription dict """ - if hasattr(s, 'home_tenant_id'): - s_dict[_HOME_TENANT_ID] = s.home_tenant_id + s_dict[_HOME_TENANT_ID] = s.home_tenant_id if hasattr(s, 'tenant_default_domain'): s_dict[_TENANT_DEFAULT_DOMAIN] = s.tenant_default_domain if hasattr(s, 'tenant_display_name'): s_dict[_TENANT_DISPLAY_NAME] = s.tenant_display_name - if hasattr(s, 'managed_by_tenants'): - if s.managed_by_tenants is None: - s_dict[_MANAGED_BY_TENANTS] = None - else: - s_dict[_MANAGED_BY_TENANTS] = [{_TENANT_ID: t.tenant_id} for t in s.managed_by_tenants] + if s.managed_by_tenants is None: + s_dict[_MANAGED_BY_TENANTS] = None + else: + s_dict[_MANAGED_BY_TENANTS] = [{_TENANT_ID: t.tenant_id} for t in s.managed_by_tenants] def _create_identity_instance(cli_ctx, authority, tenant_id=None, client_id=None): diff --git a/src/azure-cli-core/azure/cli/core/tests/test_profile.py b/src/azure-cli-core/azure/cli/core/tests/test_profile.py index 719a58ad014..b5606795d8d 100644 --- a/src/azure-cli-core/azure/cli/core/tests/test_profile.py +++ b/src/azure-cli-core/azure/cli/core/tests/test_profile.py @@ -26,6 +26,7 @@ MOCK_EXPIRES_ON_DATETIME = datetime.datetime.fromtimestamp(MOCK_EXPIRES_ON_INT).strftime("%Y-%m-%d %H:%M:%S.%f") BEARER = 'Bearer' +MOCK_TENANT_ID = '15027ca3-935c-4327-92a5-da7bfd15c8cb' MOCK_TENANT_DISPLAY_NAME = 'TEST_TENANT_DISPLAY_NAME' MOCK_TENANT_DEFAULT_DOMAIN = 'test.onmicrosoft.com' @@ -137,7 +138,7 @@ class TestProfile(unittest.TestCase): @classmethod def setUpClass(cls): - cls.tenant_id = 'test.onmicrosoft.com' + cls.tenant_id = MOCK_TENANT_ID cls.tenant_display_name = MOCK_TENANT_DISPLAY_NAME cls.tenant_default_domain = MOCK_TENANT_DEFAULT_DOMAIN @@ -164,14 +165,14 @@ def setUpClass(cls): managed_by_tenants=cls.managed_by_tenants) cls.subscription1_output = [{'environmentName': 'AzureCloud', - 'homeTenantId': 'test.onmicrosoft.com', + 'homeTenantId': MOCK_TENANT_ID, 'id': '1', 'isDefault': True, 'managedByTenants': [{'tenantId': '00000003-0000-0000-0000-000000000000'}, {'tenantId': '00000004-0000-0000-0000-000000000000'}], 'name': 'foo account', 'state': 'Enabled', - 'tenantId': 'test.onmicrosoft.com', + 'tenantId': MOCK_TENANT_ID, 'user': { 'name': 'foo@foo.com', 'type': 'user' @@ -179,14 +180,14 @@ def setUpClass(cls): cls.subscription1_with_tenant_info_output = [{ 'environmentName': 'AzureCloud', - 'homeTenantId': 'test.onmicrosoft.com', + 'homeTenantId': MOCK_TENANT_ID, 'id': '1', 'isDefault': True, 'managedByTenants': [{'tenantId': '00000003-0000-0000-0000-000000000000'}, {'tenantId': '00000004-0000-0000-0000-000000000000'}], 'name': 'foo account', 'state': 'Enabled', - 'tenantId': 'test.onmicrosoft.com', + 'tenantId': MOCK_TENANT_ID, 'tenantDisplayName': MOCK_TENANT_DISPLAY_NAME, 'tenantDefaultDomain': MOCK_TENANT_DEFAULT_DOMAIN, 'user': { @@ -200,15 +201,16 @@ def setUpClass(cls): cls.display_name1, cls.state1, tenant_id=cls.tenant_id, - managed_by_tenants=cls.managed_by_tenants, - home_tenant_id=cls.tenant_id) + home_tenant_id=cls.tenant_id, + managed_by_tenants=cls.managed_by_tenants) # Dummy result of azure.cli.core._profile.SubscriptionFinder.find_using_common_tenant # It also contains tenant information, compared to the result of find_using_specific_tenant cls.subscription1_with_tenant_info = SubscriptionStub( cls.id1, cls.display_name1, cls.state1, - tenant_id=cls.tenant_id, managed_by_tenants=cls.managed_by_tenants, + tenant_id=cls.tenant_id, home_tenant_id=cls.tenant_id, + managed_by_tenants=cls.managed_by_tenants, tenant_display_name=cls.tenant_display_name, tenant_default_domain=cls.tenant_default_domain) # Dummy result of azure.cli.core._profile.Profile._normalize_properties @@ -490,14 +492,14 @@ def test_login_with_service_principal(self, login_with_service_principal_mock, subs = profile.login(False, 'my app', {'secret': 'very_secret'}, True, self.tenant_id, use_device_code=True, allow_no_subscriptions=False) output = [{'environmentName': 'AzureCloud', - 'homeTenantId': 'test.onmicrosoft.com', + 'homeTenantId': MOCK_TENANT_ID, 'id': '1', 'isDefault': True, 'managedByTenants': [{'tenantId': '00000003-0000-0000-0000-000000000000'}, {'tenantId': '00000004-0000-0000-0000-000000000000'}], 'name': 'foo account', 'state': 'Enabled', - 'tenantId': 'test.onmicrosoft.com', + 'tenantId': MOCK_TENANT_ID, 'user': { 'name': 'my app', 'type': 'servicePrincipal'}}] @@ -1842,7 +1844,7 @@ def __exit__(self, _2, _3, _4): class SubscriptionStub(Subscription): # pylint: disable=too-few-public-methods - def __init__(self, id, display_name, state, tenant_id, managed_by_tenants=[], home_tenant_id=None, + def __init__(self, id, display_name, state, tenant_id, home_tenant_id=None, managed_by_tenants=[], tenant_display_name=None, tenant_default_domain=None): # pylint: disable=redefined-builtin policies = SubscriptionPolicies() policies.spending_limit = SpendingLimit.current_period_off @@ -1858,8 +1860,7 @@ def __init__(self, id, display_name, state, tenant_id, managed_by_tenants=[], ho self.managed_by_tenants = managed_by_tenants # Below attributes are added by CLI. Without them, this denotes a Subscription from SDK - if home_tenant_id: - self.home_tenant_id = home_tenant_id + self.home_tenant_id = home_tenant_id if tenant_display_name: self.tenant_display_name = tenant_display_name if tenant_default_domain: @@ -1894,39 +1895,29 @@ def test_attach_token_tenant_v2022_12_01(self): def test_transform_subscription_for_multiapi(self): class SimpleSubscription: - pass + def __init__(self): + self.home_tenant_id = tenant_id + self.managed_by_tenants = [] class SimpleManagedByTenant: pass tenant_id = "00000001-0000-0000-0000-000000000000" - # No 2019-06-01 property is set. - s = SimpleSubscription() - d = {} - _transform_subscription_for_multiapi(s, d) - assert d == {} - - # home_tenant_id is set. + # managed_by_tenants is set, but is []. It is still preserved. s = SimpleSubscription() - s.home_tenant_id = tenant_id d = {} _transform_subscription_for_multiapi(s, d) - assert d == {'homeTenantId': '00000001-0000-0000-0000-000000000000'} + assert d == {'homeTenantId': '00000001-0000-0000-0000-000000000000', + 'managedByTenants': []} # managed_by_tenants is set, but is None. It is still preserved. s = SimpleSubscription() s.managed_by_tenants = None d = {} _transform_subscription_for_multiapi(s, d) - assert d == {'managedByTenants': None} - - # managed_by_tenants is set, but is []. It is still preserved. - s = SimpleSubscription() - s.managed_by_tenants = [] - d = {} - _transform_subscription_for_multiapi(s, d) - assert d == {'managedByTenants': []} + assert d == {'homeTenantId': '00000001-0000-0000-0000-000000000000', + 'managedByTenants': None} # managed_by_tenants is set, and has valid items. It is preserved. s = SimpleSubscription() @@ -1935,7 +1926,8 @@ class SimpleManagedByTenant: s.managed_by_tenants = [t] d = {} _transform_subscription_for_multiapi(s, d) - assert d == {'managedByTenants': [{"tenantId": tenant_id}]} + assert d == {'homeTenantId': '00000001-0000-0000-0000-000000000000', + 'managedByTenants': [{"tenantId": tenant_id}]} if __name__ == '__main__':