Add support for Azure 2.0.0 (#27920)

* Adapt azure_rm_resource_group to azure 2.0.0 + azure Cli support

* Fix exceptions in Azure ARM plugins

* update azure_rm_networkinterface documention to reflect required params

* change state param to not required for docs in azure_rm_subnet

* fix import to reflect azure==2.0.0 changes

* add aliases and fix docs for azure_rm_storageblob

* add resource_group_name alias to azure_rm_storageaccount_facts

* fix import bug due to change in azure==2.0.0

* fix args bug and enum modules issue

* update docs to reflect azure==2.0.0

* pin management clients to a specific api_version

* update docs to reflect the new azure-ansible-base python package

* add fallback for older api resource group listing

* rework azure dependencies installation

* refactor path joining to a cross-plat solution
This commit is contained in:
Thomas Stringer 2017-08-11 11:22:02 -04:00 committed by Matt Davis
parent 1b9d9376e2
commit e4cd899363
17 changed files with 151 additions and 51 deletions

View file

@ -31,6 +31,7 @@ from ansible.module_utils.basic import AnsibleModule
from ansible.module_utils.six.moves import configparser
AZURE_COMMON_ARGS = dict(
cli_default_profile=dict(type='bool'),
profile=dict(type='str'),
subscription_id=dict(type='str', no_log=True),
client_id=dict(type='str', no_log=True),
@ -42,6 +43,7 @@ AZURE_COMMON_ARGS = dict(
)
AZURE_CREDENTIAL_ENV_MAPPING = dict(
cli_default_profile='AZURE_CLI_DEFAULT_PROFILE',
profile='AZURE_PROFILE',
subscription_id='AZURE_SUBSCRIPTION_ID',
client_id='AZURE_CLIENT_ID',
@ -70,6 +72,7 @@ AZURE_FAILED_STATE = "Failed"
HAS_AZURE = True
HAS_AZURE_EXC = None
HAS_AZURE_CLI_CORE = True
HAS_MSRESTAZURE = True
HAS_MSRESTAZURE_EXC = None
@ -91,16 +94,24 @@ try:
from azure.mgmt.storage.version import VERSION as storage_client_version
from azure.mgmt.compute.version import VERSION as compute_client_version
from azure.mgmt.resource.version import VERSION as resource_client_version
from azure.mgmt.network.network_management_client import NetworkManagementClient
from azure.mgmt.resource.resources.resource_management_client import ResourceManagementClient
from azure.mgmt.storage.storage_management_client import StorageManagementClient
from azure.mgmt.compute.compute_management_client import ComputeManagementClient
from azure.mgmt.network import NetworkManagementClient
from azure.mgmt.resource.resources import ResourceManagementClient
from azure.mgmt.storage import StorageManagementClient
from azure.mgmt.compute import ComputeManagementClient
from azure.storage.cloudstorageaccount import CloudStorageAccount
except ImportError as exc:
HAS_AZURE_EXC = exc
HAS_AZURE = False
try:
from azure.cli.core.util import CLIError
from azure.common.credentials import get_azure_cli_credentials, get_cli_profile
from azure.common.cloud import get_cli_active_cloud
except ImportError:
HAS_AZURE_CLI_CORE = False
def azure_id_to_dict(id):
pieces = re.sub(r'^\/', '', id).split('/')
result = {}
@ -112,13 +123,13 @@ def azure_id_to_dict(id):
AZURE_EXPECTED_VERSIONS = dict(
storage_client_version="0.30.0rc5",
compute_client_version="0.30.0rc5",
network_client_version="0.30.0rc5",
resource_client_version="0.30.0rc5"
storage_client_version="1.0.0",
compute_client_version="1.0.0",
network_client_version="1.0.0",
resource_client_version="1.1.0"
)
AZURE_MIN_RELEASE = '2.0.0rc5'
AZURE_MIN_RELEASE = '2.0.0'
class AzureRMModuleBase(object):
@ -171,7 +182,7 @@ class AzureRMModuleBase(object):
self.credentials = self._get_credentials(self.module.params)
if not self.credentials:
self.fail("Failed to get credentials. Either pass as parameters, set environment variables, "
"or define a profile in ~/.azure/credentials.")
"or define a profile in ~/.azure/credentials or be logged using AzureCLI.")
if self.credentials.get('subscription_id', None) is None:
self.fail("Credentials did not include a subscription_id value.")
@ -192,7 +203,14 @@ class AzureRMModuleBase(object):
self.azure_credentials = UserPassCredentials(self.credentials['ad_user'], self.credentials['password'])
else:
self.fail("Failed to authenticate with provided credentials. Some attributes were missing. "
"Credentials must include client_id, secret and tenant or ad_user and password.")
"Credentials must include client_id, secret and tenant or ad_user and password or "
"be logged using AzureCLI.")
# base_url for sovereign cloud support. For now only if AzureCLI
if self.credentials.get('base_url') is not None:
self.base_url = self.credentials.get('base_url')
else:
self.base_url = None
# common parameter validation
if self.module.params.get('tags'):
@ -313,6 +331,20 @@ class AzureRMModuleBase(object):
except Exception as exc:
self.fail("Error retrieving resource group {0} - {1}".format(resource_group, str(exc)))
def _get_azure_cli_profile(self):
if not HAS_AZURE_CLI_CORE:
self.fail("Do you have azure-cli-core installed? Try `pip install 'azure-cli-core' --upgrade`")
try:
credentials, subscription_id = get_azure_cli_credentials()
base_url = get_cli_active_cloud().endpoints.resource_manager
return {
'credentials': credentials,
'subscription_id': subscription_id,
'base_url': base_url
}
except CLIError as err:
self.fail("AzureCLI profile cannot be loaded - {0}".format(err))
def _get_profile(self, profile="default"):
path = expanduser("~/.azure/credentials")
try:
@ -338,6 +370,9 @@ class AzureRMModuleBase(object):
for attribute, env_variable in AZURE_CREDENTIAL_ENV_MAPPING.items():
env_credentials[attribute] = os.environ.get(env_variable, None)
if (env_credentials['cli_default_profile'] or '').lower() in ["true", "yes", "1"]:
return self._get_azure_cli_profile()
if env_credentials['profile']:
credentials = self._get_profile(env_credentials['profile'])
return credentials
@ -357,6 +392,10 @@ class AzureRMModuleBase(object):
for attribute, env_variable in AZURE_CREDENTIAL_ENV_MAPPING.items():
arg_credentials[attribute] = params.get(attribute, None)
if arg_credentials['cli_default_profile']:
self.log('Retrieving credentials from Azure CLI current profile')
return self._get_azure_cli_profile()
# try module params
if arg_credentials['profile'] is not None:
self.log('Retrieving credentials with profile parameter.')
@ -595,7 +634,12 @@ class AzureRMModuleBase(object):
self.log('Getting storage client...')
if not self._storage_client:
self.check_client_version('storage', storage_client_version, AZURE_EXPECTED_VERSIONS['storage_client_version'])
self._storage_client = StorageManagementClient(self.azure_credentials, self.subscription_id)
self._storage_client = StorageManagementClient(
self.azure_credentials,
self.subscription_id,
base_url=self.base_url,
api_version='2017-06-01'
)
self._register('Microsoft.Storage')
return self._storage_client
@ -604,7 +648,12 @@ class AzureRMModuleBase(object):
self.log('Getting network client')
if not self._network_client:
self.check_client_version('network', network_client_version, AZURE_EXPECTED_VERSIONS['network_client_version'])
self._network_client = NetworkManagementClient(self.azure_credentials, self.subscription_id)
self._network_client = NetworkManagementClient(
self.azure_credentials,
self.subscription_id,
base_url=self.base_url,
api_version='2017-06-01'
)
self._register('Microsoft.Network')
return self._network_client
@ -613,7 +662,12 @@ class AzureRMModuleBase(object):
self.log('Getting resource manager client')
if not self._resource_client:
self.check_client_version('resource', resource_client_version, AZURE_EXPECTED_VERSIONS['resource_client_version'])
self._resource_client = ResourceManagementClient(self.azure_credentials, self.subscription_id)
self._resource_client = ResourceManagementClient(
self.azure_credentials,
self.subscription_id,
base_url=self.base_url,
api_version='2017-05-10'
)
return self._resource_client
@property
@ -621,6 +675,11 @@ class AzureRMModuleBase(object):
self.log('Getting compute client')
if not self._compute_client:
self.check_client_version('compute', compute_client_version, AZURE_EXPECTED_VERSIONS['compute_client_version'])
self._compute_client = ComputeManagementClient(self.azure_credentials, self.subscription_id)
self._compute_client = ComputeManagementClient(
self.azure_credentials,
self.subscription_id,
base_url=self.base_url,
api_version='2017-03-30'
)
self._register('Microsoft.Compute')
return self._compute_client