From ff1ff6aa67099414718d855ad37095cc3aabaabb Mon Sep 17 00:00:00 2001 From: Fred-sun Date: Mon, 29 Jun 2020 10:41:24 +0800 Subject: [PATCH] add new test add new test--01 remove unuse file Add FileEndpoint to azure_rm_storageaccount_info (#102) * Add FileEndpoint to azure_rm_storageaccount_info Use hasattr instead of dir (#75) Add ephemeral OS disk for azure_rm_virtualmachine (#124) * Add ephemeral OS disk support for azure_rm_virtualmachine Add ephemeral OS disk for azure_rm_virtualmachinescaleset (#128) * Add ephemeral OS disk support for azure_rm_virtualmachinescaleset Change network_client api_version to match latest default api_version (#157) * #Fixes 156 Change network_client api_version to match latest default api_version * #Fixes 156 Update azure-mgmt-network to 10.2.0 Update 'latest' version listing and default version for Network Client to 2018-08-01 reverse change Add ability to remove all Subnet Service Endpoints when supplying an empty list. (#148) New azure_rm_privatednszone module with tests (#122) * New azure_rm_privatednszone module with tests Co-authored-by: Fred-sun <37327967+Fred-sun@users.noreply.github.com> Co-authored-by: Fred-sun Add new azure active directory related modules (#179) * add ad related modules * release v0.2.0 preparation and minor ad module bug fixing fixing sanity testing errors in ad related modules (#182) * disable ad relate module test * fixing sanity testing errors in ad related modules Fixing issues in azure_rm_deployment_info.py (#180) - Fixing getting the template_link when it does not exist. - Feature: Return the correlation_id Co-authored-by: Steve Kieu azure_rm_virtualmachine: Protect against no diskSizeGB (#185) Disks `diskSizeGB` is not reported if the Virtual Machine is deallocated. Trying to fetch it is causing a `KeyError`. This guards against that KeyError and then nulls out the key so it isn't set incorrectly in the update call. add new Fix wrong module deprecate statement format (#176) * fix wrong module deprecate statement format --- CHANGELOG.md | 21 ++ galaxy.yml | 3 +- log_plugin.log | 0 plugins/module_utils/azure_rm_common.py | 44 ++- plugins/modules/azure_rm_adpassword.py | 291 ++++++++++++++++++ plugins/modules/azure_rm_adpassword_info.py | 214 +++++++++++++ .../modules/azure_rm_adserviceprincipal.py | 216 +++++++++++++ .../azure_rm_adserviceprincipal_info.py | 149 +++++++++ plugins/modules/azure_rm_aks_info.py | 2 +- plugins/modules/azure_rm_aksversion_info.py | 2 +- .../azure_rm_applicationsecuritygroup_info.py | 2 +- .../modules/azure_rm_appserviceplan_info.py | 2 +- .../azure_rm_automationaccount_info.py | 2 +- plugins/modules/azure_rm_autoscale.py | 2 +- plugins/modules/azure_rm_autoscale_info.py | 4 +- .../modules/azure_rm_availabilityset_info.py | 2 +- plugins/modules/azure_rm_cdnendpoint_info.py | 2 +- plugins/modules/azure_rm_cdnprofile_info.py | 2 +- .../azure_rm_containerinstance_info.py | 2 +- .../azure_rm_containerregistry_info.py | 2 +- .../modules/azure_rm_cosmosdbaccount_info.py | 2 +- plugins/modules/azure_rm_deployment_info.py | 5 +- plugins/modules/azure_rm_devtestlab_info.py | 2 +- .../azure_rm_devtestlabarmtemplate_info.py | 3 +- .../azure_rm_devtestlabartifactsource_info.py | 2 +- .../azure_rm_devtestlabcustomimage_info.py | 3 +- .../azure_rm_devtestlabenvironment_info.py | 3 +- .../modules/azure_rm_devtestlabpolicy_info.py | 2 +- .../azure_rm_devtestlabschedule_info.py | 2 +- .../azure_rm_devtestlabvirtualmachine_info.py | 2 +- .../azure_rm_devtestlabvirtualnetwork_info.py | 2 +- plugins/modules/azure_rm_dnsrecordset_info.py | 2 +- plugins/modules/azure_rm_dnszone_info.py | 2 +- plugins/modules/azure_rm_functionapp_info.py | 2 +- .../modules/azure_rm_hdinsightcluster_info.py | 2 +- plugins/modules/azure_rm_image_info.py | 2 +- plugins/modules/azure_rm_loadbalancer_info.py | 2 +- plugins/modules/azure_rm_lock_info.py | 2 +- .../azure_rm_loganalyticsworkspace_info.py | 2 +- .../azure_rm_mariadbconfiguration_info.py | 2 +- .../modules/azure_rm_mariadbdatabase_info.py | 2 +- .../azure_rm_mariadbfirewallrule_info.py | 2 +- .../modules/azure_rm_mariadbserver_info.py | 2 +- .../azure_rm_mysqlconfiguration_info.py | 2 +- .../modules/azure_rm_mysqldatabase_info.py | 2 +- .../azure_rm_mysqlfirewallrule_info.py | 2 +- plugins/modules/azure_rm_mysqlserver_info.py | 2 +- .../modules/azure_rm_networkinterface_info.py | 2 +- .../azure_rm_postgresqlconfiguration_info.py | 2 +- .../azure_rm_postgresqldatabase_info.py | 2 +- .../azure_rm_postgresqlfirewallrule_info.py | 2 +- .../modules/azure_rm_postgresqlserver_info.py | 2 +- plugins/modules/azure_rm_privatednszone.py | 231 ++++++++++++++ .../modules/azure_rm_privatednszone_info.py | 251 +++++++++++++++ .../modules/azure_rm_publicipaddress_info.py | 2 +- plugins/modules/azure_rm_rediscache_info.py | 2 +- plugins/modules/azure_rm_resource_info.py | 2 +- .../modules/azure_rm_resourcegroup_info.py | 2 +- .../modules/azure_rm_roleassignment_info.py | 2 +- .../modules/azure_rm_roledefinition_info.py | 2 +- plugins/modules/azure_rm_routetable_info.py | 2 +- .../modules/azure_rm_securitygroup_info.py | 2 +- plugins/modules/azure_rm_servicebus_info.py | 2 +- plugins/modules/azure_rm_sqldatabase_info.py | 2 +- .../modules/azure_rm_sqlfirewallrule_info.py | 2 +- plugins/modules/azure_rm_sqlserver_info.py | 2 +- .../modules/azure_rm_storageaccount_info.py | 44 ++- plugins/modules/azure_rm_subnet.py | 2 +- plugins/modules/azure_rm_subnet_info.py | 2 +- .../azure_rm_trafficmanagerendpoint_info.py | 2 +- .../azure_rm_trafficmanagerprofile_info.py | 3 +- plugins/modules/azure_rm_virtualmachine.py | 20 +- .../modules/azure_rm_virtualmachine_info.py | 2 +- .../azure_rm_virtualmachineextension_info.py | 2 +- .../azure_rm_virtualmachineimage_info.py | 2 +- .../azure_rm_virtualmachinescaleset.py | 18 +- .../azure_rm_virtualmachinescaleset_info.py | 2 +- ...rm_virtualmachinescalesetextension_info.py | 2 +- ..._rm_virtualmachinescalesetinstance_info.py | 2 +- .../modules/azure_rm_virtualnetwork_info.py | 2 +- .../azure_rm_virtualnetworkpeering_info.py | 3 +- plugins/modules/azure_rm_webapp_info.py | 2 +- pr-pipelines.yml | 1 + requirements-azure.txt | 5 +- .../targets/azure_rm_adpassword/aliases | 4 + .../targets/azure_rm_adpassword/meta/main.yml | 2 + .../azure_rm_adpassword/tasks/main.yml | 103 +++++++ .../azure_rm_adserviceprincipal/aliases | 4 + .../azure_rm_adserviceprincipal/meta/main.yml | 2 + .../tasks/main.yml | 72 +++++ .../azure_rm_monitorlogprofile/tasks/main.yml | 4 +- .../targets/azure_rm_networkinterface/aliases | 2 +- .../targets/azure_rm_postgresqlserver/aliases | 2 +- .../targets/azure_rm_privatednszone/aliases | 4 + .../azure_rm_privatednszone/meta/main.yml | 2 + .../azure_rm_privatednszone/tasks/main.yml | 77 +++++ .../targets/azure_rm_subnet/tasks/main.yml | 12 + .../tasks/azure_test_ephemeral_os.yml | 101 ++++++ .../tasks/main.yml | 57 +++- tests/sanity/ignore-2.11.txt | 27 ++ tests/sanity/ignore-2.9.txt | 11 + tests/utils/ado/ado.sh | 9 +- 102 files changed, 2054 insertions(+), 97 deletions(-) delete mode 100644 log_plugin.log create mode 100644 plugins/modules/azure_rm_adpassword.py create mode 100644 plugins/modules/azure_rm_adpassword_info.py create mode 100644 plugins/modules/azure_rm_adserviceprincipal.py create mode 100644 plugins/modules/azure_rm_adserviceprincipal_info.py create mode 100644 plugins/modules/azure_rm_privatednszone.py create mode 100644 plugins/modules/azure_rm_privatednszone_info.py create mode 100644 tests/integration/targets/azure_rm_adpassword/aliases create mode 100644 tests/integration/targets/azure_rm_adpassword/meta/main.yml create mode 100644 tests/integration/targets/azure_rm_adpassword/tasks/main.yml create mode 100644 tests/integration/targets/azure_rm_adserviceprincipal/aliases create mode 100644 tests/integration/targets/azure_rm_adserviceprincipal/meta/main.yml create mode 100644 tests/integration/targets/azure_rm_adserviceprincipal/tasks/main.yml create mode 100644 tests/integration/targets/azure_rm_privatednszone/aliases create mode 100644 tests/integration/targets/azure_rm_privatednszone/meta/main.yml create mode 100644 tests/integration/targets/azure_rm_privatednszone/tasks/main.yml create mode 100644 tests/integration/targets/azure_rm_virtualmachine/tasks/azure_test_ephemeral_os.yml diff --git a/CHANGELOG.md b/CHANGELOG.md index c5b4761da..3e31152ca 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,26 @@ # Change Log +## v0.2.0 (2020-07-03) + +### NEW MODULES + - azure_rm_privatezone module ([#122](https://github.com/ansible-collections/azure/pull/122)) + - azure_rm_adserviceprincipal module ([#179](https://github.com/ansible-collections/azure/pull/179)) + - azure_rm_adserviceprincipal_info module ([#179](https://github.com/ansible-collections/azure/pull/179)) + - azure_rm_adpassword module ([#179](https://github.com/ansible-collections/azure/pull/179)) + - azure_rm_adpassword_info module ([#179](https://github.com/ansible-collections/azure/pull/179)) + +### FEATURE ENHANCEMENT + - add ability to remove all subnet service endpoints ([#148](https://github.com/ansible-collections/azure/pull/148)) + - update network client api version ([#157](https://github.com/ansible-collections/azure/pull/157)) + - add ephemeral os disk support for azure_rm_virualmachinescaleset ([#128](https://github.com/ansible-collections/azure/pull/128)) + - add ephemeral os disk support for azure_rm_virtualmachine ([#124](https://github.com/ansible-collections/azure/pull/124)) + - add FileEndpoint to azure_rm_storageaccount_info ([#102](https://github.com/ansible-collections/azure/pull/102)) + - add support for managing the 'Firewall and virtual networks' settings in azure_rm_storageaccount ([#108](https://github.com/ansible-collections/azure/pull/108)) + +### BUG FIXING + - bug fixing in azure_rm_aks ([#170](https://github.com/ansible-collections/azure/pull/170)) + - migrate missing doc_fragments that went missing ([#115](https://github.com/ansible-collections/azure/pull/115)) + ## v0.1.3 (2020-05-13) - add new parameter in azure_rm_aks diff --git a/galaxy.yml b/galaxy.yml index 02bad7c4c..281dfb65f 100644 --- a/galaxy.yml +++ b/galaxy.yml @@ -9,7 +9,7 @@ namespace: azure name: azcollection # The version of the collection. Must be compatible with semantic versioning -version: 0.1.3 +version: 0.2.0 # The path to the Markdown (.md) readme file. This path is relative to the root of the collection readme: README.md @@ -18,7 +18,6 @@ readme: README.md # @nicks:irc/im.site#channel' authors: - Microsoft -- Microsoft ### OPTIONAL but strongly recommended diff --git a/log_plugin.log b/log_plugin.log deleted file mode 100644 index e69de29bb..000000000 diff --git a/plugins/module_utils/azure_rm_common.py b/plugins/module_utils/azure_rm_common.py index c4caee3a2..f9f3e6b04 100644 --- a/plugins/module_utils/azure_rm_common.py +++ b/plugins/module_utils/azure_rm_common.py @@ -86,7 +86,7 @@ def default_api_version(self): snapshots='2018-10-01', virtual_machine_run_commands='2018-10-01' ), - 'NetworkManagementClient': '2018-08-01', + 'NetworkManagementClient': '2019-06-01', 'ResourceManagementClient': '2017-05-10', 'StorageManagementClient': '2017-10-01', 'WebSiteManagementClient': '2018-02-01', @@ -227,6 +227,8 @@ def default_api_version(self): from azure.mgmt.storage import StorageManagementClient from azure.mgmt.compute import ComputeManagementClient from azure.mgmt.dns import DnsManagementClient + from azure.mgmt.privatedns import PrivateDnsManagementClient + import azure.mgmt.privatedns.models as PrivateDnsModels from azure.mgmt.monitor import MonitorManagementClient from azure.mgmt.web import WebSiteManagementClient from azure.mgmt.containerservice import ContainerServiceClient @@ -327,6 +329,10 @@ def normalize_location_name(name): 'package_name': 'dns', 'expected_version': '2.1.0' }, + 'PrivateDnsManagementClient': { + 'package_name': 'privatedns', + 'expected_version': '0.1.0' + }, 'WebSiteManagementClient': { 'package_name': 'web', 'expected_version': '0.41.0' @@ -345,7 +351,7 @@ class AzureRMModuleBase(object): def __init__(self, derived_arg_spec, bypass_checks=False, no_log=False, check_invalid_arguments=None, mutually_exclusive=None, required_together=None, required_one_of=None, add_file_common_args=False, supports_check_mode=False, - required_if=None, supports_tags=True, facts_module=False, skip_exec=False): + required_if=None, supports_tags=True, facts_module=False, skip_exec=False, is_ad_resource=False): merged_arg_spec = dict() merged_arg_spec.update(AZURE_COMMON_ARGS) @@ -386,6 +392,7 @@ def __init__(self, derived_arg_spec, bypass_checks=False, no_log=False, self._resource_client = None self._compute_client = None self._dns_client = None + self._private_dns_client = None self._web_client = None self._marketplace_client = None self._sql_client = None @@ -411,7 +418,7 @@ def __init__(self, derived_arg_spec, bypass_checks=False, no_log=False, # self.debug = self.module.params.get('debug') # delegate auth to AzureRMAuth class (shared with all plugin types) - self.azure_auth = AzureRMAuth(fail_impl=self.fail, **self.module.params) + self.azure_auth = AzureRMAuth(fail_impl=self.fail, is_ad_resource=is_ad_resource, **self.module.params) # common parameter validation if self.module.params.get('tags'): @@ -820,6 +827,14 @@ def get_api_profile(self, client_type_name, api_profile_name): # wrap basic strings in a dict that just defines the default return dict(default_api_version=profile_raw) + def get_graphrbac_client(self, tenant_id): + from azure.graphrbac import GraphRbacManagementClient + cred = self.azure_auth.azure_credentials + base_url = self.azure_auth._cloud_environment.endpoints.active_directory_graph_resource_id + client = GraphRbacManagementClient(cred, tenant_id, base_url) + + return client + def get_mgmt_svc_client(self, client_type, base_url=None, api_version=None): self.log('Getting management service client {0}'.format(client_type.__name__)) self.check_client_version(client_type) @@ -989,6 +1004,20 @@ def dns_models(self): self.log("Getting dns models...") return DnsManagementClient.models('2018-05-01') + @property + def private_dns_client(self): + self.log('Getting private dns client') + if not self._private_dns_client: + self._private_dns_client = self.get_mgmt_svc_client( + PrivateDnsManagementClient, + base_url=self._cloud_environment.endpoints.resource_manager) + return self._private_dns_client + + @property + def private_dns_models(self): + self.log('Getting private dns models') + return PrivateDnsModels + @property def web_client(self): self.log('Getting web client') @@ -1204,7 +1233,7 @@ class AzureRMAuthException(Exception): class AzureRMAuth(object): def __init__(self, auth_source='auto', profile=None, subscription_id=None, client_id=None, secret=None, tenant=None, ad_user=None, password=None, cloud_environment='AzureCloud', cert_validation_mode='validate', - api_profile='latest', adfs_authority_url=None, fail_impl=None, **kwargs): + api_profile='latest', adfs_authority_url=None, fail_impl=None, is_ad_resource=False, **kwargs): if fail_impl: self._fail_impl = fail_impl @@ -1213,6 +1242,7 @@ def __init__(self, auth_source='auto', profile=None, subscription_id=None, clien self._cloud_environment = None self._adfs_authority_url = None + self.is_ad_resource = is_ad_resource # authenticate self.credentials = self._get_credentials( @@ -1358,8 +1388,10 @@ def _get_msi_credentials(self, subscription_id_param=None, **kwargs): 'subscription_id': subscription_id } - def _get_azure_cli_credentials(self): - credentials, subscription_id = get_azure_cli_credentials() + def _get_azure_cli_credentials(self, resource=None): + if self.is_ad_resource: + resource = 'https://graph.windows.net/' + credentials, subscription_id = get_azure_cli_credentials(resource) cloud_environment = get_cli_active_cloud() cli_credentials = { diff --git a/plugins/modules/azure_rm_adpassword.py b/plugins/modules/azure_rm_adpassword.py new file mode 100644 index 000000000..97823f2f1 --- /dev/null +++ b/plugins/modules/azure_rm_adpassword.py @@ -0,0 +1,291 @@ +#!/usr/bin/python +# +# Copyright (c) 2020 Haiyuan Zhang, +# +# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) + +from __future__ import absolute_import, division, print_function +import datetime + +__metaclass__ = type + + +ANSIBLE_METADATA = {'metadata_version': '1.1', + 'status': ['preview'], + 'supported_by': 'community'} + +DOCUMENTATION = ''' +--- +module: azure_rm_adpassword + +version_added: "2.10" + +short_description: Manage application password + +description: + - Manage application password. + +options: + app_id: + description: + - The application ID. + type: str + service_principal_object_id: + description: + - The service principal object ID. + type: str + key_id: + description: + - The password key ID. + type: str + tenant: + description: + - The tenant ID. + type: str + required: True + end_date: + description: + - Date or datemtime after which credentials expire. + - Default value is one year after current time. + type: str + value: + description: + - The application password value. + - Length greater than 18 characters. + type: str + app_object_id: + description: + - The application object ID. + type: str + state: + description: + - Assert the state of Active Dirctory Password. + - Use C(present) to create or update a Password and use C(absent) to delete. + - Update is not supported, if I(state=absent) and I(key_id=None), then all passwords of the application will be deleted. + default: present + choices: + - absent + - present + type: str + +extends_documentation_fragment: + - azure.azcollection.azure + - azure.azcollection.azure_tags + +author: + haiyuan_zhang (@haiyuazhang) + Fred-sun (@Fred-sun) + +''' + +EXAMPLES = ''' + - name: create ad password + azure_rm_adpassword: + app_id: "{{ app_id }}" + state: present + value: "$abc12345678" + tenant: "{{ tenant_id }}" +''' + +RETURN = ''' +end_date: + description: + - Date or datemtime after which credentials expire. + - Default value is one year after current time. + type: str + returned: always + sample: 2021-06-28T06:00:32.637070+00:00 +key_id: + description: + - The password key ID + type: str + returned: always + sample: xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx +start_date: + description: + - Date or datetime at which credentials become valid. + - Default value is current time. + type: str + returned: always + sample: 2020-06-28T06:00:32.637070+00:00 + +''' + +from ansible_collections.azure.azcollection.plugins.module_utils.azure_rm_common import AzureRMModuleBase + +try: + from msrestazure.azure_exceptions import CloudError + from azure.graphrbac.models import GraphErrorException + from azure.graphrbac.models import PasswordCredential + from azure.graphrbac.models import ApplicationUpdateParameters + from dateutil.relativedelta import relativedelta +except ImportError: + # This is handled in azure_rm_common + pass + + +class AzureRMADPassword(AzureRMModuleBase): + def __init__(self): + + self.module_arg_spec = dict( + app_id=dict(type='str'), + service_principal_object_id=dict(type='str'), + app_object_id=dict(type='str'), + key_id=dict(type='str'), + tenant=dict(type='str', required=True), + value=dict(type='str'), + end_date=dict(type='str'), + state=dict(type='str', default='present', choices=['present', 'absent']), + ) + + self.state = None + self.tenant = None + self.app_id = None + self.service_principal_object_id = None + self.app_object_id = None + self.key_id = None + self.value = None + self.end_date = None + self.results = dict(changed=False) + + self.client = None + + super(AzureRMADPassword, self).__init__(derived_arg_spec=self.module_arg_spec, + supports_check_mode=False, + supports_tags=False, + is_ad_resource=True) + + def exec_module(self, **kwargs): + for key in list(self.module_arg_spec.keys()): + setattr(self, key, kwargs[key]) + + self.client = self.get_graphrbac_client(self.tenant) + self.resolve_app_obj_id() + passwords = self.get_all_passwords() + + if self.state == 'present': + if self.key_id and self.key_exists(passwords): + self.update(passwords) + else: + self.create_password(passwords) + else: + if self.key_id is None: + self.delete_all_passwords(passwords) + else: + self.delete_password(passwords) + + return self.results + + def key_exists(self, old_passwords): + for pd in old_passwords: + if pd.key_id == self.key_id: + return True + return False + + def resolve_app_obj_id(self): + try: + if self.app_object_id is not None: + return + elif self.app_id or self.service_principal_object_id: + if not self.app_id: + sp = self.client.service_principals.get(self.service_principal_object_id) + self.app_id = sp.app_id + if not self.app_id: + self.fail("can't resolve app via service principal object id {0}".format(self.service_principal_object_id)) + + result = list(self.client.applications.list(filter="appId eq '{0}'".format(self.app_id))) + if result: + self.app_object_id = result[0].object_id + else: + self.fail("can't resolve app via app id {0}".format(self.app_id)) + else: + self.fail("one of the [app_id, app_object_id, service_principal_id] must be set") + + except GraphErrorException as ge: + self.fail("error in resolve app_object_id {0}".format(str(ge))) + + def get_all_passwords(self): + + try: + return list(self.client.applications.list_password_credentials(self.app_object_id)) + except GraphErrorException as ge: + self.fail("failed to fetch passwords for app {0}: {1}".format(self.app_object_id, str(ge))) + + def delete_all_passwords(self, old_passwords): + + if len(old_passwords) == 0: + self.results['changed'] = False + return + try: + self.client.applications.patch(self.app_object_id, ApplicationUpdateParameters(password_credentials=[])) + self.results['changed'] = True + except GraphErrorException as ge: + self.fail("fail to purge all passwords for app: {0} - {1}".format(self.app_object_id, str(ge))) + + def delete_password(self, old_passwords): + if not self.key_exists(old_passwords): + self.results['changed'] = False + return + + num_of_passwords_before_delete = len(old_passwords) + + for pd in old_passwords: + if pd.key_id == self.key_id: + old_passwords.remove(pd) + break + try: + self.client.applications.patch(self.app_object_id, ApplicationUpdateParameters(password_credentials=old_passwords)) + num_of_passwords_after_delete = len(self.get_all_passwords()) + if num_of_passwords_after_delete != num_of_passwords_before_delete: + self.results['changed'] = True + + except GraphErrorException as ge: + self.fail("failed to delete password with key id {0} - {1}".format(self.app_id, str(ge))) + + def create_password(self, old_passwords): + def gen_guid(): + import uuid + return uuid.uuid4() + + if self.value is None: + self.fail("when creating a new password, module parameter value can't be None") + + start_date = datetime.datetime.now(datetime.timezone.utc) + end_date = self.end_date or start_date + relativedelta(years=1) + value = self.value + key_id = self.key_id or str(gen_guid()) + + new_password = PasswordCredential(start_date=start_date, end_date=end_date, key_id=key_id, + value=value, custom_key_identifier=None) + old_passwords.append(new_password) + + try: + client = self.get_graphrbac_client(self.tenant) + app_patch_parameters = ApplicationUpdateParameters(password_credentials=old_passwords) + client.applications.patch(self.app_object_id, app_patch_parameters) + + new_passwords = self.get_all_passwords() + for pd in new_passwords: + if pd.key_id == key_id: + self.results['changed'] = True + self.results.update(self.to_dict(pd)) + except GraphErrorException as ge: + self.fail("failed to create new password: {0}".format(str(ge))) + + def update_password(self, old_passwords): + self.fail("update existing password is not supported") + + def to_dict(self, pd): + return dict( + end_date=pd.end_date, + start_date=pd.start_date, + key_id=pd.key_id + ) + + +def main(): + AzureRMADPassword() + + +if __name__ == '__main__': + main() diff --git a/plugins/modules/azure_rm_adpassword_info.py b/plugins/modules/azure_rm_adpassword_info.py new file mode 100644 index 000000000..8d4902807 --- /dev/null +++ b/plugins/modules/azure_rm_adpassword_info.py @@ -0,0 +1,214 @@ +#!/usr/bin/python +# +# Copyright (c) 2020 Haiyuan Zhang, +# +# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) + +from __future__ import absolute_import, division, print_function +import datetime + +__metaclass__ = type + + +ANSIBLE_METADATA = {'metadata_version': '1.1', + 'status': ['preview'], + 'supported_by': 'community'} + +DOCUMENTATION = ''' +module: azure_rm_adpassword_info + +version_added: "2.10" + +short_description: Get application password info + +description: + - Get application password info. + +options: + app_id: + description: + - The application ID. + type: str + service_principal_object_id: + description: + - The service principal object ID. + type: str + key_id: + description: + - The password key ID. + type: str + tenant: + description: + - The tenant ID. + type: str + required: True + end_date: + description: + - Date or datemtime after which credentials expire. + - Default value is one year after current time. + type: str + value: + description: + - The application password value. + - Length greater than 18 characters. + type: str + app_object_id: + description: + - The application object ID. + type: str + +extends_documentation_fragment: + - azure.azcollection.azure + - azure.azcollection.azure_tags + +author: + haiyuan_zhang (@haiyuazhang) + Fred-sun (@Fred-sun) +''' + +EXAMPLES = ''' + - name: get ad password info + azure_rm_adpassword_info: + app_id: "{{ app_id }}" + tenant: "{{ tenant_id }}" + key_id: "{{ key_id }}" +''' + +RETURN = ''' +passwords: + description: + - The password info. + returned: success + type: dict + contains: + custom_key_identifier: + description: + - Custom key identifier. + type: str + returned: always + sample: None + end_date: + description: + - Date or datemtime after which credentials expire. + - Default value is one year after current time. + type: datetime + returned: always + sample: 2021-06-18T06:51:25.508304+00:00 + key_id: + description: + - The password key ID. + type: str + returned: always + sample: xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx + start_date: + description: + - Date or datetime at which credentials become valid. + - Default value is current time + type: datetime + returned: always + sample: 2020-06-18T06:51:25.508304+00:00 + +''' + +from ansible_collections.azure.azcollection.plugins.module_utils.azure_rm_common import AzureRMModuleBase + +try: + from msrestazure.azure_exceptions import CloudError + from azure.graphrbac.models import GraphErrorException + from azure.graphrbac.models import PasswordCredential + from azure.graphrbac.models import ApplicationUpdateParameters +except ImportError: + # This is handled in azure_rm_common + pass + + +class AzureRMADPasswordInfo(AzureRMModuleBase): + def __init__(self): + + self.module_arg_spec = dict( + app_id=dict(type='str'), + app_object_id=dict(type='str'), + service_principal_object_id=dict(type='str'), + key_id=dict(type='str'), + tenant=dict(type='str', required=True), + value=dict(type='str'), + end_date=dict(type='str'), + ) + + self.tenant = None + self.app_id = None + self.service_principal_object_id = None + self.app_object_id = None + self.key_id = None + self.value = None + self.end_date = None + self.results = dict(changed=False) + + self.client = None + + super(AzureRMADPasswordInfo, self).__init__(derived_arg_spec=self.module_arg_spec, + supports_check_mode=False, + supports_tags=False, + is_ad_resource=True) + + def exec_module(self, **kwargs): + + for key in list(self.module_arg_spec.keys()): + setattr(self, key, kwargs[key]) + + self.client = self.get_graphrbac_client(self.tenant) + self.resolve_app_obj_id() + passwords = self.get_all_passwords() + + if self.key_id: + filtered = [pd for pd in passwords if pd.key_id == self.key_id] + self.results['passwords'] = [self.to_dict(pd) for pd in filtered] + else: + self.results['passwords'] = [self.to_dict(pd) for pd in passwords] + + return self.results + + def resolve_app_obj_id(self): + try: + if self.app_object_id is not None: + return + elif self.app_id or self.service_principal_object_id: + if not self.app_id: + sp = self.client.service_principals.get(self.service_principal_id) + self.app_id = sp.app_id + if not self.app_id: + self.fail("can't resolve app via service principal object id {0}".format(self.service_principal_object_id)) + + result = list(self.client.applications.list(filter="appId eq '{0}'".format(self.app_id))) + if result: + self.app_object_id = result[0].object_id + else: + self.fail("can't resolve app via app id {0}".format(self.app_id)) + else: + self.fail("one of the [app_id, app_object_id, service_principal_id] must be set") + + except GraphErrorException as ge: + self.fail("error in resolve app_object_id {0}".format(str(ge))) + + def get_all_passwords(self): + + try: + return list(self.client.applications.list_password_credentials(self.app_object_id)) + except GraphErrorException as ge: + self.fail("failed to fetch passwords for app {0}: {1}".format(self.app_object_id, str(ge))) + + def to_dict(self, pd): + return dict( + end_date=pd.end_date, + start_date=pd.start_date, + key_id=pd.key_id, + custom_key_identifier=str(pd.custom_key_identifier) + ) + + +def main(): + AzureRMADPasswordInfo() + + +if __name__ == '__main__': + main() diff --git a/plugins/modules/azure_rm_adserviceprincipal.py b/plugins/modules/azure_rm_adserviceprincipal.py new file mode 100644 index 000000000..82deb0614 --- /dev/null +++ b/plugins/modules/azure_rm_adserviceprincipal.py @@ -0,0 +1,216 @@ +#!/usr/bin/python +# +# Copyright (c) 2020 Haiyuan Zhang, +# +# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) + +from __future__ import absolute_import, division, print_function +__metaclass__ = type + + +ANSIBLE_METADATA = {'metadata_version': '1.1', + 'status': ['preview'], + 'supported_by': 'community'} + +DOCUMENTATION = ''' +--- +module: azure_rm_adserviceprincipal + +version_added: "2.10" + +short_description: Manage Azure Active Directory service principal + +description: + - Manage Azure Active Directory service principal. + +options: + app_id: + description: + - The application ID. + type: str + required: True + tenant: + description: + - The tenant ID. + type: str + required: True + app_role_assignment_required: + description: + - Whether the Role of the Service Principal is set. + type: bool + state: + description: + - Assert the state of Active Dirctory service principal. + - Use C(present) to create or update a Password and use C(absent) to delete. + default: present + choices: + - absent + - present + type: str + +extends_documentation_fragment: + - azure.azcollection.azure + - azure.azcollection.azure_tags + +author: + haiyuan_zhang (@haiyuazhang) + Fred-sun (@Fred-sun) +''' + +EXAMPLES = ''' + - name: create ad sp + azure_ad_serviceprincipal: + app_id: "{{ app_id }}" + state: present + tenant: "{{ tenant_id }}" +''' + +RETURN = ''' +app_display_name: + description: + - Object's display name or its prefix. + type: str + returned: always + sample: fredAKSCluster +app_id: + description: + - The application ID. + returned: always + type: str + sample: xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx +app_role_assignment_required: + description: + - Whether the Role of the Service Principal is set. + returned: always + type: bool + sample: false +object_id: + description: + - Object ID of the associated service principal. + returned: always + type: str + sample: xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx + +''' + +from ansible_collections.azure.azcollection.plugins.module_utils.azure_rm_common_ext import AzureRMModuleBaseExt + +try: + from msrestazure.azure_exceptions import CloudError + from azure.graphrbac.models import GraphErrorException +except ImportError: + # This is handled in azure_rm_common + pass + + +class AzureRMADServicePrincipal(AzureRMModuleBaseExt): + def __init__(self): + + self.module_arg_spec = dict( + app_id=dict(type='str', required=True), + tenant=dict(type='str', required=True), + state=dict(type='str', default='present', choices=['present', 'absent']), + app_role_assignment_required=dict(type='bool') + ) + + self.state = None + self.tenant = None + self.app_id = None + self.app_role_assignment_required = None + self.object_id = None + self.results = dict(changed=False) + + super(AzureRMADServicePrincipal, self).__init__(derived_arg_spec=self.module_arg_spec, + supports_check_mode=False, + supports_tags=False, + is_ad_resource=True) + + def exec_module(self, **kwargs): + + for key in list(self.module_arg_spec.keys()): + setattr(self, key, kwargs[key]) + + response = self.get_resource() + + if response: + if self.state == 'present': + if self.check_update(response): + self.update_resource(response) + elif self.state == 'absent': + self.delete_resource(response) + else: + if self.state == 'present': + self.create_resource() + elif self.state == 'absent': + self.log("try to delete non exist resource") + + return self.results + + def create_resource(self): + from azure.graphrbac.models import ServicePrincipalCreateParameters + try: + client = self.get_graphrbac_client(self.tenant) + response = client.service_principals.create(ServicePrincipalCreateParameters(app_id=self.app_id, account_enabled=True)) + self.results['changed'] = True + self.results.update(self.to_dict(response)) + return response + except GraphErrorException as ge: + self.fail("Error creating service principle, app id {0} - {1}".format(self.app_id, str(ge))) + + def update_resource(self, old_response): + try: + from azure.graphrbac.models import ServicePrincipalUpdateParameters + client = self.get_graphrbac_client(self.tenant) + to_update = {} + if self.app_role_assignment_required is not None: + to_update['app_role_assignment_required'] = self.app_role_assignment_required + + client.service_principals.update(old_response['object_id'], to_update) + self.results['changed'] = True + self.results.update(self.get_resource()) + + except GraphErrorException as ge: + self.fail("Error updating the service principal app_id {0} - {1}".format(self.app_id, str(ge))) + + def delete_resource(self, response): + try: + client = self.get_graphrbac_client(self.tenant) + client.service_principals.delete(response.get('object_id')) + self.results['changed'] = True + return True + except GraphErrorException as ge: + self.fail("Error deleting service principal app_id {0} - {1}".format(self.app_id, str(ge))) + + def get_resource(self): + try: + client = self.get_graphrbac_client(self.tenant) + result = list(client.service_principals.list(filter="servicePrincipalNames/any(c:c eq '{0}')".format(self.app_id))) + if not result: + return False + result = result[0] + return self.to_dict(result) + except GraphErrorException as ge: + self.log("Did not find the graph instance instance {0} - {1}".format(self.app_id, str(ge))) + return False + + def check_update(self, response): + app_assignment_changed = self.app_role_assignment_required is not None and \ + self.app_role_assignment_required != response.get('app_role_assignment_required', None) + + return False or self.app_role_assignment_required + + def to_dict(self, object): + return dict( + app_id=object.app_id, + object_id=object.object_id, + app_display_name=object.display_name, + app_role_assignment_required=object.app_role_assignment_required + ) + + +def main(): + AzureRMADServicePrincipal() + + +if __name__ == '__main__': + main() diff --git a/plugins/modules/azure_rm_adserviceprincipal_info.py b/plugins/modules/azure_rm_adserviceprincipal_info.py new file mode 100644 index 000000000..d9e3311e9 --- /dev/null +++ b/plugins/modules/azure_rm_adserviceprincipal_info.py @@ -0,0 +1,149 @@ +#!/usr/bin/python +# +# Copyright (c) 2020 Haiyuan Zhang, +# +# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) + +from __future__ import absolute_import, division, print_function +__metaclass__ = type + + +ANSIBLE_METADATA = {'metadata_version': '1.1', + 'status': ['preview'], + 'supported_by': 'community'} + +DOCUMENTATION = ''' +module: azure_rm_adserviceprincipal_info + +version_added: "2.10" + +short_description: Get Azure Active Directory service principal info + +description: + - Get Azure Active Directory service principal info. + +options: + app_id: + description: + - The application ID. + type: str + tenant: + description: + - The tenant ID. + type: str + required: True + object_id: + description: + - It's service principal's object ID. + type: str + +extends_documentation_fragment: + - azure.azcollection.azure + - azure.azcollection.azure_tags + +author: + haiyuan_zhang (@haiyuazhang) + Fred-sun (@Fred-sun) +''' + +EXAMPLES = ''' + - name: get ad sp info + azure_rm_adserviceprincipal_info: + app_id: "{{ app_id }}" + tenant: "{{ tenant_id }}" + +''' + +RETURN = ''' +app_display_name: + description: + - Object's display name or its prefix. + type: str + returned: always + sample: sp +app_id: + description: + - The application ID. + returned: always + type: str + sample: xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx +app_role_assignment_required: + description: + - Whether the Role of the Service Principal is set. + type: bool + returned: always + sample: false +object_id: + description: + - It's service principal's object ID. + returned: always + type: str + sample: xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx + + +''' + +from ansible_collections.azure.azcollection.plugins.module_utils.azure_rm_common_ext import AzureRMModuleBase + +try: + from msrestazure.azure_exceptions import CloudError + from azure.graphrbac.models import GraphErrorException +except ImportError: + # This is handled in azure_rm_common + pass + + +class AzureRMADServicePrincipalInfo(AzureRMModuleBase): + def __init__(self): + + self.module_arg_spec = dict( + app_id=dict(type='str'), + object_id=dict(type='str'), + tenant=dict(type='str', required=True), + ) + + self.tenant = None + self.app_id = None + self.object_id = None + self.results = dict(changed=False) + + super(AzureRMADServicePrincipalInfo, self).__init__(derived_arg_spec=self.module_arg_spec, + supports_check_mode=False, + supports_tags=False, + is_ad_resource=True) + + def exec_module(self, **kwargs): + + for key in list(self.module_arg_spec.keys()): + setattr(self, key, kwargs[key]) + + service_principals = [] + + try: + client = self.get_graphrbac_client(self.tenant) + if self.object_id is None: + service_principals = list(client.service_principals.list(filter="servicePrincipalNames/any(c:c eq '{0}')".format(self.app_id))) + else: + service_principals = [client.service_principals.get(self.object_id)] + + self.results['service_principals'] = [self.to_dict(sp) for sp in service_principals] + except GraphErrorException as ge: + self.fail("failed to get service principal info {0}".format(str(ge))) + + return self.results + + def to_dict(self, object): + return dict( + app_id=object.app_id, + object_id=object.object_id, + app_display_name=object.display_name, + app_role_assignment_required=object.app_role_assignment_required + ) + + +def main(): + AzureRMADServicePrincipalInfo() + + +if __name__ == '__main__': + main() diff --git a/plugins/modules/azure_rm_aks_info.py b/plugins/modules/azure_rm_aks_info.py index 162c7d7a9..8194a44a6 100644 --- a/plugins/modules/azure_rm_aks_info.py +++ b/plugins/modules/azure_rm_aks_info.py @@ -116,7 +116,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_aks_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_aks_facts' module has been renamed to 'azure_rm_aks_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_aks_facts' module has been renamed to 'azure_rm_aks_info'", version=(2.9, )) for key in self.module_args: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_aksversion_info.py b/plugins/modules/azure_rm_aksversion_info.py index 56b8f83d3..98a3a4e9f 100644 --- a/plugins/modules/azure_rm_aksversion_info.py +++ b/plugins/modules/azure_rm_aksversion_info.py @@ -93,7 +93,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_aksversion_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_aksversion_facts' module has been renamed to 'azure_rm_aksversion_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_aksversion_facts' module has been renamed to 'azure_rm_aksversion_info'", version=(2.9, )) for key in self.module_args: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_applicationsecuritygroup_info.py b/plugins/modules/azure_rm_applicationsecuritygroup_info.py index 4c0b7c367..314de0a55 100644 --- a/plugins/modules/azure_rm_applicationsecuritygroup_info.py +++ b/plugins/modules/azure_rm_applicationsecuritygroup_info.py @@ -139,7 +139,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_applicationsecuritygroup_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_applicationsecuritygroup_facts' module has been renamed to 'azure_rm_applicationsecuritygroup_info'", - version=(2, 9)) + version=(2.9, )) for key in list(self.module_arg_spec.keys()) + ['tags']: if hasattr(self, key): diff --git a/plugins/modules/azure_rm_appserviceplan_info.py b/plugins/modules/azure_rm_appserviceplan_info.py index c402969c8..ccf857a0c 100644 --- a/plugins/modules/azure_rm_appserviceplan_info.py +++ b/plugins/modules/azure_rm_appserviceplan_info.py @@ -156,7 +156,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_appserviceplan_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_appserviceplan_facts' module has been renamed to 'azure_rm_appserviceplan_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_appserviceplan_facts' module has been renamed to 'azure_rm_appserviceplan_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_automationaccount_info.py b/plugins/modules/azure_rm_automationaccount_info.py index ce41153e7..021706c56 100644 --- a/plugins/modules/azure_rm_automationaccount_info.py +++ b/plugins/modules/azure_rm_automationaccount_info.py @@ -285,7 +285,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_automationaccount_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_automationaccount_facts' module has been renamed to 'azure_rm_automationaccount_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_automationaccount_facts' module has been renamed to 'azure_rm_automationaccount_info'", version=(2.9, )) for key in list(self.module_arg_spec): setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_autoscale.py b/plugins/modules/azure_rm_autoscale.py index b60138365..1921d240a 100644 --- a/plugins/modules/azure_rm_autoscale.py +++ b/plugins/modules/azure_rm_autoscale.py @@ -373,7 +373,7 @@ def timedelta_to_minutes(time): def get_enum_value(item): - if 'value' in dir(item): + if hasattr(item, 'value'): return to_native(item.value) return to_native(item) diff --git a/plugins/modules/azure_rm_autoscale_info.py b/plugins/modules/azure_rm_autoscale_info.py index a2c6ba493..ed0370fdd 100644 --- a/plugins/modules/azure_rm_autoscale_info.py +++ b/plugins/modules/azure_rm_autoscale_info.py @@ -133,7 +133,7 @@ def timedelta_to_minutes(time): def get_enum_value(item): - if 'value' in dir(item): + if hasattr(item, 'value'): return to_native(item.value) return to_native(item) @@ -233,7 +233,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_autoscale_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_autoscale_facts' module has been renamed to 'azure_rm_autoscale_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_autoscale_facts' module has been renamed to 'azure_rm_autoscale_info'", version=(2.9, )) for key in list(self.module_arg_spec): setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_availabilityset_info.py b/plugins/modules/azure_rm_availabilityset_info.py index 15b9fe4ae..ec2c64407 100644 --- a/plugins/modules/azure_rm_availabilityset_info.py +++ b/plugins/modules/azure_rm_availabilityset_info.py @@ -148,7 +148,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_availabilityset_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_availabilityset_facts' module has been renamed to 'azure_rm_availabilityset_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_availabilityset_facts' module has been renamed to 'azure_rm_availabilityset_info'", version=(2.9, )) for key in self.module_args: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_cdnendpoint_info.py b/plugins/modules/azure_rm_cdnendpoint_info.py index 4bf76ff34..0d38c16c2 100644 --- a/plugins/modules/azure_rm_cdnendpoint_info.py +++ b/plugins/modules/azure_rm_cdnendpoint_info.py @@ -218,7 +218,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_cdnendpoint_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_cdnendpoint_facts' module has been renamed to 'azure_rm_cdnendpoint_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_cdnendpoint_facts' module has been renamed to 'azure_rm_cdnendpoint_info'", version=(2.9, )) for key in self.module_args: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_cdnprofile_info.py b/plugins/modules/azure_rm_cdnprofile_info.py index 2836eb923..af5ecf023 100644 --- a/plugins/modules/azure_rm_cdnprofile_info.py +++ b/plugins/modules/azure_rm_cdnprofile_info.py @@ -160,7 +160,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_cdnprofile_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_cdnprofile_facts' module has been renamed to 'azure_rm_cdnprofile_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_cdnprofile_facts' module has been renamed to 'azure_rm_cdnprofile_info'", version=(2.9, )) for key in self.module_args: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_containerinstance_info.py b/plugins/modules/azure_rm_containerinstance_info.py index 6ec5f9b3f..52b770c8b 100644 --- a/plugins/modules/azure_rm_containerinstance_info.py +++ b/plugins/modules/azure_rm_containerinstance_info.py @@ -212,7 +212,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_containerinstance_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_containerinstance_facts' module has been renamed to 'azure_rm_containerinstance_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_containerinstance_facts' module has been renamed to 'azure_rm_containerinstance_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_containerregistry_info.py b/plugins/modules/azure_rm_containerregistry_info.py index 17d11e3d0..5f469830b 100644 --- a/plugins/modules/azure_rm_containerregistry_info.py +++ b/plugins/modules/azure_rm_containerregistry_info.py @@ -183,7 +183,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_containerregistry_info' if is_old_facts: - self.module.deprecate("The 'azure_rm_containerregistry_facts' module has been renamed to 'azure_rm_containerregistry_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_containerregistry_facts' module has been renamed to 'azure_rm_containerregistry_info'", version=(2.9, )) for key in list(self.module_arg_spec) + ['tags']: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_cosmosdbaccount_info.py b/plugins/modules/azure_rm_cosmosdbaccount_info.py index 89b8e062e..44899f91e 100644 --- a/plugins/modules/azure_rm_cosmosdbaccount_info.py +++ b/plugins/modules/azure_rm_cosmosdbaccount_info.py @@ -394,7 +394,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_cosmosdbaccount_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_cosmosdbaccount_facts' module has been renamed to 'azure_rm_cosmosdbaccount_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_cosmosdbaccount_facts' module has been renamed to 'azure_rm_cosmosdbaccount_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_deployment_info.py b/plugins/modules/azure_rm_deployment_info.py index 37567a50c..7f2986bd4 100644 --- a/plugins/modules/azure_rm_deployment_info.py +++ b/plugins/modules/azure_rm_deployment_info.py @@ -157,7 +157,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_deployment_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_deployment_facts' module has been renamed to 'azure_rm_deployment_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_deployment_facts' module has been renamed to 'azure_rm_deployment_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) @@ -236,7 +236,8 @@ def format_response(self, item): 'parameters': d.get('properties', {}).get('parameters'), 'outputs': d.get('properties', {}).get('outputs'), 'output_resources': output_resources_list, - 'template_link': d.get('properties', {}).get('template_link').get('uri') + 'template_link': d.get('properties', {}).get('template_link', {}).get('uri'), + 'correlation_id': d.get('properties', {}).get('correlation_id') } return d diff --git a/plugins/modules/azure_rm_devtestlab_info.py b/plugins/modules/azure_rm_devtestlab_info.py index aab71ee0e..2a12b8643 100644 --- a/plugins/modules/azure_rm_devtestlab_info.py +++ b/plugins/modules/azure_rm_devtestlab_info.py @@ -181,7 +181,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_devtestlab_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_devtestlab_facts' module has been renamed to 'azure_rm_devtestlab_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_devtestlab_facts' module has been renamed to 'azure_rm_devtestlab_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_devtestlabarmtemplate_info.py b/plugins/modules/azure_rm_devtestlabarmtemplate_info.py index ab033c47d..039f85173 100644 --- a/plugins/modules/azure_rm_devtestlabarmtemplate_info.py +++ b/plugins/modules/azure_rm_devtestlabarmtemplate_info.py @@ -155,7 +155,8 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_devtestlabarmtemplate_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_devtestlabarmtemplate_facts' module has been renamed to 'azure_rm_devtestlabarmtemplate_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_devtestlabarmtemplate_facts' module has been renamed to 'azure_rm_devtestlabarmtemplate_info'", + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_devtestlabartifactsource_info.py b/plugins/modules/azure_rm_devtestlabartifactsource_info.py index bffef5167..e3f5d8da5 100644 --- a/plugins/modules/azure_rm_devtestlabartifactsource_info.py +++ b/plugins/modules/azure_rm_devtestlabartifactsource_info.py @@ -184,7 +184,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_devtestlabartifactsource_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_devtestlabartifactsource_facts' module has been renamed to 'azure_rm_devtestlabartifactsource_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_devtestlabcustomimage_info.py b/plugins/modules/azure_rm_devtestlabcustomimage_info.py index 7f2a06d19..cb81f270a 100644 --- a/plugins/modules/azure_rm_devtestlabcustomimage_info.py +++ b/plugins/modules/azure_rm_devtestlabcustomimage_info.py @@ -161,7 +161,8 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_devtestlabcustomimage_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_devtestlabcustomimage_facts' module has been renamed to 'azure_rm_devtestlabcustomimage_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_devtestlabcustomimage_facts' module has been renamed to 'azure_rm_devtestlabcustomimage_info'", + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_devtestlabenvironment_info.py b/plugins/modules/azure_rm_devtestlabenvironment_info.py index e24b40fe5..60d5cf20b 100644 --- a/plugins/modules/azure_rm_devtestlabenvironment_info.py +++ b/plugins/modules/azure_rm_devtestlabenvironment_info.py @@ -171,7 +171,8 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_devtestlabenvironment_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_devtestlabenvironment_facts' module has been renamed to 'azure_rm_devtestlabenvironment_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_devtestlabenvironment_facts' module has been renamed to 'azure_rm_devtestlabenvironment_info'", + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_devtestlabpolicy_info.py b/plugins/modules/azure_rm_devtestlabpolicy_info.py index 6cfefdafc..2b42d5a83 100644 --- a/plugins/modules/azure_rm_devtestlabpolicy_info.py +++ b/plugins/modules/azure_rm_devtestlabpolicy_info.py @@ -170,7 +170,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_devtestlabpolicy_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_devtestlabpolicy_facts' module has been renamed to 'azure_rm_devtestlabpolicy_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_devtestlabpolicy_facts' module has been renamed to 'azure_rm_devtestlabpolicy_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_devtestlabschedule_info.py b/plugins/modules/azure_rm_devtestlabschedule_info.py index 44e37d1d4..f186efbcb 100644 --- a/plugins/modules/azure_rm_devtestlabschedule_info.py +++ b/plugins/modules/azure_rm_devtestlabschedule_info.py @@ -154,7 +154,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_devtestlabschedule_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_devtestlabschedule_facts' module has been renamed to 'azure_rm_devtestlabschedule_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_devtestlabschedule_facts' module has been renamed to 'azure_rm_devtestlabschedule_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_devtestlabvirtualmachine_info.py b/plugins/modules/azure_rm_devtestlabvirtualmachine_info.py index dc8c05045..fec548d2c 100644 --- a/plugins/modules/azure_rm_devtestlabvirtualmachine_info.py +++ b/plugins/modules/azure_rm_devtestlabvirtualmachine_info.py @@ -250,7 +250,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_devtestlabvirtualmachine_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_devtestlabvirtualmachine_facts' module has been renamed to 'azure_rm_devtestlabvirtualmachine_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_devtestlabvirtualnetwork_info.py b/plugins/modules/azure_rm_devtestlabvirtualnetwork_info.py index 8bf9e08e3..b6d5c0543 100644 --- a/plugins/modules/azure_rm_devtestlabvirtualnetwork_info.py +++ b/plugins/modules/azure_rm_devtestlabvirtualnetwork_info.py @@ -153,7 +153,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_devtestlabvirtualnetwork_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_devtestlabvirtualnetwork_facts' module has been renamed to 'azure_rm_devtestlabvirtualnetwork_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_dnsrecordset_info.py b/plugins/modules/azure_rm_dnsrecordset_info.py index 032d4ea77..92b7311ed 100644 --- a/plugins/modules/azure_rm_dnsrecordset_info.py +++ b/plugins/modules/azure_rm_dnsrecordset_info.py @@ -193,7 +193,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_dnsrecordset_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_dnsrecordset_facts' module has been renamed to 'azure_rm_dnsrecordset_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_dnsrecordset_facts' module has been renamed to 'azure_rm_dnsrecordset_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_dnszone_info.py b/plugins/modules/azure_rm_dnszone_info.py index 94bdd7fed..1ae281c19 100644 --- a/plugins/modules/azure_rm_dnszone_info.py +++ b/plugins/modules/azure_rm_dnszone_info.py @@ -164,7 +164,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_dnszone_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_dnszone_facts' module has been renamed to 'azure_rm_dnszone_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_dnszone_facts' module has been renamed to 'azure_rm_dnszone_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_functionapp_info.py b/plugins/modules/azure_rm_functionapp_info.py index fd11c888e..67114e8b4 100644 --- a/plugins/modules/azure_rm_functionapp_info.py +++ b/plugins/modules/azure_rm_functionapp_info.py @@ -136,7 +136,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_functionapp_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_functionapp_facts' module has been renamed to 'azure_rm_functionapp_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_functionapp_facts' module has been renamed to 'azure_rm_functionapp_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_hdinsightcluster_info.py b/plugins/modules/azure_rm_hdinsightcluster_info.py index d540f29ae..1acb04711 100644 --- a/plugins/modules/azure_rm_hdinsightcluster_info.py +++ b/plugins/modules/azure_rm_hdinsightcluster_info.py @@ -222,7 +222,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_hdinsightcluster_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_hdinsightcluster_facts' module has been renamed to 'azure_rm_hdinsightcluster_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_image_info.py b/plugins/modules/azure_rm_image_info.py index 8cd6dd956..d8d369c37 100644 --- a/plugins/modules/azure_rm_image_info.py +++ b/plugins/modules/azure_rm_image_info.py @@ -208,7 +208,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_image_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_image_facts' module has been renamed to 'azure_rm_image_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_image_facts' module has been renamed to 'azure_rm_image_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_loadbalancer_info.py b/plugins/modules/azure_rm_loadbalancer_info.py index 64275c1db..8eaedec99 100644 --- a/plugins/modules/azure_rm_loadbalancer_info.py +++ b/plugins/modules/azure_rm_loadbalancer_info.py @@ -113,7 +113,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_loadbalancer_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_loadbalancer_facts' module has been renamed to 'azure_rm_loadbalancer_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_loadbalancer_facts' module has been renamed to 'azure_rm_loadbalancer_info'", version=(2.9, )) for key in self.module_args: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_lock_info.py b/plugins/modules/azure_rm_lock_info.py index 2d277201d..945f009a3 100644 --- a/plugins/modules/azure_rm_lock_info.py +++ b/plugins/modules/azure_rm_lock_info.py @@ -156,7 +156,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_lock_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_lock_facts' module has been renamed to 'azure_rm_lock_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_lock_facts' module has been renamed to 'azure_rm_lock_info'", version=(2.9, )) for key in self.module_arg_spec.keys(): setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_loganalyticsworkspace_info.py b/plugins/modules/azure_rm_loganalyticsworkspace_info.py index 28ae7a186..d3e9836f8 100644 --- a/plugins/modules/azure_rm_loganalyticsworkspace_info.py +++ b/plugins/modules/azure_rm_loganalyticsworkspace_info.py @@ -182,7 +182,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_loganalyticsworkspace_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_loganalyticsworkspace_facts' module has been renamed to 'azure_rm_loganalyticsworkspace_info'", - version=(2, 9)) + version=(2.9, )) for key in list(self.module_arg_spec.keys()): setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_mariadbconfiguration_info.py b/plugins/modules/azure_rm_mariadbconfiguration_info.py index 78932a8ae..9a7713d9b 100644 --- a/plugins/modules/azure_rm_mariadbconfiguration_info.py +++ b/plugins/modules/azure_rm_mariadbconfiguration_info.py @@ -138,7 +138,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_mariadbconfiguration_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_mariadbconfiguration_facts' module has been renamed to 'azure_rm_mariadbconfiguration_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_mariadbconfiguration_facts' module has been renamed to 'azure_rm_mariadbconfiguration_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_mariadbdatabase_info.py b/plugins/modules/azure_rm_mariadbdatabase_info.py index 0049f9baa..6bd1ba88d 100644 --- a/plugins/modules/azure_rm_mariadbdatabase_info.py +++ b/plugins/modules/azure_rm_mariadbdatabase_info.py @@ -144,7 +144,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_mariadbdatabase_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_mariadbdatabase_facts' module has been renamed to 'azure_rm_mariadbdatabase_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_mariadbdatabase_facts' module has been renamed to 'azure_rm_mariadbdatabase_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_mariadbfirewallrule_info.py b/plugins/modules/azure_rm_mariadbfirewallrule_info.py index 9d3d4806f..2734e1ec2 100644 --- a/plugins/modules/azure_rm_mariadbfirewallrule_info.py +++ b/plugins/modules/azure_rm_mariadbfirewallrule_info.py @@ -140,7 +140,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_mariadbfirewallrule_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_mariadbfirewallrule_facts' module has been renamed to 'azure_rm_mariadbfirewallrule_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_mariadbfirewallrule_facts' module has been renamed to 'azure_rm_mariadbfirewallrule_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_mariadbserver_info.py b/plugins/modules/azure_rm_mariadbserver_info.py index 1c08e45c3..5599397c1 100644 --- a/plugins/modules/azure_rm_mariadbserver_info.py +++ b/plugins/modules/azure_rm_mariadbserver_info.py @@ -192,7 +192,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_mariadbserver_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_mariadbserver_facts' module has been renamed to 'azure_rm_mariadbserver_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_mariadbserver_facts' module has been renamed to 'azure_rm_mariadbserver_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_mysqlconfiguration_info.py b/plugins/modules/azure_rm_mysqlconfiguration_info.py index 904767cba..13be37e67 100644 --- a/plugins/modules/azure_rm_mysqlconfiguration_info.py +++ b/plugins/modules/azure_rm_mysqlconfiguration_info.py @@ -136,7 +136,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_mysqlconfiguration_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_mysqlconfiguration_facts' module has been renamed to 'azure_rm_mysqlconfiguration_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_mysqlconfiguration_facts' module has been renamed to 'azure_rm_mysqlconfiguration_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_mysqldatabase_info.py b/plugins/modules/azure_rm_mysqldatabase_info.py index 4bb87defc..2e27faeac 100644 --- a/plugins/modules/azure_rm_mysqldatabase_info.py +++ b/plugins/modules/azure_rm_mysqldatabase_info.py @@ -142,7 +142,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_mysqldatabase_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_mysqldatabase_facts' module has been renamed to 'azure_rm_mysqldatabase_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_mysqldatabase_facts' module has been renamed to 'azure_rm_mysqldatabase_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_mysqlfirewallrule_info.py b/plugins/modules/azure_rm_mysqlfirewallrule_info.py index b47dc18d0..2e7a8e987 100644 --- a/plugins/modules/azure_rm_mysqlfirewallrule_info.py +++ b/plugins/modules/azure_rm_mysqlfirewallrule_info.py @@ -138,7 +138,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_mysqlfirewallrule_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_mysqlfirewallrule_facts' module has been renamed to 'azure_rm_mysqlfirewallrule_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_mysqlfirewallrule_facts' module has been renamed to 'azure_rm_mysqlfirewallrule_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_mysqlserver_info.py b/plugins/modules/azure_rm_mysqlserver_info.py index b239bb914..a305860ca 100644 --- a/plugins/modules/azure_rm_mysqlserver_info.py +++ b/plugins/modules/azure_rm_mysqlserver_info.py @@ -190,7 +190,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_mysqlserver_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_mysqlserver_facts' module has been renamed to 'azure_rm_mysqlserver_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_mysqlserver_facts' module has been renamed to 'azure_rm_mysqlserver_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_networkinterface_info.py b/plugins/modules/azure_rm_networkinterface_info.py index 1b6a9c5ae..c2f4cac92 100644 --- a/plugins/modules/azure_rm_networkinterface_info.py +++ b/plugins/modules/azure_rm_networkinterface_info.py @@ -289,7 +289,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_networkinterface_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_networkinterface_facts' module has been renamed to 'azure_rm_networkinterface_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_postgresqlconfiguration_info.py b/plugins/modules/azure_rm_postgresqlconfiguration_info.py index 9c96c851a..e68ad5567 100644 --- a/plugins/modules/azure_rm_postgresqlconfiguration_info.py +++ b/plugins/modules/azure_rm_postgresqlconfiguration_info.py @@ -139,7 +139,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_postgresqlconfiguration_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_postgresqlconfiguration_facts' module has been renamed to 'azure_rm_postgresqlconfiguration_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_postgresqldatabase_info.py b/plugins/modules/azure_rm_postgresqldatabase_info.py index bcb5bc958..bd9f01592 100644 --- a/plugins/modules/azure_rm_postgresqldatabase_info.py +++ b/plugins/modules/azure_rm_postgresqldatabase_info.py @@ -142,7 +142,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_postgresqldatabase_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_postgresqldatabase_facts' module has been renamed to 'azure_rm_postgresqldatabase_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_postgresqldatabase_facts' module has been renamed to 'azure_rm_postgresqldatabase_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_postgresqlfirewallrule_info.py b/plugins/modules/azure_rm_postgresqlfirewallrule_info.py index 65b56e1db..14836902d 100644 --- a/plugins/modules/azure_rm_postgresqlfirewallrule_info.py +++ b/plugins/modules/azure_rm_postgresqlfirewallrule_info.py @@ -138,7 +138,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_postgresqlfirewallrule_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_postgresqlfirewallrule_facts' module has been renamed to 'azure_rm_postgresqlfirewallrule_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_postgresqlserver_info.py b/plugins/modules/azure_rm_postgresqlserver_info.py index 0b92f004a..4750500dd 100644 --- a/plugins/modules/azure_rm_postgresqlserver_info.py +++ b/plugins/modules/azure_rm_postgresqlserver_info.py @@ -192,7 +192,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_postgresqlserver_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_postgresqlserver_facts' module has been renamed to 'azure_rm_postgresqlserver_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_postgresqlserver_facts' module has been renamed to 'azure_rm_postgresqlserver_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_privatednszone.py b/plugins/modules/azure_rm_privatednszone.py new file mode 100644 index 000000000..be729f7f4 --- /dev/null +++ b/plugins/modules/azure_rm_privatednszone.py @@ -0,0 +1,231 @@ +#!/usr/bin/python +# -*- coding: utf-8 -*- +# +# Copyright (c) 2020 Jose Angel Munoz, +# +# +# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) +# + +from __future__ import absolute_import, division, print_function +__metaclass__ = type + +ANSIBLE_METADATA = { + 'metadata_version': '1.1', + 'status': ['preview'], + 'supported_by': 'community' +} + +DOCUMENTATION = ''' +--- +module: azure_rm_privatednszone + +version_added: "2.10" + +short_description: Manage Azure private DNS zones + +description: + - Creates and deletes Azure private DNS zones. + +options: + resource_group: + description: + - Name of resource group. + type: str + required: true + name: + description: + - Name of the private DNS zone. + type: str + required: true + state: + description: + - Assert the state of the zone. Use C(present) to create or update and C(absent) to delete. + default: present + type: str + choices: + - absent + - present + +extends_documentation_fragment: + - azure.azcollection.azure + - azure.azcollection.azure_tags + +author: + - Jose Angel Munoz (@imjoseangel) +''' + +EXAMPLES = ''' + +- name: Create a private DNS zone + azure_rm_privatednszone: + resource_group: myResourceGroup + name: example.com + +- name: Delete a private DNS zone + azure_rm_privatednszone: + resource_group: myResourceGroup + name: example.com + state: absent + +''' + +RETURN = ''' +state: + description: + - Current state of the zone. + returned: always + type: dict + sample: { + "id": "/subscriptions/xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx/resourceGroup/myResourceGroup", + "location": "global", + "name": "Testing", + "number_of_record_sets": 2, + "number_of_virtual_network_links": 0, + "number_of_virtual_network_links_with_registration": 0 + } + +''' + +from ansible_collections.azure.azcollection.plugins.module_utils.azure_rm_common import AzureRMModuleBase, format_resource_id +from ansible.module_utils._text import to_native + +try: + from msrestazure.azure_exceptions import CloudError + from msrest.polling import LROPoller +except ImportError: + # This is handled in azure_rm_common + pass + + +class AzureRMPrivateDNSZone(AzureRMModuleBase): + def __init__(self): + + # define user inputs from playbook + self.module_arg_spec = dict(resource_group=dict(type='str', + required=True), + name=dict(type='str', required=True), + state=dict(choices=['present', 'absent'], + default='present', + type='str')) + + # store the results of the module operation + self.results = dict(changed=False, state=dict()) + + self.resource_group = None + self.name = None + self.state = None + self.tags = None + + super(AzureRMPrivateDNSZone, self).__init__(self.module_arg_spec, + supports_check_mode=True, + supports_tags=True) + + def exec_module(self, **kwargs): + + # create a new zone variable in case the 'try' doesn't find a zone + zone = None + for key in list(self.module_arg_spec.keys()) + ['tags']: + setattr(self, key, kwargs[key]) + + self.results['check_mode'] = self.check_mode + + # retrieve resource group to make sure it exists + self.get_resource_group(self.resource_group) + + changed = False + results = dict() + + try: + self.log('Fetching private DNS zone {0}'.format(self.name)) + zone = self.private_dns_client.private_zones.get( + self.resource_group, self.name) + + # serialize object into a dictionary + results = zone_to_dict(zone) + + # don't change anything if creating an existing zone, but change if deleting it + if self.state == 'present': + changed = False + + update_tags, results['tags'] = self.update_tags( + results['tags']) + if update_tags: + changed = True + elif self.state == 'absent': + changed = True + + except CloudError: + # the zone does not exist so create it + if self.state == 'present': + changed = True + else: + # you can't delete what is not there + changed = False + + self.results['changed'] = changed + self.results['state'] = results + + # return the results if your only gathering information + if self.check_mode: + return self.results + + if changed: + if self.state == 'present': + zone = self.private_dns_models.PrivateZone(tags=self.tags, + location='global') + self.results['state'] = self.create_or_update_zone(zone) + elif self.state == 'absent': + # delete zone + self.delete_zone() + # the delete does not actually return anything. if no exception, then we'll assume + # it worked. + self.results['state']['status'] = 'Deleted' + + return self.results + + def create_or_update_zone(self, zone): + try: + # create or update the new Zone object we created + new_zone = self.private_dns_client.private_zones.create_or_update( + self.resource_group, self.name, zone) + + if isinstance(new_zone, LROPoller): + new_zone = self.get_poller_result(new_zone) + + except Exception as exc: + self.fail("Error creating or updating zone {0} - {1}".format( + self.name, exc.message or str(exc))) + return zone_to_dict(new_zone) + + def delete_zone(self): + try: + # delete the Zone + poller = self.private_dns_client.private_zones.delete( + self.resource_group, self.name) + result = self.get_poller_result(poller) + except Exception as exc: + self.fail("Error deleting zone {0} - {1}".format( + self.name, exc.message or str(exc))) + return result + + +def zone_to_dict(zone): + # turn Zone object into a dictionary (serialization) + result = dict( + id=zone.id, + name=zone.name, + number_of_record_sets=zone.number_of_record_sets, + number_of_virtual_network_links=zone.number_of_virtual_network_links, + number_of_virtual_network_links_with_registration=zone. + number_of_virtual_network_links_with_registration, + tags=zone.tags) + return result + + +def main(): + AzureRMPrivateDNSZone() + + +if __name__ == '__main__': + main() diff --git a/plugins/modules/azure_rm_privatednszone_info.py b/plugins/modules/azure_rm_privatednszone_info.py new file mode 100644 index 000000000..a95c66450 --- /dev/null +++ b/plugins/modules/azure_rm_privatednszone_info.py @@ -0,0 +1,251 @@ +#!/usr/bin/python +# -*- coding: utf-8 -*- +# +# Copyright (c) 2020 Jose Angel Munoz, +# +# +# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) +# + +from __future__ import absolute_import, division, print_function +__metaclass__ = type + +ANSIBLE_METADATA = { + 'metadata_version': '1.1', + 'status': ['preview'], + 'supported_by': 'community' +} + +DOCUMENTATION = ''' +--- +module: azure_rm_privatednszone_info + +version_added: "2.10" + +short_description: Get private DNS zone facts + +description: + - Get facts for a specific private DNS zone or all private DNS zones within a resource group. + +options: + resource_group: + description: + - Limit results by resource group. Required when filtering by name. + type: str + name: + description: + - Only show results for a specific zone. + type: str + tags: + description: + - Limit results by providing a list of tags. Format tags as 'key' or 'key:value'. + type: list + +extends_documentation_fragment: + - azure.azcollection.azure + - azure.azcollection.azure_tags + +author: + - Jose Angel Munoz (@imjoseangel) + +''' + +EXAMPLES = ''' +- name: Get facts for one zone + azure_rm_privatednszone_info: + resource_group: myResourceGroup + name: foobar22 + +- name: Get facts for all zones in a resource group + azure_rm_privatednszone_info: + resource_group: myResourceGroup + +- name: Get facts for privatednszone with tags + azure_rm_privatednszone_info: + tags: + - testing + - foo:bar +''' + +RETURN = ''' +azure_privatednszones: + description: + - List of private zone dicts. + returned: always + type: list + example: [{ + "etag": "00000002-0000-0000-0dcb-df5776efd201", + "location": "global", + "properties": { + "maxNumberOfRecordSets": 5000, + "number_of_virtual_network_links": 0, + "number_of_virtual_network_links_with_registration": 0 + }, + "tags": {} + }] +privatednszones: + description: + - List of private zone dicts, which share the same layout as azure_rm_privatednszone module parameter. + returned: always + type: list + contains: + id: + description: + - id of the private DNS Zone. + sample: "/subscriptions/xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx/resourceGroups/myResourceGroup/providers/Microsoft.Network/privatednszones/azure.com" + type: str + name: + description: + - name of the private DNS zone. + sample: azure.com + type: str + number_of_record_sets: + description: + - The current number of record sets in this private DNS zone. + type: int + sample: 2 + number_of_virtual_network_links: + description: + - The current number of network links in this private DNS zone. + type: int + sample: 0 + number_of_virtual_network_links_with_registration: + description: + - The current number of network links with registration in this private DNS zone. + type: int + sample: 0 +''' + +from ansible_collections.azure.azcollection.plugins.module_utils.azure_rm_common import AzureRMModuleBase +from ansible.module_utils._text import to_native + +try: + from msrestazure.azure_exceptions import CloudError + from azure.common import AzureMissingResourceHttpError, AzureHttpError +except Exception: + # This is handled in azure_rm_common + pass + +AZURE_OBJECT_CLASS = 'PrivateDnsZone' + + +class AzurePrivateRMDNSZoneInfo(AzureRMModuleBase): + def __init__(self): + + # define user inputs into argument + self.module_arg_spec = dict(name=dict(type='str'), + resource_group=dict(type='str'), + tags=dict(type='list')) + + # store the results of the module operation + self.results = dict(changed=False, + ansible_info=dict(azure_privatednszones=[])) + + self.name = None + self.resource_group = None + self.tags = None + + super(AzurePrivateRMDNSZoneInfo, self).__init__(self.module_arg_spec) + + def exec_module(self, **kwargs): + + is_old_facts = self.module._name == 'azure_rm_privatednszone_facts' + if is_old_facts: + self.module.deprecate( + "The 'azure_rm_privatednszone_facts' module has been renamed to 'azure_rm_privatednszone_info'", + version=(2.9, )) + + for key in self.module_arg_spec: + setattr(self, key, kwargs[key]) + + if self.name and not self.resource_group: + self.fail( + "Parameter error: resource group required when filtering by name." + ) + + results = [] + # list the conditions and what to return based on user input + if self.name is not None: + # if there is a name, facts about that specific zone + results = self.get_item() + elif self.resource_group: + # all the zones listed in that specific resource group + results = self.list_resource_group() + else: + # all the zones in a subscription + results = self.list_items() + + self.results['ansible_info'][ + 'azure_privatednszones'] = self.serialize_items(results) + self.results['privatednszones'] = self.curated_items(results) + + return self.results + + def get_item(self): + self.log('Get properties for {0}'.format(self.name)) + item = None + results = [] + # get specific zone + try: + item = self.private_dns_client.private_zones.get( + self.resource_group, self.name) + except CloudError: + pass + + # serialize result + if item and self.has_tags(item.tags, self.tags): + results = [item] + return results + + def list_resource_group(self): + self.log('List items for resource group') + try: + response = self.private_dns_client.private_zones.list_by_resource_group( + self.resource_group) + except AzureHttpError as exc: + self.fail("Failed to list for resource group {0} - {1}".format( + self.resource_group, str(exc))) + + results = [] + for item in response: + if self.has_tags(item.tags, self.tags): + results.append(item) + return results + + def list_items(self): + self.log('List all items') + try: + response = self.private_dns_client.private_zones.list() + except AzureHttpError as exc: + self.fail("Failed to list all items - {0}".format(str(exc))) + + results = [] + for item in response: + if self.has_tags(item.tags, self.tags): + results.append(item) + return results + + def serialize_items(self, raws): + return [self.serialize_obj(item, AZURE_OBJECT_CLASS) + for item in raws] if raws else [] + + def curated_items(self, raws): + return [self.zone_to_dict(item) for item in raws] if raws else [] + + def zone_to_dict(self, zone): + return dict(id=zone.id, + name=zone.name, + number_of_record_sets=zone.number_of_record_sets, + number_of_virtual_network_links=zone. + number_of_virtual_network_links, + number_of_virtual_network_links_with_registration=zone. + number_of_virtual_network_links_with_registration, + tags=zone.tags) + + +def main(): + AzurePrivateRMDNSZoneInfo() + + +if __name__ == '__main__': + main() diff --git a/plugins/modules/azure_rm_publicipaddress_info.py b/plugins/modules/azure_rm_publicipaddress_info.py index bb45aa518..f8ba376c7 100644 --- a/plugins/modules/azure_rm_publicipaddress_info.py +++ b/plugins/modules/azure_rm_publicipaddress_info.py @@ -220,7 +220,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_publicipaddress_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_publicipaddress_facts' module has been renamed to 'azure_rm_publicipaddress_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_publicipaddress_facts' module has been renamed to 'azure_rm_publicipaddress_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_rediscache_info.py b/plugins/modules/azure_rm_rediscache_info.py index 67c64622b..179d32198 100644 --- a/plugins/modules/azure_rm_rediscache_info.py +++ b/plugins/modules/azure_rm_rediscache_info.py @@ -240,7 +240,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_rediscache_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_rediscache_facts' module has been renamed to 'azure_rm_rediscache_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_rediscache_facts' module has been renamed to 'azure_rm_rediscache_info'", version=(2.9, )) for key in self.module_args: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_resource_info.py b/plugins/modules/azure_rm_resource_info.py index 57f83b136..69277b482 100644 --- a/plugins/modules/azure_rm_resource_info.py +++ b/plugins/modules/azure_rm_resource_info.py @@ -336,7 +336,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_resource_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_resource_facts' module has been renamed to 'azure_rm_resource_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_resource_facts' module has been renamed to 'azure_rm_resource_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_resourcegroup_info.py b/plugins/modules/azure_rm_resourcegroup_info.py index 81d61e585..8ec03ffa2 100644 --- a/plugins/modules/azure_rm_resourcegroup_info.py +++ b/plugins/modules/azure_rm_resourcegroup_info.py @@ -168,7 +168,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_resourcegroup_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_resourcegroup_facts' module has been renamed to 'azure_rm_resourcegroup_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_resourcegroup_facts' module has been renamed to 'azure_rm_resourcegroup_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_roleassignment_info.py b/plugins/modules/azure_rm_roleassignment_info.py index 4bbd6cb5a..516761f5b 100644 --- a/plugins/modules/azure_rm_roleassignment_info.py +++ b/plugins/modules/azure_rm_roleassignment_info.py @@ -166,7 +166,7 @@ def exec_module(self, **kwargs): """Main module execution method""" is_old_facts = self.module._name == 'azure_rm_roleassignment_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_roleassignment_facts' module has been renamed to 'azure_rm_roleassignment_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_roleassignment_facts' module has been renamed to 'azure_rm_roleassignment_info'", version=(2.9, )) for key in list(self.module_arg_spec.keys()): if hasattr(self, key): diff --git a/plugins/modules/azure_rm_roledefinition_info.py b/plugins/modules/azure_rm_roledefinition_info.py index e72f13178..e404f5d69 100644 --- a/plugins/modules/azure_rm_roledefinition_info.py +++ b/plugins/modules/azure_rm_roledefinition_info.py @@ -184,7 +184,7 @@ def exec_module(self, **kwargs): """Main module execution method""" is_old_facts = self.module._name == 'azure_rm_roledefinition_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_roledefinition_facts' module has been renamed to 'azure_rm_roledefinition_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_roledefinition_facts' module has been renamed to 'azure_rm_roledefinition_info'", version=(2.9, )) for key in list(self.module_arg_spec.keys()): if hasattr(self, key): diff --git a/plugins/modules/azure_rm_routetable_info.py b/plugins/modules/azure_rm_routetable_info.py index 6fa3ee60c..eb1d08730 100644 --- a/plugins/modules/azure_rm_routetable_info.py +++ b/plugins/modules/azure_rm_routetable_info.py @@ -169,7 +169,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_routetable_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_routetable_facts' module has been renamed to 'azure_rm_routetable_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_routetable_facts' module has been renamed to 'azure_rm_routetable_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_securitygroup_info.py b/plugins/modules/azure_rm_securitygroup_info.py index 45334b143..ef211fd72 100644 --- a/plugins/modules/azure_rm_securitygroup_info.py +++ b/plugins/modules/azure_rm_securitygroup_info.py @@ -261,7 +261,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_securitygroup_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_securitygroup_facts' module has been renamed to 'azure_rm_securitygroup_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_securitygroup_facts' module has been renamed to 'azure_rm_securitygroup_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_servicebus_info.py b/plugins/modules/azure_rm_servicebus_info.py index 8e2b30216..c43b6391a 100644 --- a/plugins/modules/azure_rm_servicebus_info.py +++ b/plugins/modules/azure_rm_servicebus_info.py @@ -443,7 +443,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_servicebus_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_servicebus_facts' module has been renamed to 'azure_rm_servicebus_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_servicebus_facts' module has been renamed to 'azure_rm_servicebus_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_sqldatabase_info.py b/plugins/modules/azure_rm_sqldatabase_info.py index 862764eb5..9b07295d2 100644 --- a/plugins/modules/azure_rm_sqldatabase_info.py +++ b/plugins/modules/azure_rm_sqldatabase_info.py @@ -195,7 +195,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_sqldatabase_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_sqldatabase_facts' module has been renamed to 'azure_rm_sqldatabase_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_sqldatabase_facts' module has been renamed to 'azure_rm_sqldatabase_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_sqlfirewallrule_info.py b/plugins/modules/azure_rm_sqlfirewallrule_info.py index 469a3cf6d..4e4080abe 100644 --- a/plugins/modules/azure_rm_sqlfirewallrule_info.py +++ b/plugins/modules/azure_rm_sqlfirewallrule_info.py @@ -141,7 +141,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_sqlfirewallrule_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_sqlfirewallrule_facts' module has been renamed to 'azure_rm_sqlfirewallrule_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_sqlfirewallrule_facts' module has been renamed to 'azure_rm_sqlfirewallrule_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_sqlserver_info.py b/plugins/modules/azure_rm_sqlserver_info.py index 1874ffaf8..56a2e18ab 100644 --- a/plugins/modules/azure_rm_sqlserver_info.py +++ b/plugins/modules/azure_rm_sqlserver_info.py @@ -146,7 +146,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_sqlserver_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_sqlserver_facts' module has been renamed to 'azure_rm_sqlserver_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_sqlserver_facts' module has been renamed to 'azure_rm_sqlserver_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_storageaccount_info.py b/plugins/modules/azure_rm_storageaccount_info.py index b1a1e5c53..907a3b003 100644 --- a/plugins/modules/azure_rm_storageaccount_info.py +++ b/plugins/modules/azure_rm_storageaccount_info.py @@ -233,7 +233,7 @@ sample: eastus primary_endpoints: description: - - URLs to retrieve a public I(blob), I(queue), or I(table) object. + - URLs to retrieve a public I(blob), I(file), I(queue), or I(table) object. - Note that C(Standard_ZRS) and C(Premium_LRS) accounts only return the blob endpoint. returned: always type: complex @@ -256,6 +256,24 @@ returned: always type: str sample: "DefaultEndpointsProtocol=https;EndpointSuffix=core.windows.net;AccountName=X;AccountKey=X;BlobEndpoint=X" + file: + description: + - The primary file endpoint and connection string. + returned: always + type: complex + contains: + endpoint: + description: + - The primary file endpoint. + returned: always + type: str + sample: "https://testaccount001.file.core.windows.net/" + connectionstring: + description: + - Connectionstring of the file endpoint. + returned: always + type: str + sample: "DefaultEndpointsProtocol=https;EndpointSuffix=core.windows.net;AccountName=X;AccountKey=X;FileEndpoint=X" queue: description: - The primary queue endpoint and connection string. @@ -300,7 +318,7 @@ sample: xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx secondary_endpoints: description: - - The URLs to retrieve a public I(blob), I(queue), or I(table) object from the secondary location. + - The URLs to retrieve a public I(blob), I(file), I(queue), or I(table) object from the secondary location. - Only available if the SKU I(name=Standard_RAGRS). returned: always type: complex @@ -323,6 +341,24 @@ returned: always type: str sample: "DefaultEndpointsProtocol=https;EndpointSuffix=core.windows.net;AccountName=X;AccountKey=X;BlobEndpoint=X" + file: + description: + - The secondary file endpoint and connection string. + returned: always + type: complex + contains: + endpoint: + description: + - The secondary file endpoint. + returned: always + type: str + sample: "https://testaccount001.file.core.windows.net/" + connectionstring: + description: + - Connectionstring of the file endpoint. + returned: always + type: str + sample: "DefaultEndpointsProtocol=https;EndpointSuffix=core.windows.net;AccountName=X;AccountKey=X;FileEndpoint=X" queue: description: - The secondary queue endpoint and connection string. @@ -413,7 +449,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_storageaccount_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_storageaccount_facts' module has been renamed to 'azure_rm_storageaccount_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_storageaccount_facts' module has been renamed to 'azure_rm_storageaccount_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) @@ -526,6 +562,7 @@ def account_obj_to_dict(self, account_obj, blob_service_props=None): if account_obj.primary_endpoints: account_dict['primary_endpoints'] = dict( blob=self.format_endpoint_dict(account_dict['name'], account_key[0], account_obj.primary_endpoints.blob, 'blob'), + file=self.format_endpoint_dict(account_dict['name'], account_key[0], account_obj.primary_endpoints.file, 'file'), queue=self.format_endpoint_dict(account_dict['name'], account_key[0], account_obj.primary_endpoints.queue, 'queue'), table=self.format_endpoint_dict(account_dict['name'], account_key[0], account_obj.primary_endpoints.table, 'table') ) @@ -535,6 +572,7 @@ def account_obj_to_dict(self, account_obj, blob_service_props=None): if account_obj.secondary_endpoints: account_dict['secondary_endpoints'] = dict( blob=self.format_endpoint_dict(account_dict['name'], account_key[1], account_obj.primary_endpoints.blob, 'blob'), + file=self.format_endpoint_dict(account_dict['name'], account_key[1], account_obj.primary_endpoints.file, 'file'), queue=self.format_endpoint_dict(account_dict['name'], account_key[1], account_obj.primary_endpoints.queue, 'queue'), table=self.format_endpoint_dict(account_dict['name'], account_key[1], account_obj.primary_endpoints.table, 'table'), ) diff --git a/plugins/modules/azure_rm_subnet.py b/plugins/modules/azure_rm_subnet.py index 2ed2215b9..4ee9812f0 100644 --- a/plugins/modules/azure_rm_subnet.py +++ b/plugins/modules/azure_rm_subnet.py @@ -285,7 +285,7 @@ def exec_module(self, **kwargs): results['route_table']['id'] = self.route_table self.log("CHANGED: subnet {0} route_table to {1}".format(self.name, route_table.get('name'))) - if self.service_endpoints: + if self.service_endpoints or self.service_endpoints == []: oldd = {} for item in self.service_endpoints: name = item['service'] diff --git a/plugins/modules/azure_rm_subnet_info.py b/plugins/modules/azure_rm_subnet_info.py index 2d5193381..4c1f0c05c 100644 --- a/plugins/modules/azure_rm_subnet_info.py +++ b/plugins/modules/azure_rm_subnet_info.py @@ -178,7 +178,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_subnet_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_subnet_facts' module has been renamed to 'azure_rm_subnet_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_subnet_facts' module has been renamed to 'azure_rm_subnet_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_trafficmanagerendpoint_info.py b/plugins/modules/azure_rm_trafficmanagerendpoint_info.py index 51e3590e1..0b52978b1 100644 --- a/plugins/modules/azure_rm_trafficmanagerendpoint_info.py +++ b/plugins/modules/azure_rm_trafficmanagerendpoint_info.py @@ -227,7 +227,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_trafficmanagerendpoint_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_trafficmanagerendpoint_facts' module has been renamed to 'azure_rm_trafficmanagerendpoint_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_args: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_trafficmanagerprofile_info.py b/plugins/modules/azure_rm_trafficmanagerprofile_info.py index 5114a867f..ba199f70b 100644 --- a/plugins/modules/azure_rm_trafficmanagerprofile_info.py +++ b/plugins/modules/azure_rm_trafficmanagerprofile_info.py @@ -309,7 +309,8 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_trafficmanagerprofile_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_trafficmanagerprofile_facts' module has been renamed to 'azure_rm_trafficmanagerprofile_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_trafficmanagerprofile_facts' module has been renamed to 'azure_rm_trafficmanagerprofile_info'", + version=(2.9, )) for key in self.module_args: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_virtualmachine.py b/plugins/modules/azure_rm_virtualmachine.py index 8ed0b8190..f0e3996f9 100644 --- a/plugins/modules/azure_rm_virtualmachine.py +++ b/plugins/modules/azure_rm_virtualmachine.py @@ -175,6 +175,12 @@ - Windows - Linux default: Linux + ephemeral_os_disk: + description: + - Parameters of ephemeral disk settings that can be specified for operating system disk. + - Ephemeral OS disk is only supported for VMS Instances using Managed Disk. + type: bool + default: False data_disks: description: - Describes list of data disks. @@ -847,6 +853,7 @@ def __init__(self): vm_identity=dict(type='str', choices=['SystemAssigned']), winrm=dict(type='list'), boot_diagnostics=dict(type='dict'), + ephemeral_os_disk=dict(type='bool'), ) self.resource_group = None @@ -891,6 +898,7 @@ def __init__(self): self.license_type = None self.vm_identity = None self.boot_diagnostics = None + self.ephemeral_os_disk = None self.results = dict( changed=False, @@ -1054,6 +1062,13 @@ def exec_module(self, **kwargs): differences = [] current_nics = [] results = vm_dict + current_osdisk = vm_dict['properties']['storageProfile']['osDisk'] + current_ephemeral = current_osdisk.get('diffDiskSettings', None) + + if self.ephemeral_os_disk and current_ephemeral is None: + self.fail('Ephemeral OS disk not updatable: virtual machine ephemeral OS disk is {0}'.format(self.ephemeral_os_disk)) + elif not self.ephemeral_os_disk and current_ephemeral is not None: + self.fail('Ephemeral OS disk not updatable: virtual machine ephemeral OS disk is {0}'.format(self.ephemeral_os_disk)) # Try to determine if the VM needs to be updated if self.network_interface_names: @@ -1294,7 +1309,8 @@ def exec_module(self, **kwargs): managed_disk=managed_disk, create_option=self.compute_models.DiskCreateOptionTypes.from_image, caching=self.os_disk_caching, - disk_size_gb=self.os_disk_size_gb + disk_size_gb=self.os_disk_size_gb, + diff_disk_settings=self.compute_models.DiffDiskSettings(option='Local') if self.ephemeral_os_disk else None ), image_reference=image_reference, ), @@ -1577,7 +1593,7 @@ def exec_module(self, **kwargs): vhd=data_disk_vhd, caching=data_disk.get('caching'), create_option=data_disk.get('createOption'), - disk_size_gb=int(data_disk['diskSizeGB']), + disk_size_gb=int(data_disk.get('diskSizeGB', 0)) or None, managed_disk=data_disk_managed_disk, )) vm_resource.storage_profile.data_disks = data_disks diff --git a/plugins/modules/azure_rm_virtualmachine_info.py b/plugins/modules/azure_rm_virtualmachine_info.py index 3a99c5cd0..829cc3960 100644 --- a/plugins/modules/azure_rm_virtualmachine_info.py +++ b/plugins/modules/azure_rm_virtualmachine_info.py @@ -290,7 +290,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_virtualmachine_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_virtualmachine_facts' module has been renamed to 'azure_rm_virtualmachine_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_virtualmachine_facts' module has been renamed to 'azure_rm_virtualmachine_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_virtualmachineextension_info.py b/plugins/modules/azure_rm_virtualmachineextension_info.py index 49e7ff6f6..f07b8441d 100644 --- a/plugins/modules/azure_rm_virtualmachineextension_info.py +++ b/plugins/modules/azure_rm_virtualmachineextension_info.py @@ -177,7 +177,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_virtualmachineextension_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_virtualmachineextension_facts' module has been renamed to 'azure_rm_virtualmachineextension_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_virtualmachineimage_info.py b/plugins/modules/azure_rm_virtualmachineimage_info.py index 14c6ae660..d20823b9a 100644 --- a/plugins/modules/azure_rm_virtualmachineimage_info.py +++ b/plugins/modules/azure_rm_virtualmachineimage_info.py @@ -152,7 +152,7 @@ def __init__(self, **kwargs): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_virtualmachineimage_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_virtualmachineimage_facts' module has been renamed to 'azure_rm_virtualmachineimage_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_virtualmachineimage_facts' module has been renamed to 'azure_rm_virtualmachineimage_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_virtualmachinescaleset.py b/plugins/modules/azure_rm_virtualmachinescaleset.py index e59832dca..2ed149e74 100644 --- a/plugins/modules/azure_rm_virtualmachinescaleset.py +++ b/plugins/modules/azure_rm_virtualmachinescaleset.py @@ -116,6 +116,12 @@ - Windows - Linux default: Linux + ephemeral_os_disk: + description: + - Parameters of ephemeral disk settings that can be specified for operating system disk. + - Ephemeral OS disk is only supported for VMS Instances using Managed Disk. + type: bool + default: False managed_disk_type: description: - Managed disk type. @@ -540,7 +546,8 @@ def __init__(self): product=dict(type='str', required=True), name=dict(type='str', required=True), promotion_code=dict(type='str'))), scale_in_policy=dict(type='str', choices=['Default', 'OldestVM', 'NewestVM']), - terminate_event_timeout_minutes=dict(type='int') + terminate_event_timeout_minutes=dict(type='int'), + ephemeral_os_disk=dict(type='bool') ) self.resource_group = None @@ -578,6 +585,7 @@ def __init__(self): self.plan = None self.scale_in_policy = None self.terminate_event_timeout_minutes = None + self.ephemeral_os_disk = None mutually_exclusive = [('load_balancer', 'application_gateway')] self.results = dict( @@ -711,6 +719,13 @@ def exec_module(self, **kwargs): if self.state == 'present': differences = [] results = vmss_dict + current_osdisk = vmss_dict['properties']['virtualMachineProfile']['storageProfile']['osDisk'] + current_ephemeral = current_osdisk.get('diffDiskSettings', None) + + if self.ephemeral_os_disk and current_ephemeral is None: + self.fail('Ephemeral OS disk not updatable: virtual machine scale set ephemeral OS disk is {0}'.format(self.ephemeral_os_disk)) + elif not self.ephemeral_os_disk and current_ephemeral is not None: + self.fail('Ephemeral OS disk not updatable: virtual machine scale set ephemeral OS disk is {0}'.format(self.ephemeral_os_disk)) if self.os_disk_caching and \ self.os_disk_caching != vmss_dict['properties']['virtualMachineProfile']['storageProfile']['osDisk']['caching']: @@ -899,6 +914,7 @@ def exec_module(self, **kwargs): managed_disk=managed_disk, create_option=self.compute_models.DiskCreateOptionTypes.from_image, caching=self.os_disk_caching, + diff_disk_settings=self.compute_models.DiffDiskSettings(option='Local') if self.ephemeral_os_disk else None, ), image_reference=image_reference, ), diff --git a/plugins/modules/azure_rm_virtualmachinescaleset_info.py b/plugins/modules/azure_rm_virtualmachinescaleset_info.py index f430a69d8..b5d24a93d 100644 --- a/plugins/modules/azure_rm_virtualmachinescaleset_info.py +++ b/plugins/modules/azure_rm_virtualmachinescaleset_info.py @@ -297,7 +297,7 @@ def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_virtualmachinescaleset_facts' if is_old_facts: self.module.deprecate("The 'azure_rm_virtualmachinescaleset_facts' module has been renamed to 'azure_rm_virtualmachinescaleset_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_args: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_virtualmachinescalesetextension_info.py b/plugins/modules/azure_rm_virtualmachinescalesetextension_info.py index e76d99d81..bf0142faf 100644 --- a/plugins/modules/azure_rm_virtualmachinescalesetextension_info.py +++ b/plugins/modules/azure_rm_virtualmachinescalesetextension_info.py @@ -159,7 +159,7 @@ def exec_module(self, **kwargs): if is_old_facts: self.module.deprecate("The 'azure_rm_virtualmachinescalesetextension_facts' module has been renamed to" + " 'azure_rm_virtualmachinescalesetextension_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_virtualmachinescalesetinstance_info.py b/plugins/modules/azure_rm_virtualmachinescalesetinstance_info.py index e8c968ec3..47dd817b6 100644 --- a/plugins/modules/azure_rm_virtualmachinescalesetinstance_info.py +++ b/plugins/modules/azure_rm_virtualmachinescalesetinstance_info.py @@ -163,7 +163,7 @@ def exec_module(self, **kwargs): if is_old_facts: self.module.deprecate("The 'azure_rm_virtualmachinescalesetinstance_facts' module has been renamed to" + " 'azure_rm_virtualmachinescalesetinstance_info'", - version=(2, 9)) + version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_virtualnetwork_info.py b/plugins/modules/azure_rm_virtualnetwork_info.py index 9cbe6aa3d..87d491397 100644 --- a/plugins/modules/azure_rm_virtualnetwork_info.py +++ b/plugins/modules/azure_rm_virtualnetwork_info.py @@ -228,7 +228,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_virtualnetwork_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_virtualnetwork_facts' module has been renamed to 'azure_rm_virtualnetwork_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_virtualnetwork_facts' module has been renamed to 'azure_rm_virtualnetwork_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_virtualnetworkpeering_info.py b/plugins/modules/azure_rm_virtualnetworkpeering_info.py index 540cd203a..b9f252ec4 100644 --- a/plugins/modules/azure_rm_virtualnetworkpeering_info.py +++ b/plugins/modules/azure_rm_virtualnetworkpeering_info.py @@ -188,7 +188,8 @@ def exec_module(self, **kwargs): """Main module execution method""" is_old_facts = self.module._name == 'azure_rm_virtualnetworkpeering_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_virtualnetworkpeering_facts' module has been renamed to 'azure_rm_virtualnetworkpeering_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_virtualnetworkpeering_facts' module has been renamed to 'azure_rm_virtualnetworkpeering_info'", + version=(2.9, )) for key in list(self.module_arg_spec.keys()): setattr(self, key, kwargs[key]) diff --git a/plugins/modules/azure_rm_webapp_info.py b/plugins/modules/azure_rm_webapp_info.py index e3e0de7ac..5f132a4ef 100644 --- a/plugins/modules/azure_rm_webapp_info.py +++ b/plugins/modules/azure_rm_webapp_info.py @@ -265,7 +265,7 @@ def __init__(self): def exec_module(self, **kwargs): is_old_facts = self.module._name == 'azure_rm_webapp_facts' if is_old_facts: - self.module.deprecate("The 'azure_rm_webapp_facts' module has been renamed to 'azure_rm_webapp_info'", version=(2, 9)) + self.module.deprecate("The 'azure_rm_webapp_facts' module has been renamed to 'azure_rm_webapp_info'", version=(2.9, )) for key in self.module_arg_spec: setattr(self, key, kwargs[key]) diff --git a/pr-pipelines.yml b/pr-pipelines.yml index 8aa5f1596..744123069 100644 --- a/pr-pipelines.yml +++ b/pr-pipelines.yml @@ -50,6 +50,7 @@ parameters: - "azure_rm_mysqlserver" - "azure_rm_networkinterface" - "azure_rm_postgresqlserver" + - "azure_rm_privatednszone" - "azure_rm_publicipaddress" - "azure_rm_rediscache" - "azure_rm_resource" diff --git a/requirements-azure.txt b/requirements-azure.txt index 88f4ce389..c80f02f8d 100644 --- a/requirements-azure.txt +++ b/requirements-azure.txt @@ -15,8 +15,9 @@ azure-mgmt-dns==2.1.0 azure-mgmt-keyvault==1.1.0 azure-mgmt-marketplaceordering==0.1.0 azure-mgmt-monitor==0.5.2 -azure-mgmt-network==4.0.0 +azure-mgmt-network==10.2.0 azure-mgmt-nspkg==2.0.0 +azure-mgmt-privatedns==0.1.0 azure-mgmt-redis==5.0.0 azure-mgmt-resource==2.1.0 azure-mgmt-rdbms==1.4.1 @@ -30,7 +31,7 @@ azure-storage==0.35.1 msrest==0.6.10 msrestazure==0.6.2 azure-keyvault==1.0.0a1 -azure-graphrbac==0.40.0 +azure-graphrbac==0.61.1 azure-mgmt-cosmosdb==0.5.2 azure-mgmt-hdinsight==0.1.0 azure-mgmt-devtestlabs==3.0.0 diff --git a/tests/integration/targets/azure_rm_adpassword/aliases b/tests/integration/targets/azure_rm_adpassword/aliases new file mode 100644 index 000000000..fc8bf1e71 --- /dev/null +++ b/tests/integration/targets/azure_rm_adpassword/aliases @@ -0,0 +1,4 @@ +cloud/azure +shippable/azure/group10 +disabled +destructive diff --git a/tests/integration/targets/azure_rm_adpassword/meta/main.yml b/tests/integration/targets/azure_rm_adpassword/meta/main.yml new file mode 100644 index 000000000..95e1952f9 --- /dev/null +++ b/tests/integration/targets/azure_rm_adpassword/meta/main.yml @@ -0,0 +1,2 @@ +dependencies: + - setup_azure diff --git a/tests/integration/targets/azure_rm_adpassword/tasks/main.yml b/tests/integration/targets/azure_rm_adpassword/tasks/main.yml new file mode 100644 index 000000000..7c3782f17 --- /dev/null +++ b/tests/integration/targets/azure_rm_adpassword/tasks/main.yml @@ -0,0 +1,103 @@ +- set_fact: + app_id: "e0a62513-1d81-480e-a6dc-5c99cdd58d9a" + tenant_id: "72f988bf-86f1-41af-91ab-2d7cd011db47" + app_object_id: "b52e8275-a1ee-4c4a-86ff-15992e0920ed" + +- name: create first ad password by app_id + azure_rm_adpassword: + app_id: "{{ app_id }}" + value: "Password@032900001" + tenant: "{{ tenant_id }}" + state: present + register: ad_fact + +- assert: + that: + - ad_fact.changed + +- name: create second ad password by app_object_id + azure_rm_adpassword: + value: "Password@032900002" + tenant: "{{ tenant_id }}" + app_object_id: "{{ app_object_id }}" + state: present + register: ad_fact02 + +- assert: + that: + - ad_fact02.changed + +- name: create ad service principal + azure_rm_adserviceprincipal: + app_id: "{{ app_id }}" + tenant: "{{ tenant_id }}" + state: present + +- name: Get ad service principal info + azure_rm_adserviceprincipal_info: + tenant: "{{ tenant_id }}" + app_id: "{{ app_id }}" + register: sp_info +- debug: + var: sp_info + +- name: create third ad password by service_principal_object_id + azure_rm_adpassword: + value: "Password@032900003" + tenant: "{{ tenant_id }}" + service_principal_object_id: "{{ sp_info.service_principals[0].object_id }}" + state: present + register: ad_fact03 + +- assert: + that: + - ad_fact03.changed + +- name: can't update ad password + azure_rm_adpassword: + app_id: "{{ app_id }}" + value: "Password@032900003" + tenant: "{{ tenant_id }}" + key_id: "{{ ad_fact.key_id }}" + app_object_id: "{{ app_object_id }}" + state: present + register: output + ignore_errors: True + +- name: Get ad password info + azure_rm_adpassword_info: + app_id: "{{ app_id }}" + tenant: "{{ tenant_id }}" + key_id: "{{ ad_fact.key_id }}" + app_object_id: "{{ app_object_id }}" + register: ad_info + +- assert: + that: + - ad_info.passwords[0].start_date == ad_fact.start_date + - ad_info.passwords[0].end_date == ad_fact.end_date + +- name: delete one ad password + azure_rm_adpassword: + app_id: "{{ app_id }}" + key_id: "{{ ad_fact.key_id }}" + tenant: "{{ tenant_id }}" + app_object_id: "{{ app_object_id }}" + state: absent + register: output + +- assert: + that: + - output.changed + +- name: delete all ad password + azure_rm_adpassword: + app_id: "{{ app_id }}" + tenant: "{{ tenant_id }}" + app_object_id: "{{ app_object_id }}" + state: absent + register: output + +- assert: + that: + - output.changed diff --git a/tests/integration/targets/azure_rm_adserviceprincipal/aliases b/tests/integration/targets/azure_rm_adserviceprincipal/aliases new file mode 100644 index 000000000..6feba04aa --- /dev/null +++ b/tests/integration/targets/azure_rm_adserviceprincipal/aliases @@ -0,0 +1,4 @@ +cloud/azure +shippable/azure/group10 +destructive +disabled diff --git a/tests/integration/targets/azure_rm_adserviceprincipal/meta/main.yml b/tests/integration/targets/azure_rm_adserviceprincipal/meta/main.yml new file mode 100644 index 000000000..95e1952f9 --- /dev/null +++ b/tests/integration/targets/azure_rm_adserviceprincipal/meta/main.yml @@ -0,0 +1,2 @@ +dependencies: + - setup_azure diff --git a/tests/integration/targets/azure_rm_adserviceprincipal/tasks/main.yml b/tests/integration/targets/azure_rm_adserviceprincipal/tasks/main.yml new file mode 100644 index 000000000..4e4b50161 --- /dev/null +++ b/tests/integration/targets/azure_rm_adserviceprincipal/tasks/main.yml @@ -0,0 +1,72 @@ +- set_fact: + app_id: "e0a62513-1d81-480e-a6dc-5c99cdd58d9a" + tenant_id: "72f988bf-86f1-41af-91ab-2d7cd011db47" + +- name: delete ad service principal + azure_rm_adserviceprincipal: + app_id: "{{ app_id }}" + tenant: "{{ tenant_id }}" + state: absent + +- name: create ad service principal + azure_rm_adserviceprincipal: + app_id: "{{ app_id }}" + tenant: "{{ tenant_id }}" + state: present + register: ad_fact + +- assert: + that: + - ad_fact.changed + +- name: create ad service principal (idempontent) + azure_rm_adserviceprincipal: + app_id: "{{ app_id }}" + tenant: "{{ tenant_id }}" + state: present + register: output + +- assert: + that: + - not output.changed + +- name: Get ad service principal info by app_id + azure_rm_adserviceprincipal_info: + app_id: "{{ app_id }}" + tenant: "{{ tenant_id }}" + register: ad_info + +- assert: + that: + - ad_info.service_principals[0].app_display_name == ad_fact.app_display_name + - ad_info.service_principals[0].app_role_assignment_required == False + +- name: update ad service principal app_role_assignmentrequired to True + azure_rm_adserviceprincipal: + app_id: "{{ app_id }}" + tenant: "{{ tenant_id }}" + app_role_assignment_required: True + state: present + register: output + +- name: Get ad service principal info by object_id + azure_rm_adserviceprincipal_info: + tenant: "{{ tenant_id }}" + object_id: "{{ ad_info.service_principals[0].object_id }}" + register: ad_info + +- assert: + that: + - ad_info.service_principals[0].app_display_name == ad_fact.app_display_name + - ad_info.service_principals[0].app_role_assignment_required == True + +- name: delete ad service principal + azure_rm_adserviceprincipal: + app_id: "{{ app_id }}" + tenant: "{{ tenant_id }}" + state: absent + register: output + +- assert: + that: + - output.changed diff --git a/tests/integration/targets/azure_rm_monitorlogprofile/tasks/main.yml b/tests/integration/targets/azure_rm_monitorlogprofile/tasks/main.yml index 9019f59b2..6efa3e384 100644 --- a/tests/integration/targets/azure_rm_monitorlogprofile/tasks/main.yml +++ b/tests/integration/targets/azure_rm_monitorlogprofile/tasks/main.yml @@ -10,7 +10,7 @@ resource_group: "{{ resource_group }}" account_type: Standard_LRS -- name: create log profile (idempotence) +- name: create log profile (check mode) azure_rm_monitorlogprofile: name: "{{ profile_name }}" location: "{{ location }}" @@ -58,7 +58,7 @@ - output.changed - output.id -- name: update log profile (idempotence) +- name: create log profile (idempotence) azure_rm_monitorlogprofile: name: "{{ profile_name }}" location: "{{ location }}" diff --git a/tests/integration/targets/azure_rm_networkinterface/aliases b/tests/integration/targets/azure_rm_networkinterface/aliases index 67f867567..88fb70609 100644 --- a/tests/integration/targets/azure_rm_networkinterface/aliases +++ b/tests/integration/targets/azure_rm_networkinterface/aliases @@ -1,4 +1,4 @@ cloud/azure shippable/azure/group5 destructive -azure_rm_applicationsecuritygroup \ No newline at end of file +azure_rm_applicationsecuritygroup diff --git a/tests/integration/targets/azure_rm_postgresqlserver/aliases b/tests/integration/targets/azure_rm_postgresqlserver/aliases index ad065181b..e37e6ce54 100644 --- a/tests/integration/targets/azure_rm_postgresqlserver/aliases +++ b/tests/integration/targets/azure_rm_postgresqlserver/aliases @@ -1,6 +1,6 @@ cloud/azure destructive -shippable/azure/group11 +shippable/azure/group12 azure_rm_postgresqlserver_facts azure_rm_postgresqldatabase azure_rm_postgresqldatabase_facts diff --git a/tests/integration/targets/azure_rm_privatednszone/aliases b/tests/integration/targets/azure_rm_privatednszone/aliases new file mode 100644 index 000000000..90d5921a5 --- /dev/null +++ b/tests/integration/targets/azure_rm_privatednszone/aliases @@ -0,0 +1,4 @@ +cloud/azure +shippable/azure/group2 +destructive +azure_rm_privatednszone_info diff --git a/tests/integration/targets/azure_rm_privatednszone/meta/main.yml b/tests/integration/targets/azure_rm_privatednszone/meta/main.yml new file mode 100644 index 000000000..95e1952f9 --- /dev/null +++ b/tests/integration/targets/azure_rm_privatednszone/meta/main.yml @@ -0,0 +1,2 @@ +dependencies: + - setup_azure diff --git a/tests/integration/targets/azure_rm_privatednszone/tasks/main.yml b/tests/integration/targets/azure_rm_privatednszone/tasks/main.yml new file mode 100644 index 000000000..eba80899d --- /dev/null +++ b/tests/integration/targets/azure_rm_privatednszone/tasks/main.yml @@ -0,0 +1,77 @@ +- name: Create random domain name + set_fact: + domain_name: "{{ resource_group | hash('md5') | truncate(16, True, '') + (65535 | random | string) }}" + +- name: Create a private DNS zone (check mode) + azure_rm_privatednszone: + resource_group: "{{ resource_group }}" + name: "{{ domain_name }}.com" + register: results + check_mode: true + +- assert: + that: results.changed + +- name: Create a private DNS zone + azure_rm_privatednszone: + resource_group: "{{ resource_group }}" + name: "{{ domain_name }}.com" + register: results + +- assert: + that: results.changed + +- name: Update private DNS zone with tags + azure_rm_privatednszone: + resource_group: "{{ resource_group }}" + name: "{{ domain_name }}.com" + tags: + test: modified + register: results + +- assert: + that: + - results.changed + - results.state.tags.test == 'modified' + +- name: Test idempotent + azure_rm_privatednszone: + name: "{{ domain_name }}.com" + resource_group: "{{ resource_group }}" + register: results + +- assert: + that: + - not results.changed + +- name: Retrieve DNS Zone Facts + azure_rm_privatednszone_info: + resource_group: "{{ resource_group }}" + name: "{{ domain_name }}.com" + register: zones + +- name: Assert that facts module returned result + assert: + that: + - zones.privatednszones[0].tags.test == 'modified' + - zones.privatednszones[0].number_of_record_sets == 1 + +# +# azure_rm_privatednszone cleanup +# + +- name: Delete private DNS zone + azure_rm_privatednszone: + resource_group: "{{ resource_group }}" + name: "{{ domain_name }}.com" + state: absent + +- name: Delete private DNS zone (idempotent) + azure_rm_privatednszone: + resource_group: "{{ resource_group }}" + name: "{{ domain_name }}.com" + state: absent + register: results + +- assert: + that: not results.changed diff --git a/tests/integration/targets/azure_rm_subnet/tasks/main.yml b/tests/integration/targets/azure_rm_subnet/tasks/main.yml index acc91ceee..7332bc5e1 100644 --- a/tests/integration/targets/azure_rm_subnet/tasks/main.yml +++ b/tests/integration/targets/azure_rm_subnet/tasks/main.yml @@ -94,6 +94,18 @@ - assert: that: not output.changed +- name: Able to completely remove service endpoints + azure_rm_subnet: + name: foobar + virtual_network_name: My_Virtual_Network + resource_group: "{{ resource_group }}" + address_prefix_cidr: "10.1.0.0/16" + service_endpoints: [] + register: output + +- assert: + that: output.state.service_endpoints is not defined + - name: Create network security group in another resource group azure_rm_securitygroup: name: secgroupfoo diff --git a/tests/integration/targets/azure_rm_virtualmachine/tasks/azure_test_ephemeral_os.yml b/tests/integration/targets/azure_rm_virtualmachine/tasks/azure_test_ephemeral_os.yml new file mode 100644 index 000000000..f2101ca4c --- /dev/null +++ b/tests/integration/targets/azure_rm_virtualmachine/tasks/azure_test_ephemeral_os.yml @@ -0,0 +1,101 @@ +- include_tasks: setup.yml + +- name: Create minimal VM with defaults + azure_rm_virtualmachine: + resource_group: "{{ resource_group }}" + name: "{{ vm_name }}" + admin_username: "testuser" + admin_password: "Pass123$$$abx!" + vm_size: Standard_DS2_v2 + image: + offer: UbuntuServer + publisher: Canonical + sku: 16.04-LTS + version: latest + register: vm_output + +- name: Generalize VM + azure_rm_virtualmachine: + resource_group: "{{ resource_group }}" + name: "{{ vm_name }}" + generalized: yes + +- name: Create an image from VM + azure_rm_image: + resource_group: "{{ resource_group }}" + source: "{{ vm_name }}" + name: testimage + os_type: Linux + register: output + +- assert: + that: + - output.changed + +- name: Create virtual machine ephmeral OS disk + azure_rm_virtualmachine: + resource_group: "{{ resource_group }}" + name: "{{ vm_name }}-02" + admin_username: "testuser" + admin_password: "Pass123$$$abx!" + vm_size: Standard_DS2_v2 + os_disk_caching: ReadOnly + ephemeral_os_disk: True + image: testimage + register: output + +- assert: + that: + - output.changed + - output.ansible_facts.azure_vm.properties.storageProfile.osDisk.diffDiskSettings.option == 'Local' + +- name: Check virtual machine ephmeral OS disk idempotent + azure_rm_virtualmachine: + resource_group: "{{ resource_group }}" + name: "{{ vm_name }}-02" + admin_username: "testuser" + admin_password: "Pass123$$$abx!" + vm_size: Standard_DS2_v2 + os_disk_caching: ReadOnly + ephemeral_os_disk: True + image: testimage + register: output + +- assert: + that: + - not output.changed + +- name: Check virtual machine ephmeral OS disk can't update + azure_rm_virtualmachine: + resource_group: "{{ resource_group }}" + name: "{{ vm_name }}-02" + admin_username: "testuser" + admin_password: "Pass123$$$abx!" + vm_size: Standard_DS2_v2 + os_disk_caching: ReadOnly + ephemeral_os_disk: False + image: testimage + ignore_errors: yes + register: ouput + +- assert: + that: + - not output.changed + +- name: Delete VM + azure_rm_virtualmachine: + resource_group: "{{ resource_group }}" + name: "{{ vm_name }}" + state: absent + +- name: Delete VM + azure_rm_virtualmachine: + resource_group: "{{ resource_group }}" + name: "{{ vm_name }}-02" + state: absent + +- name: Create an image from VM + azure_rm_image: + resource_group: "{{ resource_group }}" + name: testimage + state: absent diff --git a/tests/integration/targets/azure_rm_virtualmachinescaleset/tasks/main.yml b/tests/integration/targets/azure_rm_virtualmachinescaleset/tasks/main.yml index 91deb5d2e..0f61968c5 100644 --- a/tests/integration/targets/azure_rm_virtualmachinescaleset/tasks/main.yml +++ b/tests/integration/targets/azure_rm_virtualmachinescaleset/tasks/main.yml @@ -299,6 +299,7 @@ vmss_name: testVMSS{{ rpfx }} name: testExtension register: results + - name: Assert that facts are returned assert: that: @@ -318,6 +319,7 @@ resource_group: "{{ resource_group }}" vmss_name: testVMSS{{ rpfx }} register: results + - name: Assert that facts are returned assert: that: @@ -332,7 +334,6 @@ - results.extensions[0]['auto_upgrade_minor_version'] != None - results.extensions[0]['provisioning_state'] != None - - name: Delete VMSS Extension azure_rm_virtualmachinescalesetextension: resource_group: "{{ resource_group }}" @@ -381,7 +382,6 @@ assert: that: results.changed - - name: Delete VMSS azure_rm_virtualmachinescaleset: resource_group: "{{ resource_group }}" @@ -519,6 +519,59 @@ name: testVMSS{{ rpfx }}2 state: absent +- name: Create VMSS with ephmeral OS disk. + azure_rm_virtualmachinescaleset: + resource_group: "{{ resource_group }}" + name: testVMSS{{ rpfx }}3 + vm_size: Standard_DS2_v2 + capacity: 0 + virtual_network_name: testVnet + subnet_name: testSubnet + admin_username: testuser + ssh_password_enabled: true + admin_password: "Password1234!" + ephemeral_os_disk: True + image: + name: testimageb + resource_group: "{{ resource_group }}" + upgrade_policy: Manual + security_group: + name: testNetworkSecurityGroup2 + resource_group: "{{ resource_group_secondary }}" + register: results + +- assert: + that: + - results.changed + - results.ansible_facts.azure_vmss.properties.virtualMachineProfile.storageProfile.osDisk.diffDiskSettings.option == 'Local' + +- name: Check VMSS ephmeral OS disk can't udpate + azure_rm_virtualmachinescaleset: + resource_group: "{{ resource_group }}" + name: testVMSS{{ rpfx }}3 + vm_size: Standard_DS2_v2 + capacity: 0 + virtual_network_name: testVnet + subnet_name: testSubnet + admin_username: testuser + ssh_password_enabled: true + admin_password: "Password1234!" + ephemeral_os_disk: False + image: + name: testimageb + resource_group: "{{ resource_group }}" + upgrade_policy: Manual + security_group: + name: testNetworkSecurityGroup2 + resource_group: "{{ resource_group_secondary }}" + ignore_errors: yes + +- name: Delete VMSS + azure_rm_virtualmachinescaleset: + resource_group: "{{ resource_group }}" + name: testVMSS{{ rpfx }}3 + state: absent + - name: Fail when instance type is not supported to enable accelerated networking azure_rm_virtualmachinescaleset: resource_group: "{{ resource_group }}" diff --git a/tests/sanity/ignore-2.11.txt b/tests/sanity/ignore-2.11.txt index fa4bad195..6bcb55434 100644 --- a/tests/sanity/ignore-2.11.txt +++ b/tests/sanity/ignore-2.11.txt @@ -867,5 +867,32 @@ plugins/modules/azure_rm_azurefirewall.py validate-modules:required_if-unknown-k plugins/modules/azure_rm_azurefirewall_info.py validate-modules:deprecation-either-date-or-version plugins/modules/azure_rm_azurefirewall_info.py validate-modules:required_if-requirements-unknown plugins/modules/azure_rm_azurefirewall_info.py validate-modules:required_if-unknown-key +plugins/modules/azure_rm_privatednszone.py validate-modules:deprecation-either-date-or-version +plugins/modules/azure_rm_privatednszone.py validate-modules:required_if-requirements-unknown +plugins/modules/azure_rm_privatednszone.py validate-modules:required_if-unknown-key +plugins/modules/azure_rm_privatednszone_info.py validate-modules:deprecation-either-date-or-version +plugins/modules/azure_rm_privatednszone_info.py validate-modules:parameter-list-no-elements +plugins/modules/azure_rm_privatednszone_info.py validate-modules:required_if-requirements-unknown +plugins/modules/azure_rm_privatednszone_info.py validate-modules:required_if-unknown-key +plugins/modules/azure_rm_adpassword.py validate-modules:deprecation-either-date-or-version +plugins/modules/azure_rm_adpassword.py validate-modules:return-syntax-error +plugins/modules/azure_rm_adpassword.py validate-modules:import-before-documentation +plugins/modules/azure_rm_adpassword.py validate-modules:nonexistent-parameter-documented +plugins/modules/azure_rm_adpassword.py validate-modules:required_if-requirements-unknown +plugins/modules/azure_rm_adpassword.py validate-modules:required_if-unknown-key +plugins/modules/azure_rm_adpassword_info.py validate-modules:nonexistent-parameter-documented +plugins/modules/azure_rm_adpassword_info.py validate-modules:required_if-requirements-unknown +plugins/modules/azure_rm_adpassword_info.py validate-modules:required_if-unknown-key +plugins/modules/azure_rm_adpassword_info.py validate-modules:deprecation-either-date-or-version +plugins/modules/azure_rm_adpassword_info.py validate-modules:return-syntax-error +plugins/modules/azure_rm_adpassword_info.py validate-modules:import-before-documentation +plugins/modules/azure_rm_adserviceprincipal.py validate-modules:deprecation-either-date-or-version +plugins/modules/azure_rm_adserviceprincipal.py validate-modules:nonexistent-parameter-documented +plugins/modules/azure_rm_adserviceprincipal.py validate-modules:required_if-requirements-unknown +plugins/modules/azure_rm_adserviceprincipal.py validate-modules:required_if-unknown-key +plugins/modules/azure_rm_adserviceprincipal_info.py validate-modules:deprecation-either-date-or-version +plugins/modules/azure_rm_adserviceprincipal_info.py validate-modules:nonexistent-parameter-documented +plugins/modules/azure_rm_adserviceprincipal_info.py validate-modules:required_if-requirements-unknown +plugins/modules/azure_rm_adserviceprincipal_info.py validate-modules:required_if-unknown-key tests/utils/shippable/check_matrix.py replace-urlopen tests/utils/shippable/timing.py shebang diff --git a/tests/sanity/ignore-2.9.txt b/tests/sanity/ignore-2.9.txt index 9cb04a767..e4da58048 100644 --- a/tests/sanity/ignore-2.9.txt +++ b/tests/sanity/ignore-2.9.txt @@ -299,5 +299,16 @@ plugins/modules/azure_rm_trafficmanager.py validate-modules:missing-module-utils plugins/modules/azure_rm_trafficmanagerprofile.py validate-modules:missing-module-utils-import plugins/modules/azure_rm_virtualnetworkpeering.py validate-modules:missing-module-utils-import plugins/modules/azure_rm_virtualnetworkpeering_info.py validate-modules:missing-module-utils-import +plugins/modules/azure_rm_adpassword.py validate-modules:missing-module-utils-import +plugins/modules/azure_rm_adpassword.py validate-modules:nonexistent-parameter-documented +plugins/modules/azure_rm_adpassword.py validate-modules:return-syntax-error +plugins/modules/azure_rm_adpassword.py validate-modules:import-before-documentation +plugins/modules/azure_rm_adpassword_info.py validate-modules:missing-module-utils-import +plugins/modules/azure_rm_adpassword_info.py validate-modules:nonexistent-parameter-documented +plugins/modules/azure_rm_adpassword_info.py validate-modules:import-before-documentation +plugins/modules/azure_rm_adserviceprincipal.py validate-modules:missing-module-utils-import +plugins/modules/azure_rm_adserviceprincipal.py validate-modules:nonexistent-parameter-documented +plugins/modules/azure_rm_adserviceprincipal_info.py validate-modules:missing-module-utils-import +plugins/modules/azure_rm_adserviceprincipal_info.py validate-modules:nonexistent-parameter-documented tests/utils/shippable/check_matrix.py replace-urlopen tests/utils/shippable/timing.py shebang diff --git a/tests/utils/ado/ado.sh b/tests/utils/ado/ado.sh index b17ca76c8..e760115a9 100755 --- a/tests/utils/ado/ado.sh +++ b/tests/utils/ado/ado.sh @@ -70,18 +70,19 @@ fi timeout=60 -test_list=("azure_rm_acs" "azure_rm_aks" "azure_rm_appgateway" "azure_rm_appserviceplan" "azure_rm_automationaccount" "azure_rm_autoscale" "azure_rm_availabilityset" "azure_rm_azurefirewall" "azure_rm_batchaccount" "azure_rm_cdnprofile" "azure_rm_containerinstance" "azure_rm_containerregistry" "azure_rm_cosmosdbaccount" "azure_rm_deployment" "azure_rm_dnsrecordset" "azure_rm_dnszone" "azure_rm_functionapp" "azure_rm_gallery" "azure_rm_hdinsightcluster" "azure_rm_image" "azure_rm_iothub" "azure_rm_keyvault" "azure_rm_keyvaultkey" "azure_rm_keyvaultsecret" "azure_rm_loadbalancer" "azure_rm_manageddisk" "azure_rm_mariadbserver" "azure_rm_monitorlogprofile" "azure_rm_mysqlserver" "azure_rm_networkinterface" "azure_rm_postgresqlserver" "azure_rm_publicipaddress" "azure_rm_rediscache" "azure_rm_resource" "azure_rm_resourcegroup" "azure_rm_routetable" "azure_rm_securitygroup" "azure_rm_servicebus" "azure_rm_sqlserver" "azure_rm_storageaccount" "azure_rm_storageblob" "azure_rm_subnet" "azure_rm_trafficmanagerprofile" "azure_rm_virtualmachine" "azure_rm_virtualmachineextension" "azure_rm_virtualmachineimage_info" "azure_rm_virtualmachinescaleset" "azure_rm_virtualnetwork" "azure_rm_virtualnetworkgateway" "azure_rm_virtualnetworkpeering" "azure_rm_webapp" "azure_rm_workspace" "inventory_azure" "setup_azure" "azure_rm_acs" "azure_rm_aks" "azure_rm_appgateway" "azure_rm_appserviceplan" "azure_rm_automationaccount" "azure_rm_autoscale" "azure_rm_availabilityset" "azure_rm_azurefirewall" "azure_rm_batchaccount" "azure_rm_cdnprofile" "azure_rm_containerinstance" "azure_rm_containerregistry" "azure_rm_cosmosdbaccount" "azure_rm_deployment" "azure_rm_dnsrecordset" "azure_rm_dnszone" "azure_rm_functionapp" "azure_rm_gallery" "azure_rm_hdinsightcluster" "azure_rm_image" "azure_rm_iothub" "azure_rm_keyvault" "azure_rm_keyvaultkey" "azure_rm_keyvaultsecret" "azure_rm_loadbalancer" "azure_rm_manageddisk" "azure_rm_mariadbserver" "azure_rm_monitorlogprofile" "azure_rm_mysqlserver" "azure_rm_networkinterface" "azure_rm_postgresqlserver" "azure_rm_publicipaddress" "azure_rm_rediscache" "azure_rm_resource" "azure_rm_resourcegroup" "azure_rm_routetable" "azure_rm_securitygroup" "azure_rm_servicebus" "azure_rm_sqlserver" "azure_rm_storageaccount" "azure_rm_storageblob" "azure_rm_subnet" "azure_rm_trafficmanagerprofile" "azure_rm_virtualmachine" "azure_rm_virtualmachineextension" "azure_rm_virtualmachineimage_info" "azure_rm_virtualmachinescaleset" "azure_rm_virtualnetwork" "azure_rm_virtualnetworkgateway" "azure_rm_virtualnetworkpeering" "azure_rm_webapp" "azure_rm_workspace" "inventory_azure" "setup_azure") if [ "$4" = "all" ] then echo "All module need test" else - for item in ${test_list[*]} + path_dir="${TEST_DIR}/tests/integration/targets/" + for item in "$path_dir"* do - if [ "${item}" = "$4" ] + if [ "${item}" = "$path_dir""$4" ] then echo "PASS" else - echo "disabled" >> "${TEST_DIR}"/tests/integration/targets/"${item}"/aliases + echo " " >> "${item}"/aliases + echo "disabled" >> "${item}"/aliases fi done fi