From a7eabc257d4d4d43851c55f0746d223b26eb5a26 Mon Sep 17 00:00:00 2001 From: Laurent Mazuel Date: Tue, 3 Apr 2018 13:54:09 -0700 Subject: [PATCH] Add profile to SDK (#2247) * Add profile to SDK * Feedback from Derek * Doc update * Update Storage with new Profile * Update Compute with new Profile * Update Resource with new Profile * Improve ResourceGroupPreparer to provide the id * Migrate all Resources tests to new framework * Generic ChangeLog with Profiles * Add RequestUrlNormalizer to SDK processors --- azure-common/azure/profiles/__init__.py | 127 ++++++++ azure-common/azure/profiles/multiapiclient.py | 81 +++++ azure-common/tests/test_profile.py | 80 +++++ azure-mgmt-compute/HISTORY.rst | 8 + .../mgmt/compute/compute_management_client.py | 74 +++-- azure-mgmt-network/HISTORY.rst | 7 + .../mgmt/network/network_management_client.py | 133 +++++---- azure-mgmt-resource/HISTORY.rst | 7 + .../mgmt/resource/features/feature_client.py | 34 ++- .../resource/links/management_link_client.py | 33 ++- .../resource/locks/management_lock_client.py | 30 +- .../mgmt/resource/policy/policy_client.py | 38 ++- .../resources/resource_management_client.py | 44 ++- .../subscriptions/subscription_client.py | 35 ++- .../test_mgmt_resource.test_deployments.yaml | 0 ...urce.test_deployments_linked_template.yaml | 0 ...est_deployments_linked_template_error.yaml | 0 ...mgmt_resource.test_provider_locations.yaml | 0 .../test_mgmt_resource.test_providers.yaml | 0 ...st_mgmt_resource.test_resource_groups.yaml | 0 .../test_mgmt_resource.test_resources.yaml | 0 ...est_mgmt_resource.test_tag_operations.yaml | 0 ..._mgmt_resource_features.test_features.yaml | 0 .../test_mgmt_resource_links.test_links.yaml | 196 ++++++++++++ .../test_mgmt_resource_locks.test_locks.yaml | 0 ...urce_subscriptions.test_subscriptions.yaml | 0 ...t_resource_subscriptions.test_tenants.yaml | 0 .../tests/test_mgmt_resource.py | 92 +++--- .../tests/test_mgmt_resource_features.py | 5 +- .../tests/test_mgmt_resource_links.py | 71 +++++ .../tests/test_mgmt_resource_locks.py | 16 +- .../tests/test_mgmt_resource_subscriptions.py | 6 +- azure-mgmt-storage/HISTORY.rst | 7 + .../mgmt/storage/storage_management_client.py | 39 ++- .../test_mgmt_resource_links.test_links.yaml | 280 ------------------ azure-mgmt/tests/test_mgmt_resource_links.py | 83 ------ .../devtools_testutils/mgmt_testcase.py | 9 +- .../devtools_testutils/resource_testcase.py | 5 +- scripts/multiapi_init_gen.py | 2 +- 39 files changed, 931 insertions(+), 611 deletions(-) create mode 100644 azure-common/azure/profiles/__init__.py create mode 100644 azure-common/azure/profiles/multiapiclient.py create mode 100644 azure-common/tests/test_profile.py rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource.test_deployments.yaml (100%) rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource.test_deployments_linked_template.yaml (100%) rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource.test_deployments_linked_template_error.yaml (100%) rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource.test_provider_locations.yaml (100%) rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource.test_providers.yaml (100%) rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource.test_resource_groups.yaml (100%) rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource.test_resources.yaml (100%) rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource.test_tag_operations.yaml (100%) rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource_features.test_features.yaml (100%) create mode 100644 azure-mgmt-resource/tests/recordings/test_mgmt_resource_links.test_links.yaml rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource_locks.test_locks.yaml (100%) rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource_subscriptions.test_subscriptions.yaml (100%) rename {azure-mgmt => azure-mgmt-resource}/tests/recordings/test_mgmt_resource_subscriptions.test_tenants.yaml (100%) rename {azure-mgmt => azure-mgmt-resource}/tests/test_mgmt_resource.py (87%) rename {azure-mgmt => azure-mgmt-resource}/tests/test_mgmt_resource_features.py (92%) create mode 100644 azure-mgmt-resource/tests/test_mgmt_resource_links.py rename {azure-mgmt => azure-mgmt-resource}/tests/test_mgmt_resource_locks.py (79%) rename {azure-mgmt => azure-mgmt-resource}/tests/test_mgmt_resource_subscriptions.py (92%) delete mode 100644 azure-mgmt/tests/recordings/test_mgmt_resource_links.test_links.yaml delete mode 100644 azure-mgmt/tests/test_mgmt_resource_links.py diff --git a/azure-common/azure/profiles/__init__.py b/azure-common/azure/profiles/__init__.py new file mode 100644 index 000000000000..cf7165f317da --- /dev/null +++ b/azure-common/azure/profiles/__init__.py @@ -0,0 +1,127 @@ +#------------------------------------------------------------------------- +# Copyright (c) Microsoft Corporation. All rights reserved. +# Licensed under the MIT License. See License.txt in the project root for +# license information. +#-------------------------------------------------------------------------- +from enum import Enum + +class ProfileDefinition(object): + """Allow to define a custom Profile definition. + + Note:: + + The dict format taken as input is yet to be confirmed and should + *not* be considered as stable in the current implementation. + + :param dict profile_dict: A profile dictionnary + :param str label: A label for pretty printing + """ + def __init__(self, profile_dict, label=None): + self._profile_dict = profile_dict + self._label = label + + @property + def label(self): + """The label associated to this profile definition. + """ + return self._label + + def __repr__(self): + return self._label if self._label else self._profile_dict.__repr__() + + def get_profile_dict(self): + """Return the current profile dict. + + This is internal information, and content should not be considered stable. + """ + return self._profile_dict + + +class DefaultProfile(object): + """Store a default profile. + + :var ProfileDefinition profile: The default profile as class attribute + """ + profile = None + + def use(self, profile): + """Define a new default profile.""" + if not isinstance(profile, (KnownProfiles, ProfileDefinition)): + raise ValueError("Can only set as default a ProfileDefinition or a KnownProfiles") + type(self).profile = profile + + def definition(self): + return type(self).profile + +class KnownProfiles(Enum): + """This defines known Azure Profiles. + + There is two meta-profiles: + + - latest : will always use latest available api-version on each package + - default : mutable, will define profile automatically for all packages + + If you change default, this changes all created packages on the fly to + this profile. This can be used to switch a complete set of API Version + without re-creating all clients. + """ + + # default - This is a meta-profile and point to another profile + default = DefaultProfile() + # latest - This is a meta-profile and does not contain definitions + latest = ProfileDefinition(None, "latest") + v2017_03_09_profile = ProfileDefinition( + { + "azure.mgmt.compute.ComputeManagementClient": { + None: "2016-03-30" + }, + "azure.mgmt.network.NetworkManagementClient": { + None: "2015-06-15" + }, + "azure.mgmt.storage.StorageManagementClient": { + None: "2016-01-01" + }, + "azure.mgmt.resource.policy.PolicyClient": { + None: "2015-10-01-preview" + }, + "azure.mgmt.resource.locks.ManagementLockClient": { + None: "2015-01-01" + }, + "azure.mgmt.resource.links.ManagementLinkClient": { + None: "2016-09-01" + }, + "azure.mgmt.resource.resources.ResourceManagementClient": { + None: "2016-02-01" + }, + "azure.mgmt.resource.subscriptions.SubscriptionClient": { + None: "2016-06-01" + } + }, + "2017-03-09-profile" + ) + + def __init__(self, profile_definition): + self._profile_definition = profile_definition + + def use(self, profile): + if self is not type(self).default: + raise ValueError("use can only be used for `default` profile") + self.value.use(profile) + + def definition(self): + if self is not type(self).default: + raise ValueError("use can only be used for `default` profile") + return self.value.definition() + + @classmethod + def from_name(cls, profile_name): + if profile_name == "default": + return cls.default + for profile in cls: + if isinstance(profile.value, ProfileDefinition) and profile.value.label == profile_name: + return profile + raise ValueError("No profile called {}".format(profile_name)) + + +# Default profile is floating "latest" +KnownProfiles.default.use(KnownProfiles.latest) \ No newline at end of file diff --git a/azure-common/azure/profiles/multiapiclient.py b/azure-common/azure/profiles/multiapiclient.py new file mode 100644 index 000000000000..4cd18cdccc68 --- /dev/null +++ b/azure-common/azure/profiles/multiapiclient.py @@ -0,0 +1,81 @@ +#------------------------------------------------------------------------- +# Copyright (c) Microsoft Corporation. All rights reserved. +# Licensed under the MIT License. See License.txt in the project root for +# license information. +#-------------------------------------------------------------------------- +from . import KnownProfiles, ProfileDefinition + +class InvalidMultiApiClientError(Exception): + """If the mixin is not used with a compatible class. + """ + pass + +class MultiApiClientMixin(object): + """Mixin that contains multi-api version profile management. + + To use this mixin, a client must define two class attributes: + - LATEST_PROFILE : a ProfileDefinition correspond to latest profile + - _PROFILE_TAG : a tag that filter a full profile for this particular client + + This should not be used directly and will only provide private methods. + """ + + def __init__(self, api_version=None, profile=KnownProfiles.default, **kwargs): + + try: + type(self).LATEST_PROFILE + except AttributeError: + raise InvalidMultiApiClientError("To use this mixin, main client MUST define LATEST_PROFILE class attribute") + + try: + type(self)._PROFILE_TAG + except AttributeError: + raise InvalidMultiApiClientError("To use this mixin, main client MUST define _PROFILE_TAG class attribute") + + if api_version and profile is not KnownProfiles.default: + raise ValueError("Cannot use api-version and profile parameters at the same time") + + if api_version: + self.profile = ProfileDefinition({ + self._PROFILE_TAG: { + None: api_version + }}, + self._PROFILE_TAG + " " + api_version + ) + elif isinstance(profile, dict): + self.profile = ProfileDefinition({ + self._PROFILE_TAG: profile, + }, + self._PROFILE_TAG + " dict" + ) + if api_version: + self.profile._profile_dict[self._PROFILE_TAG][None] = api_version + else: + self.profile = profile + + def _get_api_version(self, operation_group_name): + current_profile = self.profile + if self.profile is KnownProfiles.default: + current_profile = KnownProfiles.default.value.definition() + + if current_profile is KnownProfiles.latest: + current_profile = self.LATEST_PROFILE + elif isinstance(current_profile, KnownProfiles): + current_profile = current_profile.value + elif isinstance(current_profile, ProfileDefinition): + pass # I expect that + else: + raise ValueError("Cannot determine a ProfileDefinition from {}".format(self.profile)) + + local_profile_dict = current_profile.get_profile_dict() + if self._PROFILE_TAG not in local_profile_dict: + raise ValueError("This profile doesn't define {}".format(self._PROFILE_TAG)) + + local_profile = local_profile_dict[self._PROFILE_TAG] + if operation_group_name in local_profile: + return local_profile[operation_group_name] + try: + return local_profile[None] + except KeyError: + raise ValueError("This profile definition does not contain a default API version") + \ No newline at end of file diff --git a/azure-common/tests/test_profile.py b/azure-common/tests/test_profile.py new file mode 100644 index 000000000000..c99d7f481841 --- /dev/null +++ b/azure-common/tests/test_profile.py @@ -0,0 +1,80 @@ +#------------------------------------------------------------------------- +# Copyright (c) Microsoft Corporation. All rights reserved. +# Licensed under the MIT License. See License.txt in the project root for +# license information. +#-------------------------------------------------------------------------- +from azure.profiles import ProfileDefinition, KnownProfiles +from azure.profiles.multiapiclient import MultiApiClientMixin + +import pytest + +def test_profile_from_string(): + profile_from_string = KnownProfiles.from_name("2017-03-09-profile") + assert profile_from_string is KnownProfiles.v2017_03_09_profile + + with pytest.raises(ValueError): + KnownProfiles.from_name("blablabla") + +def test_default_profile(): + with pytest.raises(ValueError): + KnownProfiles.default.use("This is not a profile") + +def test_multiapi_client(): + + class TestClient(MultiApiClientMixin): + DEFAULT_API_VERSION = "2216-08-09" + _PROFILE_TAG = "azure.mgmt.compute.ComputeManagementClient" + LATEST_PROFILE = ProfileDefinition({ + _PROFILE_TAG: { + None: DEFAULT_API_VERSION + }}, + _PROFILE_TAG + " latest" + ) + + def __init__(self, api_version=None, profile=KnownProfiles.default): + super(TestClient, self).__init__(api_version=api_version, profile=profile) + + def operations(self): + return self._get_api_version("operations") + + # By default, use latest + client = TestClient() + assert client.operations() == TestClient.DEFAULT_API_VERSION + + # Dynamically change to a new profile + KnownProfiles.default.use(KnownProfiles.v2017_03_09_profile) + assert client.operations() == "2016-03-30" + + # I ask explicitly latest, where the default is not that + client = TestClient(profile=KnownProfiles.latest) + assert client.operations() == TestClient.DEFAULT_API_VERSION + + # Bring back default to latest for next tests + KnownProfiles.default.use(KnownProfiles.latest) + + # I asked explicily a specific profile, must not be latest + client = TestClient(profile=KnownProfiles.v2017_03_09_profile) + assert client.operations() == "2016-03-30" + + # I refuse api_version and profile at the same time + # https://github.com/Azure/azure-sdk-for-python/issues/1864 + with pytest.raises(ValueError): + TestClient(api_version="something", profile=KnownProfiles.latest) + + # If I provide only api_version, this creates a profile with just that + client = TestClient(api_version="2666-05-15") + assert client.operations() == "2666-05-15" + + # I can specify old profile syntax with dict + client = TestClient(profile={ + "operations": "1789-07-14" + }) + assert client.operations() == "1789-07-14" + + # If I give a profile definition with no default api-version + # and I call a method not define in the profile, this fails + client = TestClient(profile={ + "operations2": "1789-07-14" + }) + with pytest.raises(ValueError): + client.operations() == "1789-07-14" diff --git a/azure-mgmt-compute/HISTORY.rst b/azure-mgmt-compute/HISTORY.rst index 1b8f841eaf8a..3ef897b311f8 100644 --- a/azure-mgmt-compute/HISTORY.rst +++ b/azure-mgmt-compute/HISTORY.rst @@ -3,6 +3,14 @@ Release History =============== +XXXXXXXXXXXX +++++++++++++ + +**Features** + +- All clients now support Azure profiles. + + 4.0.0rc1 (2018-03-21) +++++++++++++++++++++ diff --git a/azure-mgmt-compute/azure/mgmt/compute/compute_management_client.py b/azure-mgmt-compute/azure/mgmt/compute/compute_management_client.py index c54a9cac4d06..d23dace4f604 100644 --- a/azure-mgmt-compute/azure/mgmt/compute/compute_management_client.py +++ b/azure-mgmt-compute/azure/mgmt/compute/compute_management_client.py @@ -12,6 +12,9 @@ from msrest.service_client import ServiceClient from msrest import Serializer, Deserializer from msrestazure import AzureConfiguration + +from azure.profiles import KnownProfiles, ProfileDefinition +from azure.profiles.multiapiclient import MultiApiClientMixin from .version import VERSION @@ -49,7 +52,7 @@ def __init__( self.subscription_id = subscription_id -class ComputeManagementClient(object): +class ComputeManagementClient(MultiApiClientMixin): """Compute Client. This ready contains multiple API versions, to help you deal with all Azure clouds @@ -73,25 +76,34 @@ class ComputeManagementClient(object): :param str api_version: API version to use if no profile is provided, or if missing in profile. :param str base_url: Service URL - :param profile: A dict using operation group name to API version. - :type profile: dict[str, str] + :param profile: A profile definition, from KnownProfiles to dict. + :type profile: azure.profiles.KnownProfiles """ DEFAULT_API_VERSION = '2017-12-01' - DEFAULT_PROFILE = { - 'disks': '2018-04-01', - 'resource_skus': '2017-09-01', - 'snapshots': '2018-04-01', - } - - def __init__(self, credentials, subscription_id, api_version=DEFAULT_API_VERSION, base_url=None, profile=DEFAULT_PROFILE): + _PROFILE_TAG = "azure.mgmt.compute.ComputeManagementClient" + LATEST_PROFILE = ProfileDefinition({ + _PROFILE_TAG: { + 'disks': '2018-04-01', + 'resource_skus': '2017-09-01', + 'snapshots': '2018-04-01', + None: DEFAULT_API_VERSION + }}, + _PROFILE_TAG + " latest" + ) + + def __init__(self, credentials, subscription_id, api_version=None, base_url=None, profile=KnownProfiles.default): + super(ComputeManagementClient, self).__init__( + credentials=credentials, + subscription_id=subscription_id, + api_version=api_version, + base_url=base_url, + profile=profile + ) self.config = ComputeManagementClientConfiguration(credentials, subscription_id, base_url) self._client = ServiceClient(self.config.credentials, self.config) - self.api_version = api_version - self.profile = dict(profile) if profile is not None else {} - ############ Generated from here ############ @classmethod @@ -143,7 +155,7 @@ def availability_sets(self): * 2017-03-30: :class:`AvailabilitySetsOperations` * 2017-12-01: :class:`AvailabilitySetsOperations` """ - api_version = self.profile.get('availability_sets', self.api_version) + api_version = self._get_api_version('availability_sets') if api_version == '2015-06-15': from .v2015_06_15.operations import AvailabilitySetsOperations as OperationClass elif api_version == '2016-03-30': @@ -166,7 +178,7 @@ def disks(self): * 2017-03-30: :class:`DisksOperations` * 2018-04-01: :class:`DisksOperations` """ - api_version = self.profile.get('disks', self.api_version) + api_version = self._get_api_version('disks') if api_version == '2016-04-30-preview': from .v2016_04_30_preview.operations import DisksOperations as OperationClass elif api_version == '2017-03-30': @@ -185,7 +197,7 @@ def images(self): * 2017-03-30: :class:`ImagesOperations` * 2017-12-01: :class:`ImagesOperations` """ - api_version = self.profile.get('images', self.api_version) + api_version = self._get_api_version('images') if api_version == '2016-04-30-preview': from .v2016_04_30_preview.operations import ImagesOperations as OperationClass elif api_version == '2017-03-30': @@ -202,7 +214,7 @@ def log_analytics(self): * 2017-12-01: :class:`LogAnalyticsOperations` """ - api_version = self.profile.get('log_analytics', self.api_version) + api_version = self._get_api_version('log_analytics') if api_version == '2017-12-01': from .v2017_12_01.operations import LogAnalyticsOperations as OperationClass else: @@ -215,7 +227,7 @@ def operations(self): * 2017-12-01: :class:`Operations` """ - api_version = self.profile.get('operations', self.api_version) + api_version = self._get_api_version('operations') if api_version == '2017-12-01': from .v2017_12_01.operations import Operations as OperationClass else: @@ -229,7 +241,7 @@ def resource_skus(self): * 2017-03-30: :class:`ResourceSkusOperations` * 2017-09-01: :class:`ResourceSkusOperations` """ - api_version = self.profile.get('resource_skus', self.api_version) + api_version = self._get_api_version('resource_skus') if api_version == '2017-03-30': from .v2017_03_30.operations import ResourceSkusOperations as OperationClass elif api_version == '2017-09-01': @@ -246,7 +258,7 @@ def snapshots(self): * 2017-03-30: :class:`SnapshotsOperations` * 2018-04-01: :class:`SnapshotsOperations` """ - api_version = self.profile.get('snapshots', self.api_version) + api_version = self._get_api_version('snapshots') if api_version == '2016-04-30-preview': from .v2016_04_30_preview.operations import SnapshotsOperations as OperationClass elif api_version == '2017-03-30': @@ -267,7 +279,7 @@ def usage(self): * 2017-03-30: :class:`UsageOperations` * 2017-12-01: :class:`UsageOperations` """ - api_version = self.profile.get('usage', self.api_version) + api_version = self._get_api_version('usage') if api_version == '2015-06-15': from .v2015_06_15.operations import UsageOperations as OperationClass elif api_version == '2016-03-30': @@ -292,7 +304,7 @@ def virtual_machine_extension_images(self): * 2017-03-30: :class:`VirtualMachineExtensionImagesOperations` * 2017-12-01: :class:`VirtualMachineExtensionImagesOperations` """ - api_version = self.profile.get('virtual_machine_extension_images', self.api_version) + api_version = self._get_api_version('virtual_machine_extension_images') if api_version == '2015-06-15': from .v2015_06_15.operations import VirtualMachineExtensionImagesOperations as OperationClass elif api_version == '2016-03-30': @@ -317,7 +329,7 @@ def virtual_machine_extensions(self): * 2017-03-30: :class:`VirtualMachineExtensionsOperations` * 2017-12-01: :class:`VirtualMachineExtensionsOperations` """ - api_version = self.profile.get('virtual_machine_extensions', self.api_version) + api_version = self._get_api_version('virtual_machine_extensions') if api_version == '2015-06-15': from .v2015_06_15.operations import VirtualMachineExtensionsOperations as OperationClass elif api_version == '2016-03-30': @@ -342,7 +354,7 @@ def virtual_machine_images(self): * 2017-03-30: :class:`VirtualMachineImagesOperations` * 2017-12-01: :class:`VirtualMachineImagesOperations` """ - api_version = self.profile.get('virtual_machine_images', self.api_version) + api_version = self._get_api_version('virtual_machine_images') if api_version == '2015-06-15': from .v2015_06_15.operations import VirtualMachineImagesOperations as OperationClass elif api_version == '2016-03-30': @@ -364,7 +376,7 @@ def virtual_machine_run_commands(self): * 2017-03-30: :class:`VirtualMachineRunCommandsOperations` * 2017-12-01: :class:`VirtualMachineRunCommandsOperations` """ - api_version = self.profile.get('virtual_machine_run_commands', self.api_version) + api_version = self._get_api_version('virtual_machine_run_commands') if api_version == '2017-03-30': from .v2017_03_30.operations import VirtualMachineRunCommandsOperations as OperationClass elif api_version == '2017-12-01': @@ -380,7 +392,7 @@ def virtual_machine_scale_set_extensions(self): * 2017-03-30: :class:`VirtualMachineScaleSetExtensionsOperations` * 2017-12-01: :class:`VirtualMachineScaleSetExtensionsOperations` """ - api_version = self.profile.get('virtual_machine_scale_set_extensions', self.api_version) + api_version = self._get_api_version('virtual_machine_scale_set_extensions') if api_version == '2017-03-30': from .v2017_03_30.operations import VirtualMachineScaleSetExtensionsOperations as OperationClass elif api_version == '2017-12-01': @@ -396,7 +408,7 @@ def virtual_machine_scale_set_rolling_upgrades(self): * 2017-03-30: :class:`VirtualMachineScaleSetRollingUpgradesOperations` * 2017-12-01: :class:`VirtualMachineScaleSetRollingUpgradesOperations` """ - api_version = self.profile.get('virtual_machine_scale_set_rolling_upgrades', self.api_version) + api_version = self._get_api_version('virtual_machine_scale_set_rolling_upgrades') if api_version == '2017-03-30': from .v2017_03_30.operations import VirtualMachineScaleSetRollingUpgradesOperations as OperationClass elif api_version == '2017-12-01': @@ -415,7 +427,7 @@ def virtual_machine_scale_set_vms(self): * 2017-03-30: :class:`VirtualMachineScaleSetVMsOperations` * 2017-12-01: :class:`VirtualMachineScaleSetVMsOperations` """ - api_version = self.profile.get('virtual_machine_scale_set_vms', self.api_version) + api_version = self._get_api_version('virtual_machine_scale_set_vms') if api_version == '2015-06-15': from .v2015_06_15.operations import VirtualMachineScaleSetVMsOperations as OperationClass elif api_version == '2016-03-30': @@ -440,7 +452,7 @@ def virtual_machine_scale_sets(self): * 2017-03-30: :class:`VirtualMachineScaleSetsOperations` * 2017-12-01: :class:`VirtualMachineScaleSetsOperations` """ - api_version = self.profile.get('virtual_machine_scale_sets', self.api_version) + api_version = self._get_api_version('virtual_machine_scale_sets') if api_version == '2015-06-15': from .v2015_06_15.operations import VirtualMachineScaleSetsOperations as OperationClass elif api_version == '2016-03-30': @@ -465,7 +477,7 @@ def virtual_machine_sizes(self): * 2017-03-30: :class:`VirtualMachineSizesOperations` * 2017-12-01: :class:`VirtualMachineSizesOperations` """ - api_version = self.profile.get('virtual_machine_sizes', self.api_version) + api_version = self._get_api_version('virtual_machine_sizes') if api_version == '2015-06-15': from .v2015_06_15.operations import VirtualMachineSizesOperations as OperationClass elif api_version == '2016-03-30': @@ -490,7 +502,7 @@ def virtual_machines(self): * 2017-03-30: :class:`VirtualMachinesOperations` * 2017-12-01: :class:`VirtualMachinesOperations` """ - api_version = self.profile.get('virtual_machines', self.api_version) + api_version = self._get_api_version('virtual_machines') if api_version == '2015-06-15': from .v2015_06_15.operations import VirtualMachinesOperations as OperationClass elif api_version == '2016-03-30': diff --git a/azure-mgmt-network/HISTORY.rst b/azure-mgmt-network/HISTORY.rst index 6f91f0af2ca0..58d93925be84 100644 --- a/azure-mgmt-network/HISTORY.rst +++ b/azure-mgmt-network/HISTORY.rst @@ -3,6 +3,13 @@ Release History =============== +XXXXXXXXXXXX +++++++++++++ + +**Features** + +- All clients now support Azure profiles. + 2.0.0rc1 (2018-03-07) +++++++++++++++++++++ diff --git a/azure-mgmt-network/azure/mgmt/network/network_management_client.py b/azure-mgmt-network/azure/mgmt/network/network_management_client.py index 51cbc40eabaa..778dc54fc37a 100644 --- a/azure-mgmt-network/azure/mgmt/network/network_management_client.py +++ b/azure-mgmt-network/azure/mgmt/network/network_management_client.py @@ -12,6 +12,9 @@ from msrest.service_client import ServiceClient from msrest import Serializer, Deserializer from msrestazure import AzureConfiguration + +from azure.profiles import KnownProfiles, ProfileDefinition +from azure.profiles.multiapiclient import MultiApiClientMixin from .version import VERSION @@ -49,7 +52,7 @@ def __init__( self.subscription_id = subscription_id -class NetworkManagementClient(object): +class NetworkManagementClient(MultiApiClientMixin): """Network Client This ready contains multiple API versions, to help you deal with all Azure clouds @@ -73,22 +76,31 @@ class NetworkManagementClient(object): :param str api_version: API version to use if no profile is provided, or if missing in profile. :param str base_url: Service URL - :param profile: A dict using operation group name to API version. - :type profile: dict[str, str] + :param profile: A profile definition, from KnownProfiles to dict. + :type profile: azure.profiles.KnownProfiles """ - DEFAULT_API_VERSION='2017-11-01' - DEFAULT_PROFILE = None - - def __init__(self, credentials, subscription_id, api_version=DEFAULT_API_VERSION, base_url=None, profile=DEFAULT_PROFILE): + DEFAULT_API_VERSION = '2017-11-01' + _PROFILE_TAG = "azure.mgmt.network.NetworkManagementClient" + LATEST_PROFILE = ProfileDefinition({ + _PROFILE_TAG: { + None: DEFAULT_API_VERSION + }}, + _PROFILE_TAG + " latest" + ) + + def __init__(self, credentials, subscription_id, api_version=None, base_url=None, profile=KnownProfiles.default): + super(NetworkManagementClient, self).__init__( + credentials=credentials, + subscription_id=subscription_id, + api_version=api_version, + base_url=base_url, + profile=profile + ) self.config = NetworkManagementClientConfiguration(credentials, subscription_id, base_url) self._client = ServiceClient(self.config.credentials, self.config) - client_models = {k: v for k, v in self.models(api_version).__dict__.items() if isinstance(v, type)} - self.api_version = api_version - self.profile = dict(profile) if profile is not None else {} - def check_dns_name_availability( self, location, domain_name_label, custom_headers=None, raw=False, **operation_config): """Checks whether a domain name in the cloudapp.azure.com zone is @@ -106,31 +118,34 @@ def check_dns_name_availability( :param operation_config: :ref:`Operation configuration overrides`. :return: :class:`DnsNameAvailabilityResult - ` or + ` or :class:`ClientRawResponse` if raw=true :rtype: :class:`DnsNameAvailabilityResult - ` or + ` or :class:`ClientRawResponse` :raises: :class:`CloudError` """ - if self.api_version == '2017-11-01': + api_version = self._get_api_version('check_dns_name_availability') + if api_version == '2018-01-01': + from .v2018_01_01 import NetworkManagementClient as ClientClass + elif api_version == '2017-11-01': from .v2017_11_01 import NetworkManagementClient as ClientClass - elif self.api_version == '2017-10-01': + elif api_version == '2017-10-01': from .v2017_10_01 import NetworkManagementClient as ClientClass - elif self.api_version == '2017-09-01': + elif api_version == '2017-09-01': from .v2017_09_01 import NetworkManagementClient as ClientClass - elif self.api_version == '2017-08-01': + elif api_version == '2017-08-01': from .v2017_08_01 import NetworkManagementClient as ClientClass - elif self.api_version == '2017-06-01': + elif api_version == '2017-06-01': from .v2017_06_01 import NetworkManagementClient as ClientClass - elif self.api_version == '2017-03-01': + elif api_version == '2017-03-01': from .v2017_03_01 import NetworkManagementClient as ClientClass - elif self.api_version == '2016-12-01': + elif api_version == '2016-12-01': from .v2016_12_01 import NetworkManagementClient as ClientClass - elif self.api_version == '2016-09-01': + elif api_version == '2016-09-01': from .v2016_09_01 import NetworkManagementClient as ClientClass - elif self.api_version == '2015-06-15': + elif api_version == '2015-06-15': from .v2015_06_15 import NetworkManagementClient as ClientClass localclient = ClientClass(self.config.credentials, self.config.subscription_id, @@ -209,7 +224,7 @@ def application_gateways(self): * 2017-11-01: :class:`ApplicationGatewaysOperations` * 2018-01-01: :class:`ApplicationGatewaysOperations` """ - api_version = self.profile.get('application_gateways', self.api_version) + api_version = self._get_api_version('application_gateways') if api_version == '2015-06-15': from .v2015_06_15.operations import ApplicationGatewaysOperations as OperationClass elif api_version == '2016-09-01': @@ -243,7 +258,7 @@ def application_security_groups(self): * 2017-11-01: :class:`ApplicationSecurityGroupsOperations` * 2018-01-01: :class:`ApplicationSecurityGroupsOperations` """ - api_version = self.profile.get('application_security_groups', self.api_version) + api_version = self._get_api_version('application_security_groups') if api_version == '2017-09-01': from .v2017_09_01.operations import ApplicationSecurityGroupsOperations as OperationClass elif api_version == '2017-10-01': @@ -267,7 +282,7 @@ def available_endpoint_services(self): * 2017-11-01: :class:`AvailableEndpointServicesOperations` * 2018-01-01: :class:`AvailableEndpointServicesOperations` """ - api_version = self.profile.get('available_endpoint_services', self.api_version) + api_version = self._get_api_version('available_endpoint_services') if api_version == '2017-06-01': from .v2017_06_01.operations import AvailableEndpointServicesOperations as OperationClass elif api_version == '2017-08-01': @@ -297,7 +312,7 @@ def bgp_service_communities(self): * 2017-11-01: :class:`BgpServiceCommunitiesOperations` * 2018-01-01: :class:`BgpServiceCommunitiesOperations` """ - api_version = self.profile.get('bgp_service_communities', self.api_version) + api_version = self._get_api_version('bgp_service_communities') if api_version == '2016-12-01': from .v2016_12_01.operations import BgpServiceCommunitiesOperations as OperationClass elif api_version == '2017-03-01': @@ -326,7 +341,7 @@ def connection_monitors(self): * 2017-11-01: :class:`ConnectionMonitorsOperations` * 2018-01-01: :class:`ConnectionMonitorsOperations` """ - api_version = self.profile.get('connection_monitors', self.api_version) + api_version = self._get_api_version('connection_monitors') if api_version == '2017-10-01': from .v2017_10_01.operations import ConnectionMonitorsOperations as OperationClass elif api_version == '2017-11-01': @@ -348,7 +363,7 @@ def default_security_rules(self): * 2017-11-01: :class:`DefaultSecurityRulesOperations` * 2018-01-01: :class:`DefaultSecurityRulesOperations` """ - api_version = self.profile.get('default_security_rules', self.api_version) + api_version = self._get_api_version('default_security_rules') if api_version == '2017-06-01': from .v2017_06_01.operations import DefaultSecurityRulesOperations as OperationClass elif api_version == '2017-08-01': @@ -380,7 +395,7 @@ def express_route_circuit_authorizations(self): * 2017-11-01: :class:`ExpressRouteCircuitAuthorizationsOperations` * 2018-01-01: :class:`ExpressRouteCircuitAuthorizationsOperations` """ - api_version = self.profile.get('express_route_circuit_authorizations', self.api_version) + api_version = self._get_api_version('express_route_circuit_authorizations') if api_version == '2015-06-15': from .v2015_06_15.operations import ExpressRouteCircuitAuthorizationsOperations as OperationClass elif api_version == '2016-09-01': @@ -420,7 +435,7 @@ def express_route_circuit_peerings(self): * 2017-11-01: :class:`ExpressRouteCircuitPeeringsOperations` * 2018-01-01: :class:`ExpressRouteCircuitPeeringsOperations` """ - api_version = self.profile.get('express_route_circuit_peerings', self.api_version) + api_version = self._get_api_version('express_route_circuit_peerings') if api_version == '2015-06-15': from .v2015_06_15.operations import ExpressRouteCircuitPeeringsOperations as OperationClass elif api_version == '2016-09-01': @@ -460,7 +475,7 @@ def express_route_circuits(self): * 2017-11-01: :class:`ExpressRouteCircuitsOperations` * 2018-01-01: :class:`ExpressRouteCircuitsOperations` """ - api_version = self.profile.get('express_route_circuits', self.api_version) + api_version = self._get_api_version('express_route_circuits') if api_version == '2015-06-15': from .v2015_06_15.operations import ExpressRouteCircuitsOperations as OperationClass elif api_version == '2016-09-01': @@ -500,7 +515,7 @@ def express_route_service_providers(self): * 2017-11-01: :class:`ExpressRouteServiceProvidersOperations` * 2018-01-01: :class:`ExpressRouteServiceProvidersOperations` """ - api_version = self.profile.get('express_route_service_providers', self.api_version) + api_version = self._get_api_version('express_route_service_providers') if api_version == '2015-06-15': from .v2015_06_15.operations import ExpressRouteServiceProvidersOperations as OperationClass elif api_version == '2016-09-01': @@ -536,7 +551,7 @@ def inbound_nat_rules(self): * 2017-11-01: :class:`InboundNatRulesOperations` * 2018-01-01: :class:`InboundNatRulesOperations` """ - api_version = self.profile.get('inbound_nat_rules', self.api_version) + api_version = self._get_api_version('inbound_nat_rules') if api_version == '2017-06-01': from .v2017_06_01.operations import InboundNatRulesOperations as OperationClass elif api_version == '2017-08-01': @@ -564,7 +579,7 @@ def load_balancer_backend_address_pools(self): * 2017-11-01: :class:`LoadBalancerBackendAddressPoolsOperations` * 2018-01-01: :class:`LoadBalancerBackendAddressPoolsOperations` """ - api_version = self.profile.get('load_balancer_backend_address_pools', self.api_version) + api_version = self._get_api_version('load_balancer_backend_address_pools') if api_version == '2017-06-01': from .v2017_06_01.operations import LoadBalancerBackendAddressPoolsOperations as OperationClass elif api_version == '2017-08-01': @@ -592,7 +607,7 @@ def load_balancer_frontend_ip_configurations(self): * 2017-11-01: :class:`LoadBalancerFrontendIPConfigurationsOperations` * 2018-01-01: :class:`LoadBalancerFrontendIPConfigurationsOperations` """ - api_version = self.profile.get('load_balancer_frontend_ip_configurations', self.api_version) + api_version = self._get_api_version('load_balancer_frontend_ip_configurations') if api_version == '2017-06-01': from .v2017_06_01.operations import LoadBalancerFrontendIPConfigurationsOperations as OperationClass elif api_version == '2017-08-01': @@ -620,7 +635,7 @@ def load_balancer_load_balancing_rules(self): * 2017-11-01: :class:`LoadBalancerLoadBalancingRulesOperations` * 2018-01-01: :class:`LoadBalancerLoadBalancingRulesOperations` """ - api_version = self.profile.get('load_balancer_load_balancing_rules', self.api_version) + api_version = self._get_api_version('load_balancer_load_balancing_rules') if api_version == '2017-06-01': from .v2017_06_01.operations import LoadBalancerLoadBalancingRulesOperations as OperationClass elif api_version == '2017-08-01': @@ -648,7 +663,7 @@ def load_balancer_network_interfaces(self): * 2017-11-01: :class:`LoadBalancerNetworkInterfacesOperations` * 2018-01-01: :class:`LoadBalancerNetworkInterfacesOperations` """ - api_version = self.profile.get('load_balancer_network_interfaces', self.api_version) + api_version = self._get_api_version('load_balancer_network_interfaces') if api_version == '2017-06-01': from .v2017_06_01.operations import LoadBalancerNetworkInterfacesOperations as OperationClass elif api_version == '2017-08-01': @@ -676,7 +691,7 @@ def load_balancer_probes(self): * 2017-11-01: :class:`LoadBalancerProbesOperations` * 2018-01-01: :class:`LoadBalancerProbesOperations` """ - api_version = self.profile.get('load_balancer_probes', self.api_version) + api_version = self._get_api_version('load_balancer_probes') if api_version == '2017-06-01': from .v2017_06_01.operations import LoadBalancerProbesOperations as OperationClass elif api_version == '2017-08-01': @@ -708,7 +723,7 @@ def load_balancers(self): * 2017-11-01: :class:`LoadBalancersOperations` * 2018-01-01: :class:`LoadBalancersOperations` """ - api_version = self.profile.get('load_balancers', self.api_version) + api_version = self._get_api_version('load_balancers') if api_version == '2015-06-15': from .v2015_06_15.operations import LoadBalancersOperations as OperationClass elif api_version == '2016-09-01': @@ -748,7 +763,7 @@ def local_network_gateways(self): * 2017-11-01: :class:`LocalNetworkGatewaysOperations` * 2018-01-01: :class:`LocalNetworkGatewaysOperations` """ - api_version = self.profile.get('local_network_gateways', self.api_version) + api_version = self._get_api_version('local_network_gateways') if api_version == '2015-06-15': from .v2015_06_15.operations import LocalNetworkGatewaysOperations as OperationClass elif api_version == '2016-09-01': @@ -784,7 +799,7 @@ def network_interface_ip_configurations(self): * 2017-11-01: :class:`NetworkInterfaceIPConfigurationsOperations` * 2018-01-01: :class:`NetworkInterfaceIPConfigurationsOperations` """ - api_version = self.profile.get('network_interface_ip_configurations', self.api_version) + api_version = self._get_api_version('network_interface_ip_configurations') if api_version == '2017-06-01': from .v2017_06_01.operations import NetworkInterfaceIPConfigurationsOperations as OperationClass elif api_version == '2017-08-01': @@ -812,7 +827,7 @@ def network_interface_load_balancers(self): * 2017-11-01: :class:`NetworkInterfaceLoadBalancersOperations` * 2018-01-01: :class:`NetworkInterfaceLoadBalancersOperations` """ - api_version = self.profile.get('network_interface_load_balancers', self.api_version) + api_version = self._get_api_version('network_interface_load_balancers') if api_version == '2017-06-01': from .v2017_06_01.operations import NetworkInterfaceLoadBalancersOperations as OperationClass elif api_version == '2017-08-01': @@ -844,7 +859,7 @@ def network_interfaces(self): * 2017-11-01: :class:`NetworkInterfacesOperations` * 2018-01-01: :class:`NetworkInterfacesOperations` """ - api_version = self.profile.get('network_interfaces', self.api_version) + api_version = self._get_api_version('network_interfaces') if api_version == '2015-06-15': from .v2015_06_15.operations import NetworkInterfacesOperations as OperationClass elif api_version == '2016-09-01': @@ -884,7 +899,7 @@ def network_security_groups(self): * 2017-11-01: :class:`NetworkSecurityGroupsOperations` * 2018-01-01: :class:`NetworkSecurityGroupsOperations` """ - api_version = self.profile.get('network_security_groups', self.api_version) + api_version = self._get_api_version('network_security_groups') if api_version == '2015-06-15': from .v2015_06_15.operations import NetworkSecurityGroupsOperations as OperationClass elif api_version == '2016-09-01': @@ -923,7 +938,7 @@ def network_watchers(self): * 2017-11-01: :class:`NetworkWatchersOperations` * 2018-01-01: :class:`NetworkWatchersOperations` """ - api_version = self.profile.get('network_watchers', self.api_version) + api_version = self._get_api_version('network_watchers') if api_version == '2016-09-01': from .v2016_09_01.operations import NetworkWatchersOperations as OperationClass elif api_version == '2016-12-01': @@ -955,7 +970,7 @@ def operations(self): * 2017-11-01: :class:`Operations` * 2018-01-01: :class:`Operations` """ - api_version = self.profile.get('operations', self.api_version) + api_version = self._get_api_version('operations') if api_version == '2017-09-01': from .v2017_09_01.operations import Operations as OperationClass elif api_version == '2017-10-01': @@ -982,7 +997,7 @@ def packet_captures(self): * 2017-11-01: :class:`PacketCapturesOperations` * 2018-01-01: :class:`PacketCapturesOperations` """ - api_version = self.profile.get('packet_captures', self.api_version) + api_version = self._get_api_version('packet_captures') if api_version == '2016-09-01': from .v2016_09_01.operations import PacketCapturesOperations as OperationClass elif api_version == '2016-12-01': @@ -1020,7 +1035,7 @@ def public_ip_addresses(self): * 2017-11-01: :class:`PublicIPAddressesOperations` * 2018-01-01: :class:`PublicIPAddressesOperations` """ - api_version = self.profile.get('public_ip_addresses', self.api_version) + api_version = self._get_api_version('public_ip_addresses') if api_version == '2015-06-15': from .v2015_06_15.operations import PublicIPAddressesOperations as OperationClass elif api_version == '2016-09-01': @@ -1058,7 +1073,7 @@ def route_filter_rules(self): * 2017-11-01: :class:`RouteFilterRulesOperations` * 2018-01-01: :class:`RouteFilterRulesOperations` """ - api_version = self.profile.get('route_filter_rules', self.api_version) + api_version = self._get_api_version('route_filter_rules') if api_version == '2016-12-01': from .v2016_12_01.operations import RouteFilterRulesOperations as OperationClass elif api_version == '2017-03-01': @@ -1092,7 +1107,7 @@ def route_filters(self): * 2017-11-01: :class:`RouteFiltersOperations` * 2018-01-01: :class:`RouteFiltersOperations` """ - api_version = self.profile.get('route_filters', self.api_version) + api_version = self._get_api_version('route_filters') if api_version == '2016-12-01': from .v2016_12_01.operations import RouteFiltersOperations as OperationClass elif api_version == '2017-03-01': @@ -1128,7 +1143,7 @@ def route_tables(self): * 2017-11-01: :class:`RouteTablesOperations` * 2018-01-01: :class:`RouteTablesOperations` """ - api_version = self.profile.get('route_tables', self.api_version) + api_version = self._get_api_version('route_tables') if api_version == '2015-06-15': from .v2015_06_15.operations import RouteTablesOperations as OperationClass elif api_version == '2016-09-01': @@ -1168,7 +1183,7 @@ def routes(self): * 2017-11-01: :class:`RoutesOperations` * 2018-01-01: :class:`RoutesOperations` """ - api_version = self.profile.get('routes', self.api_version) + api_version = self._get_api_version('routes') if api_version == '2015-06-15': from .v2015_06_15.operations import RoutesOperations as OperationClass elif api_version == '2016-09-01': @@ -1208,7 +1223,7 @@ def security_rules(self): * 2017-11-01: :class:`SecurityRulesOperations` * 2018-01-01: :class:`SecurityRulesOperations` """ - api_version = self.profile.get('security_rules', self.api_version) + api_version = self._get_api_version('security_rules') if api_version == '2015-06-15': from .v2015_06_15.operations import SecurityRulesOperations as OperationClass elif api_version == '2016-09-01': @@ -1248,7 +1263,7 @@ def subnets(self): * 2017-11-01: :class:`SubnetsOperations` * 2018-01-01: :class:`SubnetsOperations` """ - api_version = self.profile.get('subnets', self.api_version) + api_version = self._get_api_version('subnets') if api_version == '2015-06-15': from .v2015_06_15.operations import SubnetsOperations as OperationClass elif api_version == '2016-09-01': @@ -1288,7 +1303,7 @@ def usages(self): * 2017-11-01: :class:`UsagesOperations` * 2018-01-01: :class:`UsagesOperations` """ - api_version = self.profile.get('usages', self.api_version) + api_version = self._get_api_version('usages') if api_version == '2015-06-15': from .v2015_06_15.operations import UsagesOperations as OperationClass elif api_version == '2016-09-01': @@ -1328,7 +1343,7 @@ def virtual_network_gateway_connections(self): * 2017-11-01: :class:`VirtualNetworkGatewayConnectionsOperations` * 2018-01-01: :class:`VirtualNetworkGatewayConnectionsOperations` """ - api_version = self.profile.get('virtual_network_gateway_connections', self.api_version) + api_version = self._get_api_version('virtual_network_gateway_connections') if api_version == '2015-06-15': from .v2015_06_15.operations import VirtualNetworkGatewayConnectionsOperations as OperationClass elif api_version == '2016-09-01': @@ -1368,7 +1383,7 @@ def virtual_network_gateways(self): * 2017-11-01: :class:`VirtualNetworkGatewaysOperations` * 2018-01-01: :class:`VirtualNetworkGatewaysOperations` """ - api_version = self.profile.get('virtual_network_gateways', self.api_version) + api_version = self._get_api_version('virtual_network_gateways') if api_version == '2015-06-15': from .v2015_06_15.operations import VirtualNetworkGatewaysOperations as OperationClass elif api_version == '2016-09-01': @@ -1407,7 +1422,7 @@ def virtual_network_peerings(self): * 2017-11-01: :class:`VirtualNetworkPeeringsOperations` * 2018-01-01: :class:`VirtualNetworkPeeringsOperations` """ - api_version = self.profile.get('virtual_network_peerings', self.api_version) + api_version = self._get_api_version('virtual_network_peerings') if api_version == '2016-09-01': from .v2016_09_01.operations import VirtualNetworkPeeringsOperations as OperationClass elif api_version == '2016-12-01': @@ -1445,7 +1460,7 @@ def virtual_networks(self): * 2017-11-01: :class:`VirtualNetworksOperations` * 2018-01-01: :class:`VirtualNetworksOperations` """ - api_version = self.profile.get('virtual_networks', self.api_version) + api_version = self._get_api_version('virtual_networks') if api_version == '2015-06-15': from .v2015_06_15.operations import VirtualNetworksOperations as OperationClass elif api_version == '2016-09-01': diff --git a/azure-mgmt-resource/HISTORY.rst b/azure-mgmt-resource/HISTORY.rst index 57b4e4a3797e..ed603b3294db 100644 --- a/azure-mgmt-resource/HISTORY.rst +++ b/azure-mgmt-resource/HISTORY.rst @@ -3,6 +3,13 @@ Release History =============== +XXXXXXXXXXXX +++++++++++++ + +**Features** + +- All clients now support Azure profiles. + 1.3.0rc1 (2018-XX-XX) +++++++++++++++++++++ diff --git a/azure-mgmt-resource/azure/mgmt/resource/features/feature_client.py b/azure-mgmt-resource/azure/mgmt/resource/features/feature_client.py index 7bb2899b64fa..589207a785b6 100644 --- a/azure-mgmt-resource/azure/mgmt/resource/features/feature_client.py +++ b/azure-mgmt-resource/azure/mgmt/resource/features/feature_client.py @@ -12,6 +12,9 @@ from msrest.service_client import ServiceClient from msrest import Serializer, Deserializer from msrestazure import AzureConfiguration + +from azure.profiles import KnownProfiles, ProfileDefinition +from azure.profiles.multiapiclient import MultiApiClientMixin from ..version import VERSION @@ -52,7 +55,7 @@ def __init__( self.api_version = api_version -class FeatureClient(object): +class FeatureClient(MultiApiClientMixin): """Azure Feature Exposure Control (AFEC) provides a mechanism for the resource providers to control feature exposure to users. Resource providers typically use this mechanism to provide public/private preview for new features prior to making them generally available. Users need to explicitly register for AFEC features to get access to such functionality. :ivar config: Configuration for client. @@ -66,22 +69,31 @@ class FeatureClient(object): :param str api_version: API version to use if no profile is provided, or if missing in profile. :param str base_url: Service URL - :param profile: A dict using operation group name to API version. - :type profile: dict[str, str] + :param profile: A profile definition, from KnownProfiles to dict. + :type profile: azure.profiles.KnownProfiles """ DEFAULT_API_VERSION = '2015-12-01' - DEFAULT_PROFILE = None - - def __init__( - self, credentials, subscription_id, api_version=DEFAULT_API_VERSION, base_url=None, profile=DEFAULT_PROFILE): + _PROFILE_TAG = "azure.mgmt.resource.features.FeatureClient" + LATEST_PROFILE = ProfileDefinition({ + _PROFILE_TAG: { + None: DEFAULT_API_VERSION + }}, + _PROFILE_TAG + " latest" + ) + + def __init__(self, credentials, subscription_id, api_version=None, base_url=None, profile=KnownProfiles.default): + super(FeatureClient, self).__init__( + credentials=credentials, + subscription_id=subscription_id, + api_version=api_version, + base_url=base_url, + profile=profile + ) self.config = FeatureClientConfiguration(credentials, subscription_id, api_version, base_url) self._client = ServiceClient(self.config.credentials, self.config) - self.api_version = api_version - self.profile = dict(profile) if profile is not None else {} - ############ Generated from here ############ @classmethod @@ -105,7 +117,7 @@ def features(self): * 2015-12-01: :class:`FeaturesOperations` """ - api_version = self.profile.get('features', self.api_version) + api_version = self._get_api_version('features') if api_version == '2015-12-01': from .v2015_12_01.operations import FeaturesOperations as OperationClass else: diff --git a/azure-mgmt-resource/azure/mgmt/resource/links/management_link_client.py b/azure-mgmt-resource/azure/mgmt/resource/links/management_link_client.py index 1b3db33bbddf..d7120d8966a6 100644 --- a/azure-mgmt-resource/azure/mgmt/resource/links/management_link_client.py +++ b/azure-mgmt-resource/azure/mgmt/resource/links/management_link_client.py @@ -12,6 +12,9 @@ from msrest.service_client import ServiceClient from msrest import Serializer, Deserializer from msrestazure import AzureConfiguration + +from azure.profiles import KnownProfiles, ProfileDefinition +from azure.profiles.multiapiclient import MultiApiClientMixin from ..version import VERSION @@ -47,7 +50,7 @@ def __init__( self.subscription_id = subscription_id -class ManagementLinkClient(object): +class ManagementLinkClient(MultiApiClientMixin): """Azure resources can be linked together to form logical relationships. You can establish links between resources belonging to different resource groups. However, all the linked resources must belong to the same subscription. Each resource can be linked to 50 other resources. If any of the linked resources are deleted or moved, the link owner must clean up the remaining link. :ivar config: Configuration for client. @@ -61,21 +64,31 @@ class ManagementLinkClient(object): :param str api_version: API version to use if no profile is provided, or if missing in profile. :param str base_url: Service URL - :param profile: A dict using operation group name to API version. - :type profile: dict[str, str] + :param profile: A profile definition, from KnownProfiles to dict. + :type profile: azure.profiles.KnownProfiles """ DEFAULT_API_VERSION = '2016-09-01' - DEFAULT_PROFILE = None - - def __init__(self, credentials, subscription_id, api_version=DEFAULT_API_VERSION, base_url=None, profile=DEFAULT_PROFILE): + _PROFILE_TAG = "azure.mgmt.resource.links.ManagementLinkClient" + LATEST_PROFILE = ProfileDefinition({ + _PROFILE_TAG: { + None: DEFAULT_API_VERSION + }}, + _PROFILE_TAG + " latest" + ) + + def __init__(self, credentials, subscription_id, api_version=None, base_url=None, profile=KnownProfiles.default): + super(ManagementLinkClient, self).__init__( + credentials=credentials, + subscription_id=subscription_id, + api_version=api_version, + base_url=base_url, + profile=profile + ) self.config = ManagementLinkClientConfiguration(credentials, subscription_id, base_url) self._client = ServiceClient(self.config.credentials, self.config) - self.api_version = api_version - self.profile = dict(profile) if profile is not None else {} - ############ Generated from here ############ @classmethod @@ -99,7 +112,7 @@ def resource_links(self): * 2016-09-01: :class:`ResourceLinksOperations` """ - api_version = self.profile.get('resource_links', self.api_version) + api_version = self._get_api_version('resource_links') if api_version == '2016-09-01': from .v2016_09_01.operations import ResourceLinksOperations as OperationClass else: diff --git a/azure-mgmt-resource/azure/mgmt/resource/locks/management_lock_client.py b/azure-mgmt-resource/azure/mgmt/resource/locks/management_lock_client.py index 8d575b3ce4c0..878d01163393 100644 --- a/azure-mgmt-resource/azure/mgmt/resource/locks/management_lock_client.py +++ b/azure-mgmt-resource/azure/mgmt/resource/locks/management_lock_client.py @@ -12,6 +12,9 @@ from msrest.service_client import ServiceClient from msrest import Serializer, Deserializer from msrestazure import AzureConfiguration + +from azure.profiles import KnownProfiles, ProfileDefinition +from azure.profiles.multiapiclient import MultiApiClientMixin from ..version import VERSION @@ -47,7 +50,7 @@ def __init__( self.subscription_id = subscription_id -class ManagementLockClient(object): +class ManagementLockClient(MultiApiClientMixin): """Azure resources can be locked to prevent other users in your organization from deleting or modifying resources. :ivar config: Configuration for client. @@ -66,17 +69,26 @@ class ManagementLockClient(object): """ DEFAULT_API_VERSION = '2016-09-01' - DEFAULT_PROFILE = None - - def __init__( - self, credentials, subscription_id, api_version=DEFAULT_API_VERSION, base_url=None, profile=DEFAULT_PROFILE): + _PROFILE_TAG = "azure.mgmt.resource.locks.ManagementLockClient" + LATEST_PROFILE = ProfileDefinition({ + _PROFILE_TAG: { + None: DEFAULT_API_VERSION + }}, + _PROFILE_TAG + " latest" + ) + + def __init__(self, credentials, subscription_id, api_version=None, base_url=None, profile=KnownProfiles.default): + super(ManagementLockClient, self).__init__( + credentials=credentials, + subscription_id=subscription_id, + api_version=api_version, + base_url=base_url, + profile=profile + ) self.config = ManagementLockClientConfiguration(credentials, subscription_id, base_url) self._client = ServiceClient(self.config.credentials, self.config) - self.api_version = api_version - self.profile = dict(profile) if profile is not None else {} - ############ Generated from here ############ @classmethod @@ -105,7 +117,7 @@ def management_locks(self): * 2015-01-01: :class:`ManagementLocksOperations` * 2016-09-01: :class:`ManagementLocksOperations` """ - api_version = self.profile.get('management_locks', self.api_version) + api_version = self._get_api_version('management_locks') if api_version == '2015-01-01': from .v2015_01_01.operations import ManagementLocksOperations as OperationClass elif api_version == '2016-09-01': diff --git a/azure-mgmt-resource/azure/mgmt/resource/policy/policy_client.py b/azure-mgmt-resource/azure/mgmt/resource/policy/policy_client.py index 5a0a16d72631..9ae0da197e18 100644 --- a/azure-mgmt-resource/azure/mgmt/resource/policy/policy_client.py +++ b/azure-mgmt-resource/azure/mgmt/resource/policy/policy_client.py @@ -12,6 +12,9 @@ from msrest.service_client import ServiceClient from msrest import Serializer, Deserializer from msrestazure import AzureConfiguration + +from azure.profiles import KnownProfiles, ProfileDefinition +from azure.profiles.multiapiclient import MultiApiClientMixin from ..version import VERSION @@ -47,7 +50,7 @@ def __init__( self.subscription_id = subscription_id -class PolicyClient(object): +class PolicyClient(MultiApiClientMixin): """To manage and control access to your resources, you can define customized policies and assign them at a scope. :ivar config: Configuration for client. @@ -61,22 +64,31 @@ class PolicyClient(object): :param str api_version: API version to use if no profile is provided, or if missing in profile. :param str base_url: Service URL - :param profile: A dict using operation group name to API version. - :type profile: dict[str, str] + :param profile: A profile definition, from KnownProfiles to dict. + :type profile: azure.profiles.KnownProfiles """ DEFAULT_API_VERSION='2016-12-01' - DEFAULT_PROFILE=None - - def __init__( - self, credentials, subscription_id, api_version=DEFAULT_API_VERSION, base_url=None, profile=DEFAULT_PROFILE): + _PROFILE_TAG = "azure.mgmt.resource.policy.PolicyClient" + LATEST_PROFILE = ProfileDefinition({ + _PROFILE_TAG: { + None: DEFAULT_API_VERSION + }}, + _PROFILE_TAG + " latest" + ) + + def __init__(self, credentials, subscription_id, api_version=None, base_url=None, profile=KnownProfiles.default): + super(PolicyClient, self).__init__( + credentials=credentials, + subscription_id=subscription_id, + api_version=api_version, + base_url=base_url, + profile=profile + ) self.config = PolicyClientConfiguration(credentials, subscription_id, base_url) self._client = ServiceClient(self.config.credentials, self.config) - self.api_version = api_version - self.profile = dict(profile) if profile is not None else {} - ############ Generated from here ############ @classmethod @@ -115,7 +127,7 @@ def policy_assignments(self): * 2016-12-01: :class:`PolicyAssignmentsOperations` * 2017-06-01-preview: :class:`PolicyAssignmentsOperations` """ - api_version = self.profile.get('policy_assignments', self.api_version) + api_version = self._get_api_version('policy_assignments') if api_version == '2015-10-01-preview': from .v2015_10_01_preview.operations import PolicyAssignmentsOperations as OperationClass elif api_version == '2016-04-01': @@ -137,7 +149,7 @@ def policy_definitions(self): * 2016-12-01: :class:`PolicyDefinitionsOperations` * 2017-06-01-preview: :class:`PolicyDefinitionsOperations` """ - api_version = self.profile.get('policy_definitions', self.api_version) + api_version = self._get_api_version('policy_definitions') if api_version == '2015-10-01-preview': from .v2015_10_01_preview.operations import PolicyDefinitionsOperations as OperationClass elif api_version == '2016-04-01': @@ -156,7 +168,7 @@ def policy_set_definitions(self): * 2017-06-01-preview: :class:`PolicySetDefinitionsOperations` """ - api_version = self.profile.get('policy_set_definitions', self.api_version) + api_version = self._get_api_version('policy_set_definitions') if api_version == '2017-06-01-preview': from .v2017_06_01_preview.operations import PolicySetDefinitionsOperations as OperationClass else: diff --git a/azure-mgmt-resource/azure/mgmt/resource/resources/resource_management_client.py b/azure-mgmt-resource/azure/mgmt/resource/resources/resource_management_client.py index 64955ca43752..198e87390202 100644 --- a/azure-mgmt-resource/azure/mgmt/resource/resources/resource_management_client.py +++ b/azure-mgmt-resource/azure/mgmt/resource/resources/resource_management_client.py @@ -12,6 +12,9 @@ from msrest.service_client import ServiceClient from msrest import Serializer, Deserializer from msrestazure import AzureConfiguration + +from azure.profiles import KnownProfiles, ProfileDefinition +from azure.profiles.multiapiclient import MultiApiClientMixin from ..version import VERSION @@ -47,7 +50,7 @@ def __init__( self.subscription_id = subscription_id -class ResourceManagementClient(object): +class ResourceManagementClient(MultiApiClientMixin): """Provides operations for working with resources and resource groups. :ivar config: Configuration for client. @@ -61,22 +64,31 @@ class ResourceManagementClient(object): :param str api_version: API version to use if no profile is provided, or if missing in profile. :param str base_url: Service URL - :param profile: A dict using operation group name to API version. - :type profile: dict[str, str] + :param profile: A profile definition, from KnownProfiles to dict. + :type profile: azure.profiles.KnownProfiles """ DEFAULT_API_VERSION='2017-05-10' - DEFAULT_PROFILE=None - - def __init__( - self, credentials, subscription_id, api_version=DEFAULT_API_VERSION, base_url=None, profile=DEFAULT_PROFILE): + _PROFILE_TAG = "azure.mgmt.resource.resources.ResourceManagementClient" + LATEST_PROFILE = ProfileDefinition({ + _PROFILE_TAG: { + None: DEFAULT_API_VERSION + }}, + _PROFILE_TAG + " latest" + ) + + def __init__(self, credentials, subscription_id, api_version=None, base_url=None, profile=KnownProfiles.default): + super(ResourceManagementClient, self).__init__( + credentials=credentials, + subscription_id=subscription_id, + api_version=api_version, + base_url=base_url, + profile=profile + ) self.config = ResourceManagementClientConfiguration(credentials, subscription_id, base_url) self._client = ServiceClient(self.config.credentials, self.config) - self.api_version = api_version - self.profile = dict(profile) if profile is not None else {} - ############ Generated from here ############ @classmethod @@ -110,7 +122,7 @@ def deployment_operations(self): * 2016-09-01: :class:`DeploymentOperations` * 2017-05-10: :class:`DeploymentOperations` """ - api_version = self.profile.get('deployment_operations', self.api_version) + api_version = self._get_api_version('deployment_operations') if api_version == '2016-02-01': from .v2016_02_01.operations import DeploymentOperations as OperationClass elif api_version == '2016-09-01': @@ -129,7 +141,7 @@ def deployments(self): * 2016-09-01: :class:`DeploymentsOperations` * 2017-05-10: :class:`DeploymentsOperations` """ - api_version = self.profile.get('deployments', self.api_version) + api_version = self._get_api_version('deployments') if api_version == '2016-02-01': from .v2016_02_01.operations import DeploymentsOperations as OperationClass elif api_version == '2016-09-01': @@ -148,7 +160,7 @@ def providers(self): * 2016-09-01: :class:`ProvidersOperations` * 2017-05-10: :class:`ProvidersOperations` """ - api_version = self.profile.get('providers', self.api_version) + api_version = self._get_api_version('providers') if api_version == '2016-02-01': from .v2016_02_01.operations import ProvidersOperations as OperationClass elif api_version == '2016-09-01': @@ -167,7 +179,7 @@ def resource_groups(self): * 2016-09-01: :class:`ResourceGroupsOperations` * 2017-05-10: :class:`ResourceGroupsOperations` """ - api_version = self.profile.get('resource_groups', self.api_version) + api_version = self._get_api_version('resource_groups') if api_version == '2016-02-01': from .v2016_02_01.operations import ResourceGroupsOperations as OperationClass elif api_version == '2016-09-01': @@ -186,7 +198,7 @@ def resources(self): * 2016-09-01: :class:`ResourcesOperations` * 2017-05-10: :class:`ResourcesOperations` """ - api_version = self.profile.get('resources', self.api_version) + api_version = self._get_api_version('resources') if api_version == '2016-02-01': from .v2016_02_01.operations import ResourcesOperations as OperationClass elif api_version == '2016-09-01': @@ -205,7 +217,7 @@ def tags(self): * 2016-09-01: :class:`TagsOperations` * 2017-05-10: :class:`TagsOperations` """ - api_version = self.profile.get('tags', self.api_version) + api_version = self._get_api_version('tags') if api_version == '2016-02-01': from .v2016_02_01.operations import TagsOperations as OperationClass elif api_version == '2016-09-01': diff --git a/azure-mgmt-resource/azure/mgmt/resource/subscriptions/subscription_client.py b/azure-mgmt-resource/azure/mgmt/resource/subscriptions/subscription_client.py index e6bc2a421f1c..af4374d65af4 100644 --- a/azure-mgmt-resource/azure/mgmt/resource/subscriptions/subscription_client.py +++ b/azure-mgmt-resource/azure/mgmt/resource/subscriptions/subscription_client.py @@ -12,6 +12,9 @@ from msrest.service_client import ServiceClient from msrest import Serializer, Deserializer from msrestazure import AzureConfiguration + +from azure.profiles import KnownProfiles, ProfileDefinition +from azure.profiles.multiapiclient import MultiApiClientMixin from ..version import VERSION @@ -42,7 +45,7 @@ def __init__( self.credentials = credentials -class SubscriptionClient(object): +class SubscriptionClient(MultiApiClientMixin): """All resource groups and resources exist within subscriptions. These operation enable you get information about your subscriptions and tenants. A tenant is a dedicated instance of Azure Active Directory (Azure AD) for your organization. :ivar config: Configuration for client. @@ -54,22 +57,30 @@ class SubscriptionClient(object): :param str api_version: API version to use if no profile is provided, or if missing in profile. :param str base_url: Service URL - :param profile: A dict using operation group name to API version. - :type profile: dict[str, str] + :param profile: A profile definition, from KnownProfiles to dict. + :type profile: azure.profiles.KnownProfiles """ DEFAULT_API_VERSION='2016-06-01' - DEFAULT_PROFILE=None - - def __init__( - self, credentials, api_version=DEFAULT_API_VERSION, base_url=None, profile=DEFAULT_PROFILE): + _PROFILE_TAG = "azure.mgmt.resource.subscriptions.SubscriptionClient" + LATEST_PROFILE = ProfileDefinition({ + _PROFILE_TAG: { + None: DEFAULT_API_VERSION + }}, + _PROFILE_TAG + " latest" + ) + + def __init__(self, credentials, api_version=None, base_url=None, profile=KnownProfiles.default): + super(SubscriptionClient, self).__init__( + credentials=credentials, + api_version=api_version, + base_url=base_url, + profile=profile + ) self.config = SubscriptionClientConfiguration(credentials, base_url) self._client = ServiceClient(self.config.credentials, self.config) - self.api_version = api_version - self.profile = dict(profile) if profile is not None else {} - ############ Generated from here ############ @classmethod @@ -93,7 +104,7 @@ def subscriptions(self): * 2016-06-01: :class:`SubscriptionsOperations` """ - api_version = self.profile.get('subscriptions', self.api_version) + api_version = self._get_api_version('subscriptions') if api_version == '2016-06-01': from .v2016_06_01.operations import SubscriptionsOperations as OperationClass else: @@ -106,7 +117,7 @@ def tenants(self): * 2016-06-01: :class:`TenantsOperations` """ - api_version = self.profile.get('tenants', self.api_version) + api_version = self._get_api_version('tenants') if api_version == '2016-06-01': from .v2016_06_01.operations import TenantsOperations as OperationClass else: diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource.test_deployments.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_deployments.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource.test_deployments.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_deployments.yaml diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource.test_deployments_linked_template.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_deployments_linked_template.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource.test_deployments_linked_template.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_deployments_linked_template.yaml diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource.test_deployments_linked_template_error.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_deployments_linked_template_error.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource.test_deployments_linked_template_error.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_deployments_linked_template_error.yaml diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource.test_provider_locations.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_provider_locations.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource.test_provider_locations.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_provider_locations.yaml diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource.test_providers.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_providers.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource.test_providers.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_providers.yaml diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource.test_resource_groups.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_resource_groups.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource.test_resource_groups.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_resource_groups.yaml diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource.test_resources.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_resources.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource.test_resources.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_resources.yaml diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource.test_tag_operations.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_tag_operations.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource.test_tag_operations.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource.test_tag_operations.yaml diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource_features.test_features.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource_features.test_features.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource_features.test_features.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource_features.test_features.yaml diff --git a/azure-mgmt-resource/tests/recordings/test_mgmt_resource_links.test_links.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource_links.test_links.yaml new file mode 100644 index 000000000000..eb6037769fd9 --- /dev/null +++ b/azure-mgmt-resource/tests/recordings/test_mgmt_resource_links.test_links.yaml @@ -0,0 +1,196 @@ +interactions: +- request: + body: '{"location": "westus"}' + headers: + Accept: [application/json] + Accept-Encoding: ['gzip, deflate'] + Connection: [keep-alive] + Content-Length: ['22'] + Content-Type: [application/json; charset=utf-8] + User-Agent: [python/3.6.3 (Windows-10-10.0.16299-SP0) requests/2.18.4 msrest/0.4.27 + msrest_azure/0.4.22 resourcemanagementclient/1.3.0rc1 Azure-SDK-For-Python] + accept-language: [en-US] + method: PUT + uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourcegroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a?api-version=2015-05-01-preview + response: + body: {string: "{\r\n \"properties\": {\r\n \"platformUpdateDomainCount\"\ + : 5,\r\n \"platformFaultDomainCount\": 3\r\n },\r\n \"type\": \"Microsoft.Compute/availabilitySets\"\ + ,\r\n \"location\": \"westus\",\r\n \"id\": \"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a\"\ + ,\r\n \"name\": \"pytestavset7650e8a\"\r\n}"} + headers: + cache-control: [no-cache] + content-length: ['393'] + content-type: [application/json; charset=utf-8] + date: ['Tue, 03 Apr 2018 19:07:22 GMT'] + expires: ['-1'] + pragma: [no-cache] + server: [Microsoft-HTTPAPI/2.0, Microsoft-HTTPAPI/2.0] + strict-transport-security: [max-age=31536000; includeSubDomains] + transfer-encoding: [chunked] + vary: [Accept-Encoding] + x-content-type-options: [nosniff] + x-ms-ratelimit-remaining-resource: ['Microsoft.Compute/PutVM3Min;238,Microsoft.Compute/PutVM30Min;1198'] + x-ms-ratelimit-remaining-subscription-writes: ['1199'] + status: {code: 200, message: OK} +- request: + body: 'b''b\''b\\\''{"properties": {"targetId": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a", + "notes": "Testing links"}}\\\''\''''' + headers: + Accept: [application/json] + Accept-Encoding: ['gzip, deflate'] + Connection: [keep-alive] + Content-Length: ['231'] + Content-Type: [application/json; charset=utf-8] + User-Agent: [python/3.6.3 (Windows-10-10.0.16299-SP0) requests/2.18.4 msrest/0.4.27 + msrest_azure/0.4.22 managementlinkclient/1.3.0rc1 Azure-SDK-For-Python] + accept-language: [en-US] + method: PUT + uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink?api-version=2016-09-01 + response: + body: {string: '{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a/","notes":"Testing + links"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink","type":"Microsoft.Resources/links","name":"myLink"}'} + headers: + cache-control: [no-cache] + content-length: ['563'] + content-type: [application/json; charset=utf-8] + date: ['Tue, 03 Apr 2018 19:07:23 GMT'] + expires: ['-1'] + pragma: [no-cache] + strict-transport-security: [max-age=31536000; includeSubDomains] + x-content-type-options: [nosniff] + x-ms-ratelimit-remaining-subscription-writes: ['1199'] + status: {code: 201, message: Created} +- request: + body: null + headers: + Accept: [application/json] + Accept-Encoding: ['gzip, deflate'] + Connection: [keep-alive] + Content-Type: [application/json; charset=utf-8] + User-Agent: [python/3.6.3 (Windows-10-10.0.16299-SP0) requests/2.18.4 msrest/0.4.27 + msrest_azure/0.4.22 managementlinkclient/1.3.0rc1 Azure-SDK-For-Python] + accept-language: [en-US] + method: GET + uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink?api-version=2016-09-01 + response: + body: {string: '{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a/","notes":"Testing + links"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink","type":"Microsoft.Resources/links","name":"myLink"}'} + headers: + cache-control: [no-cache] + content-length: ['563'] + content-type: [application/json; charset=utf-8] + date: ['Tue, 03 Apr 2018 19:07:33 GMT'] + expires: ['-1'] + pragma: [no-cache] + strict-transport-security: [max-age=31536000; includeSubDomains] + transfer-encoding: [chunked] + vary: ['Accept-Encoding,Accept-Encoding'] + x-content-type-options: [nosniff] + status: {code: 200, message: OK} +- request: + body: null + headers: + Accept: [application/json] + Accept-Encoding: ['gzip, deflate'] + Connection: [keep-alive] + Content-Type: [application/json; charset=utf-8] + User-Agent: [python/3.6.3 (Windows-10-10.0.16299-SP0) requests/2.18.4 msrest/0.4.27 + msrest_azure/0.4.22 managementlinkclient/1.3.0rc1 Azure-SDK-For-Python] + accept-language: [en-US] + method: GET + uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/providers/Microsoft.Resources/links?api-version=2016-09-01 + response: + body: {string: '{"value":[{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a/","notes":"Testing + links"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink","type":"Microsoft.Resources/links","name":"myLink"},{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourcegroups/CIStressbasiceff7fcbdedb548758ac9b61306cf6188/providers/Microsoft.AppService/apiapps/Microsoft.Azure.AppService.ApiApps.TestBench/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/CIStressbasiceff7fcbdedb548758ac9b61306cf6188/providers/Microsoft.Web/sites/Microsoft-Azure-AppService-A4d3f666ccb764f2899daaa3fceffd6c7/"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourcegroups/CIStressbasiceff7fcbdedb548758ac9b61306cf6188/providers/Microsoft.AppService/apiapps/Microsoft.Azure.AppService.ApiApps.TestBench/providers/Microsoft.Resources/links/apiAppSite","type":"Microsoft.Resources/links","name":"apiAppSite"},{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourcegroups/CIStressbasicf9d9bc55679a43d58684974d0971857f/providers/Microsoft.AppService/gateways/CIStressbasicf9d9bc55679a43d00977cdb163f435f9c3239ec8ae61f4d/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/CIStressbasicf9d9bc55679a43d58684974d0971857f/providers/Microsoft.Web/sites/CIStressbasicf9d9bc55679a43d00977cdb163f435f9c3239ec8ae61f4d/"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourcegroups/CIStressbasicf9d9bc55679a43d58684974d0971857f/providers/Microsoft.AppService/gateways/CIStressbasicf9d9bc55679a43d00977cdb163f435f9c3239ec8ae61f4d/providers/Microsoft.Resources/links/gatewaySite","type":"Microsoft.Resources/links","name":"gatewaySite"},{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourcegroups/CIStressbasic1ab4b88952c74b1da467a0bf3683d5d3/providers/Microsoft.AppService/gateways/CIStressbasic1ab4b88952c74b100977cdb163f435f9c3239ec8ae61f4d/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/CIStressbasic1ab4b88952c74b1da467a0bf3683d5d3/providers/Microsoft.Web/sites/CIStressbasic1ab4b88952c74b100977cdb163f435f9c3239ec8ae61f4d/"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourcegroups/CIStressbasic1ab4b88952c74b1da467a0bf3683d5d3/providers/Microsoft.AppService/gateways/CIStressbasic1ab4b88952c74b100977cdb163f435f9c3239ec8ae61f4d/providers/Microsoft.Resources/links/gatewaySite","type":"Microsoft.Resources/links","name":"gatewaySite"}]}'} + headers: + cache-control: [no-cache] + content-length: ['2903'] + content-type: [application/json; charset=utf-8] + date: ['Tue, 03 Apr 2018 19:07:33 GMT'] + expires: ['-1'] + pragma: [no-cache] + strict-transport-security: [max-age=31536000; includeSubDomains] + transfer-encoding: [chunked] + vary: ['Accept-Encoding,Accept-Encoding'] + x-content-type-options: [nosniff] + status: {code: 200, message: OK} +- request: + body: null + headers: + Accept: [application/json] + Accept-Encoding: ['gzip, deflate'] + Connection: [keep-alive] + Content-Type: [application/json; charset=utf-8] + User-Agent: [python/3.6.3 (Windows-10-10.0.16299-SP0) requests/2.18.4 msrest/0.4.27 + msrest_azure/0.4.22 managementlinkclient/1.3.0rc1 Azure-SDK-For-Python] + accept-language: [en-US] + method: GET + uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links?api-version=2016-09-01 + response: + body: {string: '{"value":[{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a/","notes":"Testing + links"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink","type":"Microsoft.Resources/links","name":"myLink"}]}'} + headers: + cache-control: [no-cache] + content-length: ['575'] + content-type: [application/json; charset=utf-8] + date: ['Tue, 03 Apr 2018 19:07:34 GMT'] + expires: ['-1'] + pragma: [no-cache] + strict-transport-security: [max-age=31536000; includeSubDomains] + transfer-encoding: [chunked] + vary: ['Accept-Encoding,Accept-Encoding'] + x-content-type-options: [nosniff] + status: {code: 200, message: OK} +- request: + body: null + headers: + Accept: [application/json] + Accept-Encoding: ['gzip, deflate'] + Connection: [keep-alive] + Content-Type: [application/json; charset=utf-8] + User-Agent: [python/3.6.3 (Windows-10-10.0.16299-SP0) requests/2.18.4 msrest/0.4.27 + msrest_azure/0.4.22 managementlinkclient/1.3.0rc1 Azure-SDK-For-Python] + accept-language: [en-US] + method: GET + uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links?$filter=atScope%28%29&api-version=2016-09-01 + response: + body: {string: '{"value":[{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a/","notes":"Testing + links"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink","type":"Microsoft.Resources/links","name":"myLink"}]}'} + headers: + cache-control: [no-cache] + content-length: ['575'] + content-type: [application/json; charset=utf-8] + date: ['Tue, 03 Apr 2018 19:07:34 GMT'] + expires: ['-1'] + pragma: [no-cache] + strict-transport-security: [max-age=31536000; includeSubDomains] + transfer-encoding: [chunked] + vary: ['Accept-Encoding,Accept-Encoding'] + x-content-type-options: [nosniff] + status: {code: 200, message: OK} +- request: + body: null + headers: + Accept: [application/json] + Accept-Encoding: ['gzip, deflate'] + Connection: [keep-alive] + Content-Length: ['0'] + Content-Type: [application/json; charset=utf-8] + User-Agent: [python/3.6.3 (Windows-10-10.0.16299-SP0) requests/2.18.4 msrest/0.4.27 + msrest_azure/0.4.22 managementlinkclient/1.3.0rc1 Azure-SDK-For-Python] + accept-language: [en-US] + method: DELETE + uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink?api-version=2016-09-01 + response: + body: {string: ''} + headers: + cache-control: [no-cache] + content-length: ['0'] + date: ['Tue, 03 Apr 2018 19:07:35 GMT'] + expires: ['-1'] + pragma: [no-cache] + strict-transport-security: [max-age=31536000; includeSubDomains] + x-content-type-options: [nosniff] + x-ms-ratelimit-remaining-subscription-writes: ['1199'] + status: {code: 200, message: OK} +version: 1 diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource_locks.test_locks.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource_locks.test_locks.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource_locks.test_locks.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource_locks.test_locks.yaml diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource_subscriptions.test_subscriptions.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource_subscriptions.test_subscriptions.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource_subscriptions.test_subscriptions.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource_subscriptions.test_subscriptions.yaml diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource_subscriptions.test_tenants.yaml b/azure-mgmt-resource/tests/recordings/test_mgmt_resource_subscriptions.test_tenants.yaml similarity index 100% rename from azure-mgmt/tests/recordings/test_mgmt_resource_subscriptions.test_tenants.yaml rename to azure-mgmt-resource/tests/recordings/test_mgmt_resource_subscriptions.test_tenants.yaml diff --git a/azure-mgmt/tests/test_mgmt_resource.py b/azure-mgmt-resource/tests/test_mgmt_resource.py similarity index 87% rename from azure-mgmt/tests/test_mgmt_resource.py rename to azure-mgmt-resource/tests/test_mgmt_resource.py index 11f09be8a7b9..af0f36ede3eb 100644 --- a/azure-mgmt/tests/test_mgmt_resource.py +++ b/azure-mgmt-resource/tests/test_mgmt_resource.py @@ -9,15 +9,15 @@ import azure.mgmt.resource.resources.models import azure.common.exceptions -from testutils.common_recordingtestcase import record -from tests.mgmt_testcase import HttpStatusCode, AzureMgmtTestCase - +from devtools_testutils import AzureMgmtTestCase, ResourceGroupPreparer class MgmtResourceTest(AzureMgmtTestCase): def setUp(self): super(MgmtResourceTest, self).setUp() + self.resource_client = self.create_mgmt_client( + azure.mgmt.resource.ResourceManagementClient + ) - @record def test_tag_operations(self): tag_name = 'tag1' tag_value = 'value1' @@ -51,8 +51,8 @@ def test_tag_operations(self): tag_name ) - @record def test_resource_groups(self): + group_name = "test_mgmt_resource_test_resource_groups457f1050" # Create or update params_create = azure.mgmt.resource.resources.models.ResourceGroup( location=self.region, @@ -61,18 +61,18 @@ def test_resource_groups(self): }, ) result_create = self.resource_client.resource_groups.create_or_update( - self.group_name, + group_name, params_create, ) # Get - result_get = self.resource_client.resource_groups.get(self.group_name) - self.assertEqual(result_get.name, self.group_name) + result_get = self.resource_client.resource_groups.get(group_name) + self.assertEqual(result_get.name, group_name) self.assertEqual(result_get.tags['tag1'], 'value1') # Check existence result_check = self.resource_client.resource_groups.check_existence( - self.group_name, + group_name, ) self.assertTrue(result_check) @@ -98,7 +98,7 @@ def test_resource_groups(self): }, ) result_patch = self.resource_client.resource_groups.update( - self.group_name, + group_name, params_patch, ) self.assertEqual(result_patch.tags['tag1'], 'valueA') @@ -106,33 +106,27 @@ def test_resource_groups(self): # List resources resources = list(self.resource_client.resources.list_by_resource_group( - self.group_name + group_name )) # Export template template = self.resource_client.resource_groups.export_template( - self.group_name, + group_name, ['*'] ) self.assertTrue(hasattr(template, 'template')) # Delete - result_delete = self.resource_client.resource_groups.delete(self.group_name) + result_delete = self.resource_client.resource_groups.delete(group_name) result_delete.wait() - @record - def test_resources(self): - # WARNING: For some strange url parsing reason, this test has to be recorded twice: - # - Once in Python 2.7 for 2.7/3.3/3.4 (...Microsoft.Compute//availabilitySets...) - # - Once in Python 3.5 (...Microsoft.Compute/availabilitySets...) - # I don't know why 3.5 has one / and 2.7-3.4 two / - # I don't really care, being that Azure accept both URLs... - self.create_resource_group() + @ResourceGroupPreparer() + def test_resources(self, resource_group, location): resource_name = self.get_resource_name("pytestavset") resource_exist = self.resource_client.resources.check_existence( - resource_group_name=self.group_name, + resource_group_name=resource_group.name, resource_provider_namespace="Microsoft.Compute", parent_resource_path="", resource_type="availabilitySets", @@ -142,7 +136,7 @@ def test_resources(self): self.assertFalse(resource_exist) create_result = self.resource_client.resources.create_or_update( - resource_group_name=self.group_name, + resource_group_name=resource_group.name, resource_provider_namespace="Microsoft.Compute", parent_resource_path="", resource_type="availabilitySets", @@ -154,7 +148,7 @@ def test_resources(self): self.assertEqual(result.name, resource_name) get_result = self.resource_client.resources.get( - resource_group_name=self.group_name, + resource_group_name=resource_group.name, resource_provider_namespace="Microsoft.Compute", parent_resource_path="", resource_type="availabilitySets", @@ -171,11 +165,11 @@ def test_resources(self): new_group_name = self.get_resource_name("pynewgroup") new_group = self.resource_client.resource_groups.create_or_update( new_group_name, - {'location': self.region}, + {'location': location}, ) async_move = self.resource_client.resources.move_resources( - self.group_name, + resource_group.name, [get_result.id], new_group.id ) @@ -197,15 +191,14 @@ def test_resources(self): async_delete.wait() - @record - def test_deployments(self): - self.create_resource_group() + @ResourceGroupPreparer() + def test_deployments(self, resource_group, location): # for more sample templates, see https://github.com/Azure/azure-quickstart-templates deployment_name = self.get_resource_name("pytestdeployment") deployment_exists = self.resource_client.deployments.check_existence( - self.group_name, + resource_group.name, deployment_name ) self.assertFalse(deployment_exists) @@ -253,7 +246,7 @@ def test_deployments(self): ) deployment_create_result = self.resource_client.deployments.create_or_update( - self.group_name, + resource_group.name, deployment_name, deployment_params, ) @@ -261,7 +254,7 @@ def test_deployments(self): self.assertEqual(deployment_name, deployment_create_result.name) deployment_list_result = self.resource_client.deployments.list_by_resource_group( - self.group_name, + resource_group.name, None, ) deployment_list_result = list(deployment_list_result) @@ -269,20 +262,20 @@ def test_deployments(self): self.assertEqual(deployment_name, deployment_list_result[0].name) deployment_get_result = self.resource_client.deployments.get( - self.group_name, + resource_group.name, deployment_name, ) self.assertEqual(deployment_name, deployment_get_result.name) deployment_operations = list(self.resource_client.deployment_operations.list( - self.group_name, + resource_group.name, deployment_name )) self.assertGreater(len(deployment_operations), 1) deployment_operation = deployment_operations[0] deployment_operation_get = self.resource_client.deployment_operations.get( - self.group_name, + resource_group.name, deployment_name, deployment_operation.operation_id ) @@ -291,14 +284,14 @@ def test_deployments(self): # Should throw, since the deployment is done => cannot be cancelled with self.assertRaises(azure.common.exceptions.CloudError) as cm: self.resource_client.deployments.cancel( - self.group_name, + resource_group.name, deployment_name ) self.assertIn('cannot be cancelled', cm.exception.message) # Validate validation =self.resource_client.deployments.validate( - self.group_name, + resource_group.name, deployment_name, {'mode': azure.mgmt.resource.resources.models.DeploymentMode.incremental} ) @@ -306,21 +299,20 @@ def test_deployments(self): # Export template export =self.resource_client.deployments.export_template( - self.group_name, + resource_group.name, deployment_name ) self.assertTrue(hasattr(export, 'template')) # Delete the template async_delete = self.resource_client.deployments.delete( - self.group_name, + resource_group.name, deployment_name ) async_delete.wait() - @record - def test_deployments_linked_template(self): - self.create_resource_group() + @ResourceGroupPreparer() + def test_deployments_linked_template(self, resource_group, location): # for more sample templates, see https://github.com/Azure/azure-quickstart-templates deployment_name = self.get_resource_name("pytestlinked") @@ -338,7 +330,7 @@ def test_deployments_linked_template(self): ) deployment_create_result = self.resource_client.deployments.create_or_update( - self.group_name, + resource_group.name, deployment_name, deployment_params, ) @@ -346,7 +338,7 @@ def test_deployments_linked_template(self): self.assertEqual(deployment_name, deployment_create_result.name) deployment_list_result = self.resource_client.deployments.list_by_resource_group( - self.group_name, + resource_group.name, None, ) deployment_list_result = list(deployment_list_result) @@ -354,14 +346,13 @@ def test_deployments_linked_template(self): self.assertEqual(deployment_name, deployment_list_result[0].name) deployment_get_result = self.resource_client.deployments.get( - self.group_name, + resource_group.name, deployment_name, ) self.assertEqual(deployment_name, deployment_get_result.name) - @record - def test_deployments_linked_template_error(self): - self.create_resource_group() + @ResourceGroupPreparer() + def test_deployments_linked_template_error(self, resource_group, location): # for more sample templates, see https://github.com/Azure/azure-quickstart-templates deployment_name = self.get_resource_name("pytestlinked") @@ -380,22 +371,19 @@ def test_deployments_linked_template_error(self): with self.assertRaises(azure.common.exceptions.CloudError) as err: self.resource_client.deployments.create_or_update( - self.group_name, + resource_group.name, deployment_name, deployment_params, ) cloud_error = err.exception self.assertTrue(cloud_error.message) - - @record def test_provider_locations(self): result_get = self.resource_client.providers.get('Microsoft.Web') for resource in result_get.resource_types: if resource.resource_type == 'sites': self.assertIn('West US', resource.locations) - @record def test_providers(self): self.resource_client.providers.unregister('Microsoft.Batch') self.resource_client.providers.get('Microsoft.Batch') diff --git a/azure-mgmt/tests/test_mgmt_resource_features.py b/azure-mgmt-resource/tests/test_mgmt_resource_features.py similarity index 92% rename from azure-mgmt/tests/test_mgmt_resource_features.py rename to azure-mgmt-resource/tests/test_mgmt_resource_features.py index 517c060c1bfa..626ff494b450 100644 --- a/azure-mgmt/tests/test_mgmt_resource_features.py +++ b/azure-mgmt-resource/tests/test_mgmt_resource_features.py @@ -8,9 +8,7 @@ import unittest import azure.mgmt.resource.features.models -from testutils.common_recordingtestcase import record -from tests.mgmt_testcase import HttpStatusCode, AzureMgmtTestCase - +from devtools_testutils import AzureMgmtTestCase class MgmtResourceFeaturesTest(AzureMgmtTestCase): @@ -20,7 +18,6 @@ def setUp(self): azure.mgmt.resource.FeatureClient ) - @record def test_features(self): features = list(self.features_client.features.list_all()) self.assertGreater(len(features), 0) diff --git a/azure-mgmt-resource/tests/test_mgmt_resource_links.py b/azure-mgmt-resource/tests/test_mgmt_resource_links.py new file mode 100644 index 000000000000..0e86d8a6a82d --- /dev/null +++ b/azure-mgmt-resource/tests/test_mgmt_resource_links.py @@ -0,0 +1,71 @@ +# coding: utf-8 + +#------------------------------------------------------------------------- +# Copyright (c) Microsoft Corporation. All rights reserved. +# Licensed under the MIT License. See License.txt in the project root for +# license information. +#-------------------------------------------------------------------------- +import unittest + +import azure.mgmt.resource +from devtools_testutils import AzureMgmtTestCase, ResourceGroupPreparer + +class MgmtResourceLinksTest(AzureMgmtTestCase): + + def setUp(self): + super(MgmtResourceLinksTest, self).setUp() + self.client = self.create_mgmt_client( + azure.mgmt.resource.ManagementLinkClient + ) + self.resource_client = self.create_mgmt_client( + azure.mgmt.resource.ResourceManagementClient + ) + + @ResourceGroupPreparer() + def test_links(self, resource_group, location): + if not self.is_playback(): + resource_name = self.get_resource_name("pytestavset") + create_result = self.resource_client.resources.create_or_update( + resource_group_name=resource_group.name, + resource_provider_namespace="Microsoft.Compute", + parent_resource_path="", + resource_type="availabilitySets", + resource_name=resource_name, + api_version="2015-05-01-preview", + parameters={'location': location} + ) + result = create_result.result() + self.result_id = result.id + else: + self.result_id = resource_group.id + "/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a" + + link = self.client.resource_links.create_or_update( + resource_group.id+'/providers/Microsoft.Resources/links/myLink', + { + 'target_id' : self.result_id, + 'notes': 'Testing links' + } + ) + self.assertEqual(link.name, 'myLink') + + if not self.is_playback(): + import time + time.sleep(10) + + link = self.client.resource_links.get(link.id) + self.assertEqual(link.name, 'myLink') + + links = list(self.client.resource_links.list_at_subscription()) + self.assertTrue(any(link.name=='myLink' for link in links)) + + links = list(self.client.resource_links.list_at_source_scope(resource_group.id)) + self.assertTrue(any(link.name=='myLink' for link in links)) + + links = list(self.client.resource_links.list_at_source_scope(resource_group.id, 'atScope()')) + self.assertTrue(any(link.name=='myLink' for link in links)) + + self.client.resource_links.delete(link.id) + +#------------------------------------------------------------------------------ +if __name__ == '__main__': + unittest.main() diff --git a/azure-mgmt/tests/test_mgmt_resource_locks.py b/azure-mgmt-resource/tests/test_mgmt_resource_locks.py similarity index 79% rename from azure-mgmt/tests/test_mgmt_resource_locks.py rename to azure-mgmt-resource/tests/test_mgmt_resource_locks.py index 1f04372794bd..6a19185df093 100644 --- a/azure-mgmt/tests/test_mgmt_resource_locks.py +++ b/azure-mgmt-resource/tests/test_mgmt_resource_locks.py @@ -8,9 +8,7 @@ import unittest import azure.mgmt.resource -from testutils.common_recordingtestcase import record -from tests.mgmt_testcase import HttpStatusCode, AzureMgmtTestCase - +from devtools_testutils import AzureMgmtTestCase, ResourceGroupPreparer class MgmtResourceLocksTest(AzureMgmtTestCase): @@ -19,15 +17,13 @@ def setUp(self): self.locks_client = self.create_mgmt_client( azure.mgmt.resource.ManagementLockClient ) - if not self.is_playback(): - self.create_resource_group() - @record - def test_locks(self): + @ResourceGroupPreparer() + def test_locks(self, resource_group, location): lock_name = 'pylockrg' lock = self.locks_client.management_locks.create_or_update_at_resource_group_level( - self.group_name, + resource_group.name, lock_name, { 'level': 'CanNotDelete' @@ -36,12 +32,12 @@ def test_locks(self): self.assertIsNotNone(lock) locks = list(self.locks_client.management_locks.list_at_resource_group_level( - self.group_name + resource_group.name )) self.assertEqual(len(locks), 1) lock = self.locks_client.management_locks.delete_at_resource_group_level( - self.group_name, + resource_group.name, lock_name ) diff --git a/azure-mgmt/tests/test_mgmt_resource_subscriptions.py b/azure-mgmt-resource/tests/test_mgmt_resource_subscriptions.py similarity index 92% rename from azure-mgmt/tests/test_mgmt_resource_subscriptions.py rename to azure-mgmt-resource/tests/test_mgmt_resource_subscriptions.py index 6b39c88b3e7e..65e0f467da1c 100644 --- a/azure-mgmt/tests/test_mgmt_resource_subscriptions.py +++ b/azure-mgmt-resource/tests/test_mgmt_resource_subscriptions.py @@ -8,9 +8,7 @@ import unittest import azure.mgmt.resource.subscriptions.models -from testutils.common_recordingtestcase import record -from tests.mgmt_testcase import HttpStatusCode, AzureMgmtTestCase - +from devtools_testutils import AzureMgmtTestCase class MgmtResourceSubscriptionsTest(AzureMgmtTestCase): @@ -20,7 +18,6 @@ def setUp(self): azure.mgmt.resource.SubscriptionClient ) - @record def test_subscriptions(self): subs = list(self.subscriptions_client.subscriptions.list()) self.assertGreater(len(subs), 0) @@ -33,7 +30,6 @@ def test_subscriptions(self): sub = self.subscriptions_client.subscriptions.get(self.settings.SUBSCRIPTION_ID) self.assertEqual(sub.subscription_id, self.settings.SUBSCRIPTION_ID) - @record def test_tenants(self): tenants = list(self.subscriptions_client.tenants.list()) self.assertGreater(len(tenants), 0) diff --git a/azure-mgmt-storage/HISTORY.rst b/azure-mgmt-storage/HISTORY.rst index a49c31166c09..7d84e6596103 100644 --- a/azure-mgmt-storage/HISTORY.rst +++ b/azure-mgmt-storage/HISTORY.rst @@ -3,6 +3,13 @@ Release History =============== +XXXXXXXXXXXX +++++++++++++ + +**Features** + +- All clients now support Azure profiles. + 1.5.0 (2017-12-12) ++++++++++++++++++ diff --git a/azure-mgmt-storage/azure/mgmt/storage/storage_management_client.py b/azure-mgmt-storage/azure/mgmt/storage/storage_management_client.py index 1e0c8e547cb4..73de573d1aa2 100644 --- a/azure-mgmt-storage/azure/mgmt/storage/storage_management_client.py +++ b/azure-mgmt-storage/azure/mgmt/storage/storage_management_client.py @@ -12,6 +12,9 @@ from msrest.service_client import ServiceClient from msrest import Serializer, Deserializer from msrestazure import AzureConfiguration + +from azure.profiles import KnownProfiles, ProfileDefinition +from azure.profiles.multiapiclient import MultiApiClientMixin from .version import VERSION @@ -49,7 +52,7 @@ def __init__( self.subscription_id = subscription_id -class StorageManagementClient(object): +class StorageManagementClient(MultiApiClientMixin): """The Azure Storage Management API. This ready contains multiple API versions, to help you deal with all Azure clouds @@ -73,21 +76,31 @@ class StorageManagementClient(object): :param str api_version: API version to use if no profile is provided, or if missing in profile. :param str base_url: Service URL - :param profile: A dict using operation group name to API version. - :type profile: dict[str, str] + :param profile: A profile definition, from KnownProfiles to dict. + :type profile: azure.profiles.KnownProfiles """ DEFAULT_API_VERSION='2017-10-01' - DEFAULT_PROFILE = None - - def __init__(self, credentials, subscription_id, api_version=DEFAULT_API_VERSION, base_url=None, profile=DEFAULT_PROFILE): + _PROFILE_TAG = "azure.mgmt.storage.StorageManagementClient" + LATEST_PROFILE = ProfileDefinition({ + _PROFILE_TAG: { + None: DEFAULT_API_VERSION + }}, + _PROFILE_TAG + " latest" + ) + + def __init__(self, credentials, subscription_id, api_version=None, base_url=None, profile=KnownProfiles.default): + super(StorageManagementClient, self).__init__( + credentials=credentials, + subscription_id=subscription_id, + api_version=api_version, + base_url=base_url, + profile=profile + ) self.config = StorageManagementClientConfiguration(credentials, subscription_id, base_url) self._client = ServiceClient(self.config.credentials, self.config) - self.api_version = api_version - self.profile = dict(profile) if profile is not None else {} - ############ Generated from here ############ @classmethod @@ -128,7 +141,7 @@ def operations(self): * 2017-06-01: :class:`Operations` * 2017-10-01: :class:`Operations` """ - api_version = self.profile.get('operations', self.api_version) + api_version = self._get_api_version('operations') if api_version == '2017-06-01': from .v2017_06_01.operations import Operations as OperationClass elif api_version == '2017-10-01': @@ -144,7 +157,7 @@ def skus(self): * 2017-06-01: :class:`SkusOperations` * 2017-10-01: :class:`SkusOperations` """ - api_version = self.profile.get('skus', self.api_version) + api_version = self._get_api_version('skus') if api_version == '2017-06-01': from .v2017_06_01.operations import SkusOperations as OperationClass elif api_version == '2017-10-01': @@ -163,7 +176,7 @@ def storage_accounts(self): * 2017-06-01: :class:`StorageAccountsOperations` * 2017-10-01: :class:`StorageAccountsOperations` """ - api_version = self.profile.get('storage_accounts', self.api_version) + api_version = self._get_api_version('storage_accounts') if api_version == '2015-06-15': from .v2015_06_15.operations import StorageAccountsOperations as OperationClass elif api_version == '2016-01-01': @@ -188,7 +201,7 @@ def usage(self): * 2017-06-01: :class:`UsageOperations` * 2017-10-01: :class:`UsageOperations` """ - api_version = self.profile.get('usage', self.api_version) + api_version = self._get_api_version('usage') if api_version == '2015-06-15': from .v2015_06_15.operations import UsageOperations as OperationClass elif api_version == '2016-01-01': diff --git a/azure-mgmt/tests/recordings/test_mgmt_resource_links.test_links.yaml b/azure-mgmt/tests/recordings/test_mgmt_resource_links.test_links.yaml deleted file mode 100644 index da21bf85eb63..000000000000 --- a/azure-mgmt/tests/recordings/test_mgmt_resource_links.test_links.yaml +++ /dev/null @@ -1,280 +0,0 @@ -interactions: -- request: - body: '{"location": "westus"}' - headers: - Accept: [application/json] - Accept-Encoding: ['gzip, deflate'] - Connection: [keep-alive] - Content-Length: ['22'] - Content-Type: [application/json; charset=utf-8] - User-Agent: [python/3.5.1 (Windows-10-10.0.14393-SP0) requests/2.11.1 msrest/0.4.6 - msrest_azure/0.4.7 resourcemanagementclient/0.31.0 Azure-SDK-For-Python] - accept-language: [en-US] - x-ms-client-request-id: [88cf93da-0376-11e7-b68c-ecb1d756380e] - method: PUT - uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourcegroups/test_mgmt_resource_links_test_links7650e8a?api-version=2016-09-01 - response: - body: {string: '{"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a","name":"test_mgmt_resource_links_test_links7650e8a","location":"westus","properties":{"provisioningState":"Succeeded"}}'} - headers: - Cache-Control: [no-cache] - Content-Length: ['237'] - Content-Type: [application/json; charset=utf-8] - Date: ['Tue, 07 Mar 2017 20:42:10 GMT'] - Expires: ['-1'] - Pragma: [no-cache] - Strict-Transport-Security: [max-age=31536000; includeSubDomains] - x-ms-correlation-request-id: [a3c6a812-10bb-4dd7-8783-fcab61eae671] - x-ms-ratelimit-remaining-subscription-writes: ['1194'] - x-ms-request-id: [a3c6a812-10bb-4dd7-8783-fcab61eae671] - x-ms-routing-request-id: ['WESTUS2:20170307T204210Z:a3c6a812-10bb-4dd7-8783-fcab61eae671'] - status: {code: 201, message: Created} -- request: - body: '{"location": "westus"}' - headers: - Accept: [application/json] - Accept-Encoding: ['gzip, deflate'] - Connection: [keep-alive] - Content-Length: ['22'] - Content-Type: [application/json; charset=utf-8] - User-Agent: [python/3.5.1 (Windows-10-10.0.14393-SP0) requests/2.11.1 msrest/0.4.6 - msrest_azure/0.4.7 resourcemanagementclient/0.31.0 Azure-SDK-For-Python] - accept-language: [en-US] - x-ms-client-request-id: [8990b462-0376-11e7-82ec-ecb1d756380e] - method: PUT - uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourcegroups/FakeGroup1ForLinksTest?api-version=2016-09-01 - response: - body: {string: '{"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/FakeGroup1ForLinksTest","name":"FakeGroup1ForLinksTest","location":"westus","properties":{"provisioningState":"Succeeded"}}'} - headers: - Cache-Control: [no-cache] - Content-Type: [application/json; charset=utf-8] - Date: ['Tue, 07 Mar 2017 20:42:11 GMT'] - Expires: ['-1'] - Pragma: [no-cache] - Strict-Transport-Security: [max-age=31536000; includeSubDomains] - Transfer-Encoding: [chunked] - Vary: [Accept-Encoding] - content-length: ['197'] - x-ms-correlation-request-id: [2f084001-695b-4dca-bb90-50ec36341a21] - x-ms-ratelimit-remaining-subscription-writes: ['1199'] - x-ms-request-id: [2f084001-695b-4dca-bb90-50ec36341a21] - x-ms-routing-request-id: ['WESTUS2:20170307T204211Z:2f084001-695b-4dca-bb90-50ec36341a21'] - status: {code: 200, message: OK} -- request: - body: '{"location": "westus"}' - headers: - Accept: [application/json] - Accept-Encoding: ['gzip, deflate'] - Connection: [keep-alive] - Content-Length: ['22'] - Content-Type: [application/json; charset=utf-8] - User-Agent: [python/3.5.1 (Windows-10-10.0.14393-SP0) requests/2.11.1 msrest/0.4.6 - msrest_azure/0.4.7 resourcemanagementclient/0.31.0 Azure-SDK-For-Python] - accept-language: [en-US] - x-ms-client-request-id: [8a1dd91e-0376-11e7-be96-ecb1d756380e] - method: PUT - uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourcegroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a?api-version=2015-05-01-preview - response: - body: {string: "{\r\n \"properties\": {\r\n \"platformUpdateDomainCount\": - 5,\r\n \"platformFaultDomainCount\": 3\r\n },\r\n \"type\": \"Microsoft.Compute/availabilitySets\",\r\n - \ \"location\": \"westus\",\r\n \"id\": \"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a\",\r\n - \ \"name\": \"pytestavset7650e8a\"\r\n}"} - headers: - Cache-Control: [no-cache] - Content-Type: [application/json; charset=utf-8] - Date: ['Tue, 07 Mar 2017 20:42:12 GMT'] - Expires: ['-1'] - Pragma: [no-cache] - Server: [Microsoft-HTTPAPI/2.0, Microsoft-HTTPAPI/2.0] - Strict-Transport-Security: [max-age=31536000; includeSubDomains] - Transfer-Encoding: [chunked] - Vary: [Accept-Encoding] - content-length: ['393'] - x-ms-correlation-request-id: [200d1e93-59d6-42ea-ab55-e25d42edaa4b] - x-ms-ratelimit-remaining-subscription-writes: ['1193'] - x-ms-request-id: [1130c253-caf4-4853-8113-6eb5114d59b2] - x-ms-routing-request-id: ['WESTUS2:20170307T204212Z:200d1e93-59d6-42ea-ab55-e25d42edaa4b'] - x-ms-served-by: [2d78c99a-5cdc-4580-9eb7-b3e168e83a95_131282043969998685] - status: {code: 200, message: OK} -- request: - body: '{"properties": {"notes": "Testing links", "targetId": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a"}}' - headers: - Accept: [application/json] - Accept-Encoding: ['gzip, deflate'] - Connection: [keep-alive] - Content-Length: ['231'] - Content-Type: [application/json; charset=utf-8] - User-Agent: [python/3.5.1 (Windows-10-10.0.14393-SP0) requests/2.11.1 msrest/0.4.6 - msrest_azure/0.4.7 resourcemanagementclient/0.31.0 Azure-SDK-For-Python] - accept-language: [en-US] - x-ms-client-request-id: [8ac70d6c-0376-11e7-86de-ecb1d756380e] - method: PUT - uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink?api-version=2016-09-01 - response: - body: {string: '{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a/","notes":"Testing - links"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink","type":"Microsoft.Resources/links","name":"myLink"}'} - headers: - Cache-Control: [no-cache] - Content-Length: ['563'] - Content-Type: [application/json; charset=utf-8] - Date: ['Tue, 07 Mar 2017 20:42:13 GMT'] - Expires: ['-1'] - Pragma: [no-cache] - Strict-Transport-Security: [max-age=31536000; includeSubDomains] - x-ms-correlation-request-id: [5da141a3-1784-41ef-97ae-07d59bb09a46] - x-ms-ratelimit-remaining-subscription-writes: ['1197'] - x-ms-request-id: ['westus2:a490b70d-4508-4030-86f7-91b95a66fa82'] - x-ms-routing-request-id: ['WESTUS2:20170307T204213Z:5da141a3-1784-41ef-97ae-07d59bb09a46'] - status: {code: 201, message: Created} -- request: - body: null - headers: - Accept: [application/json] - Accept-Encoding: ['gzip, deflate'] - Connection: [keep-alive] - Content-Type: [application/json; charset=utf-8] - User-Agent: [python/3.5.1 (Windows-10-10.0.14393-SP0) requests/2.11.1 msrest/0.4.6 - msrest_azure/0.4.7 resourcemanagementclient/0.31.0 Azure-SDK-For-Python] - accept-language: [en-US] - x-ms-client-request-id: [915cb61c-0376-11e7-8743-ecb1d756380e] - method: GET - uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink?api-version=2016-09-01 - response: - body: {string: '{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a/","notes":"Testing - links"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink","type":"Microsoft.Resources/links","name":"myLink"}'} - headers: - Cache-Control: [no-cache] - Content-Type: [application/json; charset=utf-8] - Date: ['Tue, 07 Mar 2017 20:42:23 GMT'] - Expires: ['-1'] - Pragma: [no-cache] - Strict-Transport-Security: [max-age=31536000; includeSubDomains] - Transfer-Encoding: [chunked] - Vary: ['Accept-Encoding,Accept-Encoding'] - content-length: ['563'] - x-ms-correlation-request-id: [6b4c3517-4163-467f-8673-fcd6c3053fcf] - x-ms-ratelimit-remaining-subscription-reads: ['14998'] - x-ms-request-id: ['westus2:577408dd-cc05-4067-81cc-ba51e17f38ac'] - x-ms-routing-request-id: ['WESTUS2:20170307T204224Z:6b4c3517-4163-467f-8673-fcd6c3053fcf'] - status: {code: 200, message: OK} -- request: - body: null - headers: - Accept: [application/json] - Accept-Encoding: ['gzip, deflate'] - Connection: [keep-alive] - Content-Type: [application/json; charset=utf-8] - User-Agent: [python/3.5.1 (Windows-10-10.0.14393-SP0) requests/2.11.1 msrest/0.4.6 - msrest_azure/0.4.7 resourcemanagementclient/0.31.0 Azure-SDK-For-Python] - accept-language: [en-US] - x-ms-client-request-id: [91ac2f9a-0376-11e7-899c-ecb1d756380e] - method: GET - uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/providers/Microsoft.Resources/links?api-version=2016-09-01 - response: - body: {string: '{"value":[{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a/","notes":"Testing - links"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink","type":"Microsoft.Resources/links","name":"myLink"}]}'} - headers: - Cache-Control: [no-cache] - Content-Type: [application/json; charset=utf-8] - Date: ['Tue, 07 Mar 2017 20:42:26 GMT'] - Expires: ['-1'] - Pragma: [no-cache] - Strict-Transport-Security: [max-age=31536000; includeSubDomains] - Transfer-Encoding: [chunked] - Vary: ['Accept-Encoding,Accept-Encoding'] - content-length: ['575'] - x-ms-correlation-request-id: [50c23b1c-79bb-4094-ba51-9ae10295445b] - x-ms-ratelimit-remaining-subscription-reads: ['14997'] - x-ms-request-id: ['westus2:2ae85b76-79f5-4fdc-b6db-65d2f01d6724'] - x-ms-routing-request-id: ['WESTUS2:20170307T204227Z:50c23b1c-79bb-4094-ba51-9ae10295445b'] - status: {code: 200, message: OK} -- request: - body: null - headers: - Accept: [application/json] - Accept-Encoding: ['gzip, deflate'] - Connection: [keep-alive] - Content-Type: [application/json; charset=utf-8] - User-Agent: [python/3.5.1 (Windows-10-10.0.14393-SP0) requests/2.11.1 msrest/0.4.6 - msrest_azure/0.4.7 resourcemanagementclient/0.31.0 Azure-SDK-For-Python] - accept-language: [en-US] - x-ms-client-request-id: [938c95ee-0376-11e7-a0cd-ecb1d756380e] - method: GET - uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links?api-version=2016-09-01 - response: - body: {string: '{"value":[{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a/","notes":"Testing - links"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink","type":"Microsoft.Resources/links","name":"myLink"}]}'} - headers: - Cache-Control: [no-cache] - Content-Type: [application/json; charset=utf-8] - Date: ['Tue, 07 Mar 2017 20:42:28 GMT'] - Expires: ['-1'] - Pragma: [no-cache] - Strict-Transport-Security: [max-age=31536000; includeSubDomains] - Transfer-Encoding: [chunked] - Vary: ['Accept-Encoding,Accept-Encoding'] - content-length: ['575'] - x-ms-correlation-request-id: [93908127-ee18-44f7-8e9a-31cb68da555c] - x-ms-ratelimit-remaining-subscription-reads: ['14999'] - x-ms-request-id: ['southcentralus:19ae09b9-f6f2-4373-9e65-010a191ef062'] - x-ms-routing-request-id: ['WESTUS2:20170307T204229Z:93908127-ee18-44f7-8e9a-31cb68da555c'] - status: {code: 200, message: OK} -- request: - body: null - headers: - Accept: [application/json] - Accept-Encoding: ['gzip, deflate'] - Connection: [keep-alive] - Content-Type: [application/json; charset=utf-8] - User-Agent: [python/3.5.1 (Windows-10-10.0.14393-SP0) requests/2.11.1 msrest/0.4.6 - msrest_azure/0.4.7 resourcemanagementclient/0.31.0 Azure-SDK-For-Python] - accept-language: [en-US] - x-ms-client-request-id: [94b4e390-0376-11e7-b90b-ecb1d756380e] - method: GET - uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links?api-version=2016-09-01&$filter=atScope%28%29 - response: - body: {string: '{"value":[{"properties":{"sourceId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/","targetId":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a/","notes":"Testing - links"},"id":"/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink","type":"Microsoft.Resources/links","name":"myLink"}]}'} - headers: - Cache-Control: [no-cache] - Content-Type: [application/json; charset=utf-8] - Date: ['Tue, 07 Mar 2017 20:42:29 GMT'] - Expires: ['-1'] - Pragma: [no-cache] - Strict-Transport-Security: [max-age=31536000; includeSubDomains] - Transfer-Encoding: [chunked] - Vary: ['Accept-Encoding,Accept-Encoding'] - content-length: ['575'] - x-ms-correlation-request-id: [3de7bc9c-f4d1-4eff-b4d9-7d0f4c6b41ef] - x-ms-ratelimit-remaining-subscription-reads: ['14998'] - x-ms-request-id: ['westus2:6409a39f-45b9-4296-b4b5-8f12fd6d0bb2'] - x-ms-routing-request-id: ['WESTUS2:20170307T204229Z:3de7bc9c-f4d1-4eff-b4d9-7d0f4c6b41ef'] - status: {code: 200, message: OK} -- request: - body: null - headers: - Accept: [application/json] - Accept-Encoding: ['gzip, deflate'] - Connection: [keep-alive] - Content-Length: ['0'] - Content-Type: [application/json; charset=utf-8] - User-Agent: [python/3.5.1 (Windows-10-10.0.14393-SP0) requests/2.11.1 msrest/0.4.6 - msrest_azure/0.4.7 resourcemanagementclient/0.31.0 Azure-SDK-For-Python] - accept-language: [en-US] - x-ms-client-request-id: [9504a8ca-0376-11e7-a910-ecb1d756380e] - method: DELETE - uri: https://management.azure.com/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a/providers/Microsoft.Resources/links/myLink?api-version=2016-09-01 - response: - body: {string: ''} - headers: - Cache-Control: [no-cache] - Content-Length: ['0'] - Date: ['Tue, 07 Mar 2017 20:42:29 GMT'] - Expires: ['-1'] - Pragma: [no-cache] - Strict-Transport-Security: [max-age=31536000; includeSubDomains] - x-ms-correlation-request-id: [e74e1b15-b854-482e-979c-833ec00bbebd] - x-ms-ratelimit-remaining-subscription-writes: ['1198'] - x-ms-request-id: ['westus2:2a11089d-b485-4e79-9f53-844c74e3564c'] - x-ms-routing-request-id: ['WESTUS2:20170307T204230Z:e74e1b15-b854-482e-979c-833ec00bbebd'] - status: {code: 200, message: OK} -version: 1 diff --git a/azure-mgmt/tests/test_mgmt_resource_links.py b/azure-mgmt/tests/test_mgmt_resource_links.py deleted file mode 100644 index f0449bc1d8cd..000000000000 --- a/azure-mgmt/tests/test_mgmt_resource_links.py +++ /dev/null @@ -1,83 +0,0 @@ -# coding: utf-8 - -#------------------------------------------------------------------------- -# Copyright (c) Microsoft Corporation. All rights reserved. -# Licensed under the MIT License. See License.txt in the project root for -# license information. -#-------------------------------------------------------------------------- -import unittest - -import azure.mgmt.resource -from testutils.common_recordingtestcase import record -from tests.mgmt_testcase import HttpStatusCode, AzureMgmtTestCase - - -class MgmtResourceLinksTest(AzureMgmtTestCase): - - def setUp(self): - super(MgmtResourceLinksTest, self).setUp() - self.client = self.create_mgmt_client( - azure.mgmt.resource.ManagementLinkClient - ) - - def test_links(self): - if not self.is_playback(): - self.create_resource_group() - self.group_id = self.group.id - group1 = self.resource_client.resource_groups.create_or_update( - "FakeGroup1ForLinksTest", - { - 'location': self.region - } - ) - - resource_name = self.get_resource_name("pytestavset") - create_result = self.resource_client.resources.create_or_update( - resource_group_name=self.group_name, - resource_provider_namespace="Microsoft.Compute", - parent_resource_path="", - resource_type="availabilitySets", - resource_name=resource_name, - api_version="2015-05-01-preview", - parameters={'location': self.region} - ) - result = create_result.result() - self.result_id = result.id - else: - self.group_id = "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test_mgmt_resource_links_test_links7650e8a" - self.result_id = self.group_id + "/providers/Microsoft.Compute/availabilitySets/pytestavset7650e8a" - - with self.recording(): - link = self.client.resource_links.create_or_update( - self.group_id+'/providers/Microsoft.Resources/links/myLink', - { - 'target_id' : self.result_id, - 'notes': 'Testing links' - } - ) - self.assertEqual(link.name, 'myLink') - - if not self.is_playback(): - import time - time.sleep(10) - - link = self.client.resource_links.get(link.id) - self.assertEqual(link.name, 'myLink') - - links = list(self.client.resource_links.list_at_subscription()) - self.assertTrue(any(link.name=='myLink' for link in links)) - - links = list(self.client.resource_links.list_at_source_scope(self.group_id)) - self.assertTrue(any(link.name=='myLink' for link in links)) - - links = list(self.client.resource_links.list_at_source_scope(self.group_id, 'atScope()')) - self.assertTrue(any(link.name=='myLink' for link in links)) - - self.client.resource_links.delete(link.id) - - if not self.is_playback(): - self.resource_client.resource_groups.delete(group1.name) - -#------------------------------------------------------------------------------ -if __name__ == '__main__': - unittest.main() diff --git a/azure-sdk-testutils/devtools_testutils/mgmt_testcase.py b/azure-sdk-testutils/devtools_testutils/mgmt_testcase.py index a0361fe67489..fd03c8d5e4b5 100644 --- a/azure-sdk-testutils/devtools_testutils/mgmt_testcase.py +++ b/azure-sdk-testutils/devtools_testutils/mgmt_testcase.py @@ -12,6 +12,7 @@ ReplayableTest, AzureTestError, AbstractPreparer, GeneralNameReplacer, OAuthRequestResponsesFilter, DeploymentNameReplacer, + RequestUrlNormalizer ) from .config import TEST_SETTING_FILENAME from . import mgmt_settings_fake as fake_settings @@ -73,7 +74,7 @@ def __init__(self, method_name, config_file=None, recording_dir=recording_dir, recording_name=recording_name or self.qualified_test_name, recording_processors=recording_processors or self._get_recording_processors(), - replay_processors=replay_processors, + replay_processors=replay_processors or self._get_replay_processors(), recording_patches=recording_patches, replay_patches=replay_patches, ) @@ -100,6 +101,12 @@ def _get_recording_processors(self): self.scrubber, OAuthRequestResponsesFilter(), DeploymentNameReplacer(), + RequestUrlNormalizer() + ] + + def _get_replay_processors(self): + return [ + RequestUrlNormalizer() ] def is_playback(self): diff --git a/azure-sdk-testutils/devtools_testutils/resource_testcase.py b/azure-sdk-testutils/devtools_testutils/resource_testcase.py index 8484b517db88..14f3df07f0cf 100644 --- a/azure-sdk-testutils/devtools_testutils/resource_testcase.py +++ b/azure-sdk-testutils/devtools_testutils/resource_testcase.py @@ -39,7 +39,10 @@ def create_resource(self, name, **kwargs): name, {'location': self.location} ) else: - self.resource = self.resource or FakeResource(name=name, id='') + self.resource = self.resource or FakeResource( + name=name, + id="/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/"+name + ) return { self.parameter_name: self.resource, self.parameter_name_for_location: self.location, diff --git a/scripts/multiapi_init_gen.py b/scripts/multiapi_init_gen.py index cd10c3d6837c..25d651ad6491 100644 --- a/scripts/multiapi_init_gen.py +++ b/scripts/multiapi_init_gen.py @@ -108,7 +108,7 @@ def build_operation_group(module_name, operation_name, versions): template_intro_doc= ' """Instance depends on the API version:\n\n' template_inside_doc=" * {api_version}: :class:`{clsname}<{module_name}.{api_version_module}.operations.{clsname}>`\n" template_end_doc=' """\n' - template_code_prefix=" api_version = self.profile.get('{attr}', self.api_version)" + template_code_prefix=" api_version = self._get_api_version('{attr}')" template_if = """ {first}if api_version == '{api_version}': from .{api_version_module}.operations import {clsname} as OperationClass""" template_end_def = """ else: