diff --git a/lib/ansible/module_utils/network/avi/ansible_utils.py b/lib/ansible/module_utils/network/avi/ansible_utils.py new file mode 100644 index 00000000000..d2799cba993 --- /dev/null +++ b/lib/ansible/module_utils/network/avi/ansible_utils.py @@ -0,0 +1,556 @@ +from __future__ import absolute_import + +""" +Created on Aug 16, 2016 + +@author: Gaurav Rastogi (grastogi@avinetworks.com) +""" +import os +import re +import logging +import sys +from copy import deepcopy + +try: + from ansible.module_utils.network.avi.avi_api import ( + ApiSession, ObjectNotFound, avi_sdk_syslog_logger, AviCredentials, HAS_AVI) +except ImportError: + HAS_AVI = False + + +if os.environ.get('AVI_LOG_HANDLER', '') != 'syslog': + log = logging.getLogger(__name__) +else: + # Ansible does not allow logging from the modules. + log = avi_sdk_syslog_logger() + + +def _check_type_string(x): + """ + :param x: + :return: True if it is of type string + """ + if isinstance(x, str): + return True + if sys.version_info[0] < 3: + try: + return isinstance(x, unicode) + except NameError: + return False + + +class AviCheckModeResponse(object): + """ + Class to support ansible check mode. + """ + + def __init__(self, obj, status_code=200): + self.obj = obj + self.status_code = status_code + + def json(self): + return self.obj + + +def ansible_return(module, rsp, changed, req=None, existing_obj=None, + api_context=None): + """ + :param module: AnsibleModule + :param rsp: ApiResponse from avi_api + :param changed: boolean + :param req: ApiRequest to avi_api + :param existing_obj: object to be passed debug output + :param api_context: api login context + + helper function to return the right ansible based on the error code and + changed + Returns: specific ansible module exit function + """ + + if rsp is not None and rsp.status_code > 299: + return module.fail_json( + msg='Error %d Msg %s req: %s api_context:%s ' % ( + rsp.status_code, rsp.text, req, api_context)) + api_creds = AviCredentials() + api_creds.update_from_ansible_module(module) + key = '%s:%s:%s' % (api_creds.controller, api_creds.username, + api_creds.port) + disable_fact = module.params.get('avi_disable_session_cache_as_fact') + + fact_context = None + if not disable_fact: + fact_context = module.params.get('api_context', {}) + if fact_context: + fact_context.update({key: api_context}) + else: + fact_context = {key: api_context} + + obj_val = rsp.json() if rsp else existing_obj + + if (obj_val and module.params.get("obj_username", None) and + "username" in obj_val): + obj_val["obj_username"] = obj_val["username"] + if (obj_val and module.params.get("obj_password", None) and + "password" in obj_val): + obj_val["obj_password"] = obj_val["password"] + old_obj_val = existing_obj if changed and existing_obj else None + api_context_val = api_context if disable_fact else None + ansible_facts_val = dict( + avi_api_context=fact_context) if not disable_fact else {} + + return module.exit_json( + changed=changed, obj=obj_val, old_obj=old_obj_val, + ansible_facts=ansible_facts_val, api_context=api_context_val) + + +def purge_optional_fields(obj, module): + """ + It purges the optional arguments to be sent to the controller. + :param obj: dictionary of the ansible object passed as argument. + :param module: AnsibleModule + return modified obj + """ + purge_fields = [] + for param, spec in module.argument_spec.items(): + if not spec.get('required', False): + if param not in obj: + # these are ansible common items + continue + if obj[param] is None: + purge_fields.append(param) + log.debug('purging fields %s', purge_fields) + for param in purge_fields: + obj.pop(param, None) + return obj + + +def cleanup_absent_fields(obj): + """ + cleans up any field that is marked as state: absent. It needs to be removed + from the object if it is present. + :param obj: + :return: Purged object + """ + if type(obj) != dict: + return obj + cleanup_keys = [] + for k, v in obj.items(): + if type(v) == dict: + if (('state' in v and v['state'] == 'absent') or + (v == "{'state': 'absent'}")): + cleanup_keys.append(k) + else: + cleanup_absent_fields(v) + if not v: + cleanup_keys.append(k) + elif type(v) == list: + new_list = [] + for elem in v: + elem = cleanup_absent_fields(elem) + if elem: + # remove the item from list + new_list.append(elem) + if new_list: + obj[k] = new_list + else: + cleanup_keys.append(k) + elif isinstance(v, str) or isinstance(v, str): + if v == "{'state': 'absent'}": + cleanup_keys.append(k) + for k in cleanup_keys: + del obj[k] + return obj + + +RE_REF_MATCH = re.compile(r'^/api/[\w/]+\?name\=[\w]+[^#<>]*$') +# if HTTP ref match then strip out the #name +HTTP_REF_MATCH = re.compile(r'https://[\w.0-9:-]+/api/.+') +HTTP_REF_W_NAME_MATCH = re.compile(r'https://[\w.0-9:-]+/api/.*#.+') + + +def ref_n_str_cmp(x, y): + """ + compares two references + 1. check for exact reference + 2. check for obj_type/uuid + 3. check for name + + if x is ref=name then extract uuid and name from y and use it. + if x is http_ref then + strip x and y + compare them. + + if x and y are urls then match with split on # + if x is a RE_REF_MATCH then extract name + if y is a REF_MATCH then extract name + :param x: first string + :param y: second string from controller's object + + Returns + True if they are equivalent else False + """ + if type(y) in (int, float, bool, int, complex): + y = str(y) + x = str(x) + if not (_check_type_string(x) and _check_type_string(y)): + return False + y_uuid = y_name = str(y) + x = str(x) + if RE_REF_MATCH.match(x): + x = x.split('name=')[1] + elif HTTP_REF_MATCH.match(x): + x = x.rsplit('#', 1)[0] + y = y.rsplit('#', 1)[0] + elif RE_REF_MATCH.match(y): + y = y.split('name=')[1] + + if HTTP_REF_W_NAME_MATCH.match(y): + path = y.split('api/', 1)[1] + # Fetching name or uuid from path /xxxx_xx/xx/xx_x/uuid_or_name + uuid_or_name = path.split('/')[-1] + parts = uuid_or_name.rsplit('#', 1) + y_uuid = parts[0] + y_name = parts[1] if len(parts) > 1 else '' + # is just string but y is a url so match either uuid or name + result = (x in (y, y_name, y_uuid)) + if not result: + log.debug('x: %s y: %s y_name %s y_uuid %s', + x, y, y_name, y_uuid) + return result + + +def avi_obj_cmp(x, y, sensitive_fields=None): + """ + compares whether x is fully contained in y. The comparision is different + from a simple dictionary compare for following reasons + 1. Some fields could be references. The object in controller returns the + full URL for those references. However, the ansible script would have + it specified as /api/pool?name=blah. So, the reference fields need + to match uuid, relative reference based on name and actual reference. + + 2. Optional fields with defaults: In case there are optional fields with + defaults then controller automatically fills it up. This would + cause the comparison with Ansible object specification to always return + changed. + + 3. Optional fields without defaults: This is most tricky. The issue is + how to specify deletion of such objects from ansible script. If the + ansible playbook has object specified as Null then Avi controller will + reject for non Message(dict) type fields. In addition, to deal with the + defaults=null issue all the fields that are set with None are purged + out before comparing with Avi controller's version + + So, the solution is to pass state: absent if any optional field needs + to be deleted from the configuration. The script would return changed + =true if it finds a key in the controller version and it is marked with + state: absent in ansible playbook. Alternatively, it would return + false if key is not present in the controller object. Before, doing + put or post it would purge the fields that are marked state: absent. + + :param x: first string + :param y: second string from controller's object + :param sensitive_fields: sensitive fields to ignore for diff + + Returns: + True if x is subset of y else False + """ + if not sensitive_fields: + sensitive_fields = set() + if isinstance(x, str) or isinstance(x, str): + # Special handling for strings as they can be references. + return ref_n_str_cmp(x, y) + if type(x) not in [list, dict]: + # if it is not list or dict or string then simply compare the values + return x == y + if type(x) == list: + # should compare each item in the list and that should match + if len(x) != len(y): + log.debug('x has %d items y has %d', len(x), len(y)) + return False + for i in zip(x, y): + if not avi_obj_cmp(i[0], i[1], sensitive_fields=sensitive_fields): + # no need to continue + return False + + if type(x) == dict: + x.pop('_last_modified', None) + x.pop('tenant', None) + y.pop('_last_modified', None) + x.pop('api_version', None) + y.pop('api_verison', None) + d_xks = [k for k in x.keys() if k in sensitive_fields] + + if d_xks: + # if there is sensitive field then always return changed + return False + # pop the keys that are marked deleted but not present in y + # return false if item is marked absent and is present in y + d_x_absent_ks = [] + for k, v in x.items(): + if v is None: + d_x_absent_ks.append(k) + continue + if isinstance(v, dict): + if ('state' in v) and (v['state'] == 'absent'): + if type(y) == dict and k not in y: + d_x_absent_ks.append(k) + else: + return False + elif not v: + d_x_absent_ks.append(k) + elif isinstance(v, list) and not v: + d_x_absent_ks.append(k) + # Added condition to check key in dict. + elif isinstance(v, str) or (k in y and isinstance(y[k], str)): + # this is the case when ansible converts the dictionary into a + # string. + if v == "{'state': 'absent'}" and k not in y: + d_x_absent_ks.append(k) + elif not v and k not in y: + # this is the case when x has set the value that qualifies + # as not but y does not have that value + d_x_absent_ks.append(k) + for k in d_x_absent_ks: + x.pop(k) + x_keys = set(x.keys()) + y_keys = set(y.keys()) + if not x_keys.issubset(y_keys): + # log.debug('x has %s and y has %s keys', len(x_keys), len(y_keys)) + return False + for k, v in x.items(): + if k not in y: + # log.debug('k %s is not in y %s', k, y) + return False + if not avi_obj_cmp(v, y[k], sensitive_fields=sensitive_fields): + # log.debug('k %s v %s did not match in y %s', k, v, y[k]) + return False + return True + + +POP_FIELDS = ['state', 'controller', 'username', 'password', 'api_version', + 'avi_credentials', 'avi_api_update_method', 'avi_api_patch_op', + 'api_context', 'tenant', 'tenant_uuid', 'avi_disable_session_cache_as_fact'] + + +def get_api_context(module, api_creds): + api_context = module.params.get('api_context') + if api_context and module.params.get('avi_disable_session_cache_as_fact'): + return api_context + elif api_context and not module.params.get( + 'avi_disable_session_cache_as_fact'): + key = '%s:%s:%s' % (api_creds.controller, api_creds.username, + api_creds.port) + return api_context.get(key) + else: + return None + + +def avi_ansible_api(module, obj_type, sensitive_fields): + """ + This converts the Ansible module into AVI object and invokes APIs + :param module: Ansible module + :param obj_type: string representing Avi object type + :param sensitive_fields: sensitive fields to be excluded for comparison + purposes. + Returns: + success: module.exit_json with obj=avi object + faliure: module.fail_json + """ + + api_creds = AviCredentials() + api_creds.update_from_ansible_module(module) + api_context = get_api_context(module, api_creds) + if api_context: + api = ApiSession.get_session( + api_creds.controller, + api_creds.username, + password=api_creds.password, + timeout=api_creds.timeout, + tenant=api_creds.tenant, + tenant_uuid=api_creds.tenant_uuid, + token=api_context['csrftoken'], + port=api_creds.port, + session_id=api_context['session_id'], + csrftoken=api_context['csrftoken']) + else: + api = ApiSession.get_session( + api_creds.controller, + api_creds.username, + password=api_creds.password, + timeout=api_creds.timeout, + tenant=api_creds.tenant, + tenant_uuid=api_creds.tenant_uuid, + token=api_creds.token, + port=api_creds.port) + state = module.params['state'] + # Get the api version. + avi_update_method = module.params.get('avi_api_update_method', 'put') + avi_patch_op = module.params.get('avi_api_patch_op', 'add') + + api_version = api_creds.api_version + name = module.params.get('name', None) + # Added Support to get uuid + uuid = module.params.get('uuid', None) + check_mode = module.check_mode + if uuid and obj_type != 'cluster': + obj_path = '%s/%s' % (obj_type, uuid) + else: + obj_path = '%s/' % obj_type + obj = deepcopy(module.params) + tenant = obj.pop('tenant', '') + tenant_uuid = obj.pop('tenant_uuid', '') + # obj.pop('cloud_ref', None) + for k in POP_FIELDS: + obj.pop(k, None) + purge_optional_fields(obj, module) + + # Special code to handle situation where object has a field + # named username. This is used in case of api/user + # The following code copies the username and password + # from the obj_username and obj_password fields. + if 'obj_username' in obj: + obj['username'] = obj['obj_username'] + obj.pop('obj_username') + if 'obj_password' in obj: + obj['password'] = obj['obj_password'] + obj.pop('obj_password') + if 'full_name' not in obj and 'name' in obj and obj_type == "user": + obj['full_name'] = obj['name'] + # Special case as name represent full_name in user module + # As per API response, name is always same as username regardless of full_name + obj['name'] = obj['username'] + + log.info('passed object %s ', obj) + + if uuid: + # Get the object based on uuid. + try: + existing_obj = api.get( + obj_path, tenant=tenant, tenant_uuid=tenant_uuid, + params={'include_refs': '', 'include_name': ''}, + api_version=api_version) + existing_obj = existing_obj.json() + except ObjectNotFound: + existing_obj = None + elif name: + params = {'include_refs': '', 'include_name': ''} + if obj.get('cloud_ref', None): + # this is the case when gets have to be scoped with cloud + cloud = obj['cloud_ref'].split('name=')[1] + params['cloud_ref.name'] = cloud + existing_obj = api.get_object_by_name( + obj_type, name, tenant=tenant, tenant_uuid=tenant_uuid, + params=params, api_version=api_version) + + # Need to check if tenant_ref was provided and the object returned + # is actually in admin tenant. + if existing_obj and 'tenant_ref' in obj and 'tenant_ref' in existing_obj: + # https://10.10.25.42/api/tenant/admin#admin + existing_obj_tenant = existing_obj['tenant_ref'].split('#')[1] + obj_tenant = obj['tenant_ref'].split('name=')[1] + if obj_tenant != existing_obj_tenant: + existing_obj = None + else: + # added api version to avi api call. + existing_obj = api.get(obj_path, tenant=tenant, tenant_uuid=tenant_uuid, + params={'include_refs': '', 'include_name': ''}, + api_version=api_version).json() + + if state == 'absent': + rsp = None + changed = False + err = False + if not check_mode and existing_obj: + try: + if name is not None: + # added api version to avi api call. + rsp = api.delete_by_name( + obj_type, name, tenant=tenant, tenant_uuid=tenant_uuid, + api_version=api_version) + else: + # added api version to avi api call. + rsp = api.delete( + obj_path, tenant=tenant, tenant_uuid=tenant_uuid, + api_version=api_version) + except ObjectNotFound: + pass + if check_mode and existing_obj: + changed = True + + if rsp: + if rsp.status_code == 204: + changed = True + else: + err = True + if not err: + return ansible_return( + module, rsp, changed, existing_obj=existing_obj, + api_context=api.get_context()) + elif rsp: + return module.fail_json(msg=rsp.text) + + rsp = None + req = None + if existing_obj: + # this is case of modify as object exists. should find out + # if changed is true or not + if name is not None and obj_type != 'cluster': + obj_uuid = existing_obj['uuid'] + obj_path = '%s/%s' % (obj_type, obj_uuid) + if avi_update_method == 'put': + changed = not avi_obj_cmp(obj, existing_obj, sensitive_fields) + obj = cleanup_absent_fields(obj) + if changed: + req = obj + if check_mode: + # No need to process any further. + rsp = AviCheckModeResponse(obj=existing_obj) + else: + rsp = api.put( + obj_path, data=req, tenant=tenant, + tenant_uuid=tenant_uuid, api_version=api_version) + elif check_mode: + rsp = AviCheckModeResponse(obj=existing_obj) + else: + if check_mode: + # No need to process any further. + rsp = AviCheckModeResponse(obj=existing_obj) + changed = True + else: + obj.pop('name', None) + patch_data = {avi_patch_op: obj} + rsp = api.patch( + obj_path, data=patch_data, tenant=tenant, + tenant_uuid=tenant_uuid, api_version=api_version) + obj = rsp.json() + changed = not avi_obj_cmp(obj, existing_obj) + if changed: + log.debug('EXISTING OBJ %s', existing_obj) + log.debug('NEW OBJ %s', obj) + else: + changed = True + req = obj + if check_mode: + rsp = AviCheckModeResponse(obj=None) + else: + rsp = api.post(obj_type, data=obj, tenant=tenant, + tenant_uuid=tenant_uuid, api_version=api_version) + return ansible_return(module, rsp, changed, req, existing_obj=existing_obj, + api_context=api.get_context()) + + +def avi_common_argument_spec(): + """ + Returns common arguments for all Avi modules + :return: dict + """ + return dict( + controller=dict(default=os.environ.get('AVI_CONTROLLER', '')), + username=dict(default=os.environ.get('AVI_USERNAME', '')), + password=dict(default=os.environ.get('AVI_PASSWORD', ''), no_log=True), + tenant=dict(default='admin'), + tenant_uuid=dict(default=''), + api_version=dict(default='16.4.4', type='str'), + avi_credentials=dict(default=None, no_log=True, type='dict'), + api_context=dict(type='dict'), + avi_disable_session_cache_as_fact=dict(default=False, type='bool')) diff --git a/lib/ansible/module_utils/network/avi/avi.py b/lib/ansible/module_utils/network/avi/avi.py index a6c3c723e77..74aaac46737 100644 --- a/lib/ansible/module_utils/network/avi/avi.py +++ b/lib/ansible/module_utils/network/avi/avi.py @@ -32,59 +32,7 @@ # avi.sdk. from __future__ import absolute_import -import os -from distutils.version import LooseVersion -HAS_AVI = True -try: - import avi.sdk - sdk_version = getattr(avi.sdk, '__version__', None) - if ((sdk_version is None) or (sdk_version and (LooseVersion(sdk_version) < LooseVersion('17.2.4')))): - # It allows the __version__ to be '' as that value is used in development builds - raise ImportError - from avi.sdk.utils.ansible_utils import avi_ansible_api -except ImportError: - HAS_AVI = False - - -def avi_common_argument_spec(): - """ - Returns common arguments for all Avi modules - :return: dict - """ - return dict( - controller=dict(default=os.environ.get('AVI_CONTROLLER', '')), - username=dict(default=os.environ.get('AVI_USERNAME', '')), - password=dict(default=os.environ.get('AVI_PASSWORD', ''), no_log=True), - tenant=dict(default='admin'), - tenant_uuid=dict(default=''), - api_version=dict(default='16.4.4'), - avi_credentials=dict(default=None, no_log=True, type='dict'), - api_context=dict(type='dict')) - - -def ansible_return(module, rsp, changed, req=None, existing_obj=None, - api_context=None): - """ - Helper function to return the right ansible return based on the error code and - changed status. - :param module: AnsibleModule - :param rsp: ApiResponse from avi_api - :param changed: boolean - :param req: Actual req dictionary used in Avi API - :param existing_obj: Existing Avi resource. Used for allowing caller to do - diff if desired. - :param api_context: Avi API context information like CSRF token, session_id - used. This can be passed to the next API call to avoid re-login. - - Returns: specific ansible module exit function - """ - if rsp.status_code > 299: - return module.fail_json(msg='Error %d Msg %s req: %s api_context:%s ' % ( - rsp.status_code, rsp.text, req, api_context)) - if changed and existing_obj: - return module.exit_json( - changed=changed, obj=rsp.json(), old_obj=existing_obj, - api_context=api_context) - return module.exit_json(changed=changed, obj=rsp.json(), - api_context=api_context) +from ansible.module_utils.network.avi.ansible_utils import ( + avi_ansible_api, avi_common_argument_spec, ansible_return, + avi_obj_cmp, cleanup_absent_fields, AviCheckModeResponse, HAS_AVI) diff --git a/lib/ansible/module_utils/network/avi/avi_api.py b/lib/ansible/module_utils/network/avi/avi_api.py new file mode 100644 index 00000000000..817f909dd09 --- /dev/null +++ b/lib/ansible/module_utils/network/avi/avi_api.py @@ -0,0 +1,972 @@ +from __future__ import absolute_import +import os +import sys +import copy +import json +import logging +import time +from datetime import datetime, timedelta +from ssl import SSLError + + +class MockResponse(object): + def __init__(self, *args, **kwargs): + raise Exception("Requests library Response object not found. Using fake one.") + + +class MockRequestsConnectionError(Exception): + pass + + +class MockSession(object): + def __init__(self, *args, **kwargs): + raise Exception("Requests library Session object not found. Using fake one.") + + +HAS_AVI = True +try: + from requests import ConnectionError as RequestsConnectionError + from requests import Response + from requests.sessions import Session +except ImportError: + HAS_AVI = False + Response = MockResponse + RequestsConnectionError = MockRequestsConnectionError + Session = MockSession + + +logger = logging.getLogger(__name__) + +sessionDict = {} + + +def avi_timedelta(td): + ''' + This is a wrapper class to workaround python 2.6 builtin datetime.timedelta + does not have total_seconds method + :param timedelta object + ''' + if type(td) != timedelta: + raise TypeError() + if sys.version_info >= (2, 7): + ts = td.total_seconds() + else: + ts = td.seconds + (24 * 3600 * td.days) + return ts + + +def avi_sdk_syslog_logger(logger_name='avi.sdk'): + # The following sets up syslog module to log underlying avi SDK messages + # based on the environment variables: + # AVI_LOG_HANDLER: names the logging handler to use. Only syslog is + # supported. + # AVI_LOG_LEVEL: Logging level used for the avi SDK. Default is DEBUG + # AVI_SYSLOG_ADDRESS: Destination address for the syslog handler. + # Default is /dev/log + from logging.handlers import SysLogHandler + lf = '[%(asctime)s] %(levelname)s [%(module)s.%(funcName)s:%(lineno)d] %(message)s' + log = logging.getLogger(logger_name) + log_level = os.environ.get('AVI_LOG_LEVEL', 'DEBUG') + if log_level: + log.setLevel(getattr(logging, log_level)) + formatter = logging.Formatter(lf) + sh = SysLogHandler(address=os.environ.get('AVI_SYSLOG_ADDRESS', '/dev/log')) + sh.setFormatter(formatter) + log.addHandler(sh) + return log + + +class ObjectNotFound(Exception): + pass + + +class APIError(Exception): + def __init__(self, arg, rsp=None): + self.args = [arg, rsp] + self.rsp = rsp + + +class AviServerError(APIError): + def __init__(self, arg, rsp=None): + super(AviServerError, self).__init__(arg, rsp) + + +class APINotImplemented(Exception): + pass + + +class ApiResponse(Response): + """ + Returns copy of the requests.Response object provides additional helper + routines + 1. obj: returns dictionary of Avi Object + """ + def __init__(self, rsp): + super(ApiResponse, self).__init__() + for k, v in list(rsp.__dict__.items()): + setattr(self, k, v) + + def json(self): + """ + Extends the session default json interface to handle special errors + and raise Exceptions + returns the Avi object as a dictionary from rsp.text + """ + if self.status_code in (200, 201): + if not self.text: + # In cases like status_code == 201 the response text could be + # empty string. + return None + return super(ApiResponse, self).json() + elif self.status_code == 204: + # No response needed; e.g., delete operation + return None + elif self.status_code == 404: + raise ObjectNotFound('HTTP Error: %s Error Msg %s' % ( + self.status_code, self.text), self) + elif self.status_code >= 500: + raise AviServerError('HTTP Error: %s Error Msg %s' % ( + self.status_code, self.text), self) + else: + raise APIError('HTTP Error: %s Error Msg %s' % ( + self.status_code, self.text), self) + + def count(self): + """ + return the number of objects in the collection response. If it is not + a collection response then it would simply return 1. + """ + obj = self.json() + if 'count' in obj: + # this was a resposne to collection + return obj['count'] + return 1 + + @staticmethod + def to_avi_response(resp): + if type(resp) == Response: + return ApiResponse(resp) + return resp + + +class AviCredentials(object): + controller = '' + username = '' + password = '' + api_version = '16.4.4' + tenant = None + tenant_uuid = None + token = None + port = None + timeout = 300 + session_id = None + csrftoken = None + + def __init__(self, **kwargs): + for k, v in kwargs.items(): + setattr(self, k, v) + + def update_from_ansible_module(self, m): + """ + :param m: ansible module + :return: + """ + if m.params.get('avi_credentials'): + for k, v in m.params['avi_credentials'].items(): + if hasattr(self, k): + setattr(self, k, v) + if m.params['controller']: + self.controller = m.params['controller'] + if m.params['username']: + self.username = m.params['username'] + if m.params['password']: + self.password = m.params['password'] + if (m.params['api_version'] and + (m.params['api_version'] != '16.4.4')): + self.api_version = m.params['api_version'] + if m.params['tenant']: + self.tenant = m.params['tenant'] + if m.params['tenant_uuid']: + self.tenant_uuid = m.params['tenant_uuid'] + if m.params.get('session_id'): + self.session_id = m.params['session_id'] + if m.params.get('csrftoken'): + self.csrftoken = m.params['csrftoken'] + + def __str__(self): + return 'controller %s user %s api %s tenant %s' % ( + self.controller, self.username, self.api_version, self.tenant) + + +class ApiSession(Session): + """ + Extends the Request library's session object to provide helper + utilities to work with Avi Controller like authentication, api massaging + etc. + """ + + # This keeps track of the process which created the cache. + # At anytime the pid of the process changes then it would create + # a new cache for that process. + AVI_SLUG = 'Slug' + SESSION_CACHE_EXPIRY = 20 * 60 + SHARED_USER_HDRS = ['X-CSRFToken', 'Session-Id', 'Referer', 'Content-Type'] + MAX_API_RETRIES = 3 + + def __init__(self, controller_ip=None, username=None, password=None, + token=None, tenant=None, tenant_uuid=None, verify=False, + port=None, timeout=60, api_version=None, + retry_conxn_errors=True, data_log=False, + avi_credentials=None, session_id=None, csrftoken=None, + lazy_authentication=False, max_api_retries=None): + """ + ApiSession takes ownership of avi_credentials and may update the + information inside it. + + Initialize new session object with authenticated token from login api. + It also keeps a cache of user sessions that are cleaned up if inactive + for more than 20 mins. + + Notes: + 01. If mode is https and port is none or 443, we don't embed the + port in the prefix. The prefix would be 'https://ip'. If port + is a non-default value then we concatenate https://ip:port + in the prefix. + 02. If mode is http and the port is none or 80, we don't embed the + port in the prefix. The prefix would be 'http://ip'. If port is + a non-default value, then we concatenate http://ip:port in + the prefix. + """ + super(ApiSession, self).__init__() + if not avi_credentials: + tenant = tenant if tenant else "admin" + self.avi_credentials = AviCredentials( + controller=controller_ip, username=username, password=password, + api_version=api_version, tenant=tenant, tenant_uuid=tenant_uuid, + token=token, port=port, timeout=timeout, + session_id=session_id, csrftoken=csrftoken) + else: + self.avi_credentials = avi_credentials + self.headers = {} + self.verify = verify + self.retry_conxn_errors = retry_conxn_errors + self.remote_api_version = {} + self.session_cookie_name = '' + self.user_hdrs = {} + self.data_log = data_log + self.num_session_retries = 0 + self.retry_wait_time = 0 + self.max_session_retries = ( + self.MAX_API_RETRIES if max_api_retries is None + else int(max_api_retries)) + # Refer Notes 01 and 02 + k_port = port if port else 443 + if self.avi_credentials.controller.startswith('http'): + k_port = 80 if not self.avi_credentials.port else k_port + if self.avi_credentials.port is None or self.avi_credentials.port\ + == 80: + self.prefix = self.avi_credentials.controller + else: + self.prefix = '{x}:{y}'.format( + x=self.avi_credentials.controller, + y=self.avi_credentials.port) + else: + if port is None or port == 443: + self.prefix = 'https://{x}'.format( + x=self.avi_credentials.controller) + else: + self.prefix = 'https://{x}:{y}'.format( + x=self.avi_credentials.controller, + y=self.avi_credentials.port) + self.timeout = timeout + self.key = '%s:%s:%s' % (self.avi_credentials.controller, + self.avi_credentials.username, k_port) + # Added api token and session id to sessionDict for handle single + # session + if self.avi_credentials.csrftoken: + sessionDict[self.key] = { + 'api': self, + "csrftoken": self.avi_credentials.csrftoken, + "session_id": self.avi_credentials.session_id, + "last_used": datetime.utcnow() + } + elif lazy_authentication: + sessionDict.get(self.key, {}).update( + {'api': self, "last_used": datetime.utcnow()}) + else: + self.authenticate_session() + + self.num_session_retries = 0 + self.pid = os.getpid() + ApiSession._clean_inactive_sessions() + return + + @property + def controller_ip(self): + return self.avi_credentials.controller + + @controller_ip.setter + def controller_ip(self, controller_ip): + self.avi_credentials.controller = controller_ip + + @property + def username(self): + return self.avi_credentials.username + + @property + def connected(self): + return sessionDict.get(self.key, {}).get('connected', False) + + @username.setter + def username(self, username): + self.avi_credentials.username = username + + @property + def password(self): + return self.avi_credentials.password + + @password.setter + def password(self, password): + self.avi_credentials.password = password + + @property + def keystone_token(self): + return sessionDict.get(self.key, {}).get('csrftoken', None) + + @keystone_token.setter + def keystone_token(self, token): + sessionDict[self.key]['csrftoken'] = token + + @property + def tenant_uuid(self): + self.avi_credentials.tenant_uuid + + @tenant_uuid.setter + def tenant_uuid(self, tenant_uuid): + self.avi_credentials.tenant_uuid = tenant_uuid + + @property + def tenant(self): + return self.avi_credentials.tenant + + @tenant.setter + def tenant(self, tenant): + if tenant: + self.avi_credentials.tenant = tenant + else: + self.avi_credentials.tenant = 'admin' + + @property + def port(self): + self.avi_credentials.port + + @port.setter + def port(self, port): + self.avi_credentials.port = port + + @property + def api_version(self): + return self.avi_credentials.api_version + + @api_version.setter + def api_version(self, api_version): + self.avi_credentials.api_version = api_version + + @property + def session_id(self): + return sessionDict[self.key]['session_id'] + + def get_context(self): + return { + 'session_id': sessionDict[self.key]['session_id'], + 'csrftoken': sessionDict[self.key]['csrftoken'] + } + + @staticmethod + def clear_cached_sessions(): + global sessionDict + sessionDict = {} + + @staticmethod + def get_session( + controller_ip=None, username=None, password=None, token=None, tenant=None, + tenant_uuid=None, verify=False, port=None, timeout=60, + retry_conxn_errors=True, api_version=None, data_log=False, + avi_credentials=None, session_id=None, csrftoken=None, + lazy_authentication=False, max_api_retries=None): + """ + returns the session object for same user and tenant + calls init if session dose not exist and adds it to session cache + :param controller_ip: controller IP address + :param username: + :param password: + :param token: Token to use; example, a valid keystone token + :param tenant: Name of the tenant on Avi Controller + :param tenant_uuid: Don't specify tenant when using tenant_id + :param port: Rest-API may use a different port other than 443 + :param timeout: timeout for API calls; Default value is 60 seconds + :param retry_conxn_errors: retry on connection errors + :param api_version: Controller API version + """ + if not avi_credentials: + tenant = tenant if tenant else "admin" + avi_credentials = AviCredentials( + controller=controller_ip, username=username, password=password, + api_version=api_version, tenant=tenant, tenant_uuid=tenant_uuid, + token=token, port=port, timeout=timeout, + session_id=session_id, csrftoken=csrftoken) + + k_port = avi_credentials.port if avi_credentials.port else 443 + if avi_credentials.controller.startswith('http'): + k_port = 80 if not avi_credentials.port else k_port + key = '%s:%s:%s' % (avi_credentials.controller, + avi_credentials.username, k_port) + cached_session = sessionDict.get(key) + if cached_session: + user_session = cached_session['api'] + if not (user_session.avi_credentials.csrftoken or + lazy_authentication): + user_session.authenticate_session() + else: + user_session = ApiSession( + controller_ip, username, password, token=token, tenant=tenant, + tenant_uuid=tenant_uuid, verify=verify, port=port, + timeout=timeout, retry_conxn_errors=retry_conxn_errors, + api_version=api_version, data_log=data_log, + avi_credentials=avi_credentials, + lazy_authentication=lazy_authentication, + max_api_retries=max_api_retries) + ApiSession._clean_inactive_sessions() + return user_session + + def reset_session(self): + """ + resets and re-authenticates the current session. + """ + sessionDict[self.key]['connected'] = False + logger.info('resetting session for %s', self.key) + self.user_hdrs = {} + for k, v in self.headers.items(): + if k not in self.SHARED_USER_HDRS: + self.user_hdrs[k] = v + self.headers = {} + self.authenticate_session() + + def authenticate_session(self): + """ + Performs session authentication with Avi controller and stores + session cookies and sets header options like tenant. + """ + body = {"username": self.avi_credentials.username} + if self.avi_credentials.password: + body["password"] = self.avi_credentials.password + elif self.avi_credentials.token: + body["token"] = self.avi_credentials.token + else: + raise APIError("Neither user password or token provided") + logger.debug('authenticating user %s prefix %s', + self.avi_credentials.username, self.prefix) + self.cookies.clear() + err = None + try: + rsp = super(ApiSession, self).post( + self.prefix + "/login", body, timeout=self.timeout, verify=self.verify) + + if rsp.status_code == 200: + self.num_session_retries = 0 + self.remote_api_version = rsp.json().get('version', {}) + self.session_cookie_name = rsp.json().get('session_cookie_name', 'sessionid') + self.headers.update(self.user_hdrs) + if rsp.cookies and 'csrftoken' in rsp.cookies: + csrftoken = rsp.cookies['csrftoken'] + sessionDict[self.key] = { + 'csrftoken': csrftoken, + 'session_id': rsp.cookies[self.session_cookie_name], + 'last_used': datetime.utcnow(), + 'api': self, + 'connected': True + } + logger.debug("authentication success for user %s", + self.avi_credentials.username) + return + # Check for bad request and invalid credentials response code + elif rsp.status_code in [401, 403]: + logger.error('Status Code %s msg %s', rsp.status_code, rsp.text) + err = APIError('Status Code %s msg %s' % ( + rsp.status_code, rsp.text), rsp) + raise err + else: + logger.error("Error status code %s msg %s", rsp.status_code, + rsp.text) + err = APIError('Status Code %s msg %s' % ( + rsp.status_code, rsp.text), rsp) + except (RequestsConnectionError, SSLError) as e: + if not self.retry_conxn_errors: + raise + logger.warning('Connection error retrying %s', e) + err = e + # comes here only if there was either exception or login was not + # successful + if self.retry_wait_time: + time.sleep(self.retry_wait_time) + self.num_session_retries += 1 + if self.num_session_retries > self.max_session_retries: + self.num_session_retries = 0 + logger.error("giving up after %d retries connection failure %s", + self.max_session_retries, True) + ret_err = ( + err if err else APIError("giving up after %d retries connection failure %s" % + (self.max_session_retries, True))) + raise ret_err + self.authenticate_session() + return + + def _get_api_headers(self, tenant, tenant_uuid, timeout, headers, + api_version): + """ + returns the headers that are passed to the requests.Session api calls. + """ + api_hdrs = copy.deepcopy(self.headers) + api_hdrs.update({ + "Referer": self.prefix, + "Content-Type": "application/json" + }) + api_hdrs['timeout'] = str(timeout) + if self.key in sessionDict and 'csrftoken' in sessionDict.get(self.key): + api_hdrs['X-CSRFToken'] = sessionDict.get(self.key)['csrftoken'] + else: + self.authenticate_session() + api_hdrs['X-CSRFToken'] = sessionDict.get(self.key)['csrftoken'] + if api_version: + api_hdrs['X-Avi-Version'] = api_version + elif self.avi_credentials.api_version: + api_hdrs['X-Avi-Version'] = self.avi_credentials.api_version + if tenant: + tenant_uuid = None + elif tenant_uuid: + tenant = None + else: + tenant = self.avi_credentials.tenant + tenant_uuid = self.avi_credentials.tenant_uuid + if tenant_uuid: + api_hdrs.update({"X-Avi-Tenant-UUID": "%s" % tenant_uuid}) + api_hdrs.pop("X-Avi-Tenant", None) + elif tenant: + api_hdrs.update({"X-Avi-Tenant": "%s" % tenant}) + api_hdrs.pop("X-Avi-Tenant-UUID", None) + # Override any user headers that were passed by users. We don't know + # when the user had updated the user_hdrs + if self.user_hdrs: + api_hdrs.update(self.user_hdrs) + if headers: + # overwrite the headers passed via the API calls. + api_hdrs.update(headers) + return api_hdrs + + def _api(self, api_name, path, tenant, tenant_uuid, data=None, + headers=None, timeout=None, api_version=None, **kwargs): + """ + It calls the requests.Session APIs and handles session expiry + and other situations where session needs to be reset. + returns ApiResponse object + :param path: takes relative path to the AVI api. + :param tenant: overrides the tenant used during session creation + :param tenant_uuid: overrides the tenant or tenant_uuid during session + creation + :param timeout: timeout for API calls; Default value is 60 seconds + :param headers: dictionary of headers that override the session + headers. + """ + if self.pid != os.getpid(): + logger.info('pid %d change detected new %d. Closing session', + self.pid, os.getpid()) + self.close() + self.pid = os.getpid() + if timeout is None: + timeout = self.timeout + fullpath = self._get_api_path(path) + fn = getattr(super(ApiSession, self), api_name) + api_hdrs = self._get_api_headers(tenant, tenant_uuid, timeout, headers, + api_version) + connection_error = False + err = None + cookies = { + 'csrftoken': api_hdrs['X-CSRFToken'], + } + try: + if self.session_cookie_name: + cookies[self.session_cookie_name] = sessionDict[self.key]['session_id'] + except KeyError: + pass + try: + if (data is not None) and (type(data) == dict): + resp = fn(fullpath, data=json.dumps(data), headers=api_hdrs, + timeout=timeout, cookies=cookies, **kwargs) + else: + resp = fn(fullpath, data=data, headers=api_hdrs, + timeout=timeout, cookies=cookies, **kwargs) + except (RequestsConnectionError, SSLError) as e: + logger.warning('Connection error retrying %s', e) + if not self.retry_conxn_errors: + raise + connection_error = True + err = e + except Exception as e: + logger.error('Error in Requests library %s', e) + raise + if not connection_error: + logger.debug('path: %s http_method: %s hdrs: %s params: ' + '%s data: %s rsp: %s', fullpath, api_name.upper(), + api_hdrs, kwargs, data, + (resp.text if self.data_log else 'None')) + if connection_error or resp.status_code in (401, 419): + if connection_error: + try: + self.close() + except Exception: + # ignoring exception in cleanup path + pass + logger.warning('Connection failed, retrying.') + # Adding sleep before retrying + if self.retry_wait_time: + time.sleep(self.retry_wait_time) + else: + logger.info('received error %d %s so resetting connection', + resp.status_code, resp.text) + ApiSession.reset_session(self) + self.num_session_retries += 1 + if self.num_session_retries > self.max_session_retries: + # Added this such that any code which re-tries can succeed + # eventually. + self.num_session_retries = 0 + if not connection_error: + err = APIError('Status Code %s msg %s' % ( + resp.status_code, resp.text), resp) + logger.error( + "giving up after %d retries conn failure %s err %s", + self.max_session_retries, connection_error, err) + ret_err = ( + err if err else APIError("giving up after %d retries connection failure %s" % + (self.max_session_retries, True))) + raise ret_err + # should restore the updated_hdrs to one passed down + resp = self._api(api_name, path, tenant, tenant_uuid, data, + headers=headers, api_version=api_version, + timeout=timeout, **kwargs) + self.num_session_retries = 0 + + if resp.cookies and 'csrftoken' in resp.cookies: + csrftoken = resp.cookies['csrftoken'] + self.headers.update({"X-CSRFToken": csrftoken}) + self._update_session_last_used() + return ApiResponse.to_avi_response(resp) + + def get_controller_details(self): + result = { + "controller_ip": self.controller_ip, + "controller_api_version": self.remote_api_version + } + return result + + def get(self, path, tenant='', tenant_uuid='', timeout=None, params=None, + api_version=None, **kwargs): + """ + It extends the Session Library interface to add AVI API prefixes, + handle session exceptions related to authentication and update + the global user session cache. + :param path: takes relative path to the AVI api. + :param tenant: overrides the tenant used during session creation + :param tenant_uuid: overrides the tenant or tenant_uuid during session + creation + :param timeout: timeout for API calls; Default value is 60 seconds + :param params: dictionary of key value pairs to be sent as query + parameters + :param api_version: overrides x-avi-header in request header during + session creation + get method takes relative path to service and kwargs as per Session + class get method + returns session's response object + """ + return self._api('get', path, tenant, tenant_uuid, timeout=timeout, + params=params, api_version=api_version, **kwargs) + + def get_object_by_name(self, path, name, tenant='', tenant_uuid='', + timeout=None, params=None, api_version=None, + **kwargs): + """ + Helper function to access Avi REST Objects using object + type and name. It behaves like python dictionary interface where it + returns None when the object is not present in the AviController. + Internally, it transforms the request to api/path?name=... + :param path: relative path to service + :param name: name of the object + :param tenant: overrides the tenant used during session creation + :param tenant_uuid: overrides the tenant or tenant_uuid during session + creation + :param timeout: timeout for API calls; Default value is 60 seconds + :param params: dictionary of key value pairs to be sent as query + parameters + :param api_version: overrides x-avi-header in request header during + session creation + returns dictionary object if successful else None + """ + obj = None + if not params: + params = {} + params['name'] = name + resp = self.get(path, tenant=tenant, tenant_uuid=tenant_uuid, + timeout=timeout, + params=params, api_version=api_version, **kwargs) + if resp.status_code in (401, 419): + ApiSession.reset_session(self) + resp = self.get_object_by_name( + path, name, tenant, tenant_uuid, timeout=timeout, + params=params, **kwargs) + if resp.status_code > 499 or 'Invalid version' in resp.text: + logger.error('Error in get object by name for %s named %s. ' + 'Error: %s', path, name, resp.text) + raise AviServerError(resp.text, rsp=resp) + elif resp.status_code > 299: + return obj + try: + if 'results' in resp.json(): + obj = resp.json()['results'][0] + else: + # For apis returning single object eg. api/cluster + obj = resp.json() + except IndexError: + logger.warning('Warning: Object Not found for %s named %s', + path, name) + obj = None + self._update_session_last_used() + return obj + + def post(self, path, data=None, tenant='', tenant_uuid='', timeout=None, + force_uuid=None, params=None, api_version=None, **kwargs): + """ + It extends the Session Library interface to add AVI API prefixes, + handle session exceptions related to authentication and update + the global user session cache. + :param path: takes relative path to the AVI api.It is modified by + the library to conform to AVI Controller's REST API interface + :param data: dictionary of the data. Support for json string + is deprecated + :param tenant: overrides the tenant used during session creation + :param tenant_uuid: overrides the tenant or tenant_uuid during session + creation + :param timeout: timeout for API calls; Default value is 60 seconds + :param params: dictionary of key value pairs to be sent as query + parameters + :param api_version: overrides x-avi-header in request header during + session creation + returns session's response object + """ + if force_uuid is not None: + headers = kwargs.get('headers', {}) + headers[self.AVI_SLUG] = force_uuid + kwargs['headers'] = headers + return self._api('post', path, tenant, tenant_uuid, data=data, + timeout=timeout, params=params, + api_version=api_version, **kwargs) + + def put(self, path, data=None, tenant='', tenant_uuid='', + timeout=None, params=None, api_version=None, **kwargs): + """ + It extends the Session Library interface to add AVI API prefixes, + handle session exceptions related to authentication and update + the global user session cache. + :param path: takes relative path to the AVI api.It is modified by + the library to conform to AVI Controller's REST API interface + :param data: dictionary of the data. Support for json string + is deprecated + :param tenant: overrides the tenant used during session creation + :param tenant_uuid: overrides the tenant or tenant_uuid during session + creation + :param timeout: timeout for API calls; Default value is 60 seconds + :param params: dictionary of key value pairs to be sent as query + parameters + :param api_version: overrides x-avi-header in request header during + session creation + returns session's response object + """ + return self._api('put', path, tenant, tenant_uuid, data=data, + timeout=timeout, params=params, + api_version=api_version, **kwargs) + + def patch(self, path, data=None, tenant='', tenant_uuid='', + timeout=None, params=None, api_version=None, **kwargs): + """ + It extends the Session Library interface to add AVI API prefixes, + handle session exceptions related to authentication and update + the global user session cache. + :param path: takes relative path to the AVI api.It is modified by + the library to conform to AVI Controller's REST API interface + :param data: dictionary of the data. Support for json string + is deprecated + :param tenant: overrides the tenant used during session creation + :param tenant_uuid: overrides the tenant or tenant_uuid during session + creation + :param timeout: timeout for API calls; Default value is 60 seconds + :param params: dictionary of key value pairs to be sent as query + parameters + :param api_version: overrides x-avi-header in request header during + session creation + returns session's response object + """ + return self._api('patch', path, tenant, tenant_uuid, data=data, + timeout=timeout, params=params, + api_version=api_version, **kwargs) + + def put_by_name(self, path, name, data=None, tenant='', + tenant_uuid='', timeout=None, params=None, + api_version=None, **kwargs): + """ + Helper function to perform HTTP PUT on Avi REST Objects using object + type and name. + Internally, it transforms the request to api/path?name=... + :param path: relative path to service + :param name: name of the object + :param data: dictionary of the data. Support for json string + is deprecated + :param tenant: overrides the tenant used during session creation + :param tenant_uuid: overrides the tenant or tenant_uuid during session + creation + :param timeout: timeout for API calls; Default value is 60 seconds + :param params: dictionary of key value pairs to be sent as query + parameters + :param api_version: overrides x-avi-header in request header during + session creation + returns session's response object + """ + uuid = self._get_uuid_by_name( + path, name, tenant, tenant_uuid, api_version=api_version) + path = '%s/%s' % (path, uuid) + return self.put(path, data, tenant, tenant_uuid, timeout=timeout, + params=params, api_version=api_version, **kwargs) + + def delete(self, path, tenant='', tenant_uuid='', timeout=None, params=None, + data=None, api_version=None, **kwargs): + """ + It extends the Session Library interface to add AVI API prefixes, + handle session exceptions related to authentication and update + the global user session cache. + :param path: takes relative path to the AVI api.It is modified by + the library to conform to AVI Controller's REST API interface + :param tenant: overrides the tenant used during session creation + :param tenant_uuid: overrides the tenant or tenant_uuid during session + creation + :param timeout: timeout for API calls; Default value is 60 seconds + :param params: dictionary of key value pairs to be sent as query + parameters + :param data: dictionary of the data. Support for json string + is deprecated + :param api_version: overrides x-avi-header in request header during + session creation + returns session's response object + """ + return self._api('delete', path, tenant, tenant_uuid, data=data, + timeout=timeout, params=params, + api_version=api_version, **kwargs) + + def delete_by_name(self, path, name, tenant='', tenant_uuid='', + timeout=None, params=None, api_version=None, **kwargs): + """ + Helper function to perform HTTP DELETE on Avi REST Objects using object + type and name.Internally, it transforms the request to + api/path?name=... + :param path: relative path to service + :param name: name of the object + :param tenant: overrides the tenant used during session creation + :param tenant_uuid: overrides the tenant or tenant_uuid during session + creation + :param timeout: timeout for API calls; Default value is 60 seconds + :param params: dictionary of key value pairs to be sent as query + parameters + :param api_version: overrides x-avi-header in request header during + session creation + returns session's response object + """ + uuid = self._get_uuid_by_name(path, name, tenant, tenant_uuid, + api_version=api_version) + if not uuid: + raise ObjectNotFound("%s/?name=%s" % (path, name)) + path = '%s/%s' % (path, uuid) + return self.delete(path, tenant, tenant_uuid, timeout=timeout, + params=params, api_version=api_version, **kwargs) + + def get_obj_ref(self, obj): + """returns reference url from dict object""" + if not obj: + return None + if isinstance(obj, Response): + obj = json.loads(obj.text) + if obj.get(0, None): + return obj[0]['url'] + elif obj.get('url', None): + return obj['url'] + elif obj.get('results', None): + return obj['results'][0]['url'] + else: + return None + + def get_obj_uuid(self, obj): + """returns uuid from dict object""" + if not obj: + raise ObjectNotFound('Object %s Not found' % (obj)) + if isinstance(obj, Response): + obj = json.loads(obj.text) + if obj.get(0, None): + return obj[0]['uuid'] + elif obj.get('uuid', None): + return obj['uuid'] + elif obj.get('results', None): + return obj['results'][0]['uuid'] + else: + return None + + def _get_api_path(self, path, uuid=None): + """ + This function returns the full url from relative path and uuid. + """ + if path == 'logout': + return self.prefix + '/' + path + elif uuid: + return self.prefix + '/api/' + path + '/' + uuid + else: + return self.prefix + '/api/' + path + + def _get_uuid_by_name(self, path, name, tenant='admin', + tenant_uuid='', api_version=None): + """gets object by name and service path and returns uuid""" + resp = self.get_object_by_name( + path, name, tenant, tenant_uuid, api_version=api_version) + if not resp: + raise ObjectNotFound("%s/%s" % (path, name)) + return self.get_obj_uuid(resp) + + def _update_session_last_used(self): + if self.key in sessionDict: + sessionDict[self.key]["last_used"] = datetime.utcnow() + + @staticmethod + def _clean_inactive_sessions(): + """Removes sessions which are inactive more than 20 min""" + session_cache = sessionDict + logger.debug("cleaning inactive sessions in pid %d num elem %d", + os.getpid(), len(session_cache)) + keys_to_delete = [] + for key, session in list(session_cache.items()): + tdiff = avi_timedelta(datetime.utcnow() - session["last_used"]) + if tdiff < ApiSession.SESSION_CACHE_EXPIRY: + continue + keys_to_delete.append(key) + for key in keys_to_delete: + del session_cache[key] + logger.debug("Removed session for : %s", key) + + def delete_session(self): + """ Removes the session for cleanup""" + logger.debug("Removed session for : %s", self.key) + sessionDict.pop(self.key, None) + return +# End of file diff --git a/lib/ansible/modules/network/avi/avi_actiongroupconfig.py b/lib/ansible/modules/network/avi/avi_actiongroupconfig.py index 363f614f540..44017e63c38 100644 --- a/lib/ansible/modules/network/avi/avi_actiongroupconfig.py +++ b/lib/ansible/modules/network/avi/avi_actiongroupconfig.py @@ -114,7 +114,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -144,7 +144,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'actiongroupconfig', set([])) diff --git a/lib/ansible/modules/network/avi/avi_alertconfig.py b/lib/ansible/modules/network/avi/avi_alertconfig.py index 0b26e960185..6a4fe00aa2b 100644 --- a/lib/ansible/modules/network/avi/avi_alertconfig.py +++ b/lib/ansible/modules/network/avi/avi_alertconfig.py @@ -74,7 +74,6 @@ options: - The original event triggering the alert remains in the event's log. - Allowed values are 1-31536000. - Default value when not specified in API or module is interpreted by Avi Controller as 86400. - - Units(SEC). name: description: - Name of the alert configuration. @@ -86,39 +85,43 @@ options: description: - The object type to which the alert config is associated with. - Valid object types are - virtual service, pool, service engine. - - Enum options - VIRTUALSERVICE, POOL, HEALTHMONITOR, NETWORKPROFILE, APPLICATIONPROFILE, HTTPPOLICYSET, DNSPOLICY, IPADDRGROUP, STRINGGROUP, - - SSLPROFILE, SSLKEYANDCERTIFICATE, NETWORKSECURITYPOLICY, APPLICATIONPERSISTENCEPROFILE, ANALYTICSPROFILE, VSDATASCRIPTSET, TENANT, PKIPROFILE, - - AUTHPROFILE, CLOUD, SERVERAUTOSCALEPOLICY, AUTOSCALELAUNCHCONFIG, MICROSERVICEGROUP, IPAMPROFILE, HARDWARESECURITYMODULEGROUP, POOLGROUP, - - PRIORITYLABELS, POOLGROUPDEPLOYMENTPOLICY, GSLBSERVICE, GSLBSERVICERUNTIME, SCHEDULER, GSLBGEODBPROFILE, GSLBAPPLICATIONPERSISTENCEPROFILE, - - TRAFFICCLONEPROFILE, VSVIP, WAFPOLICY, WAFPROFILE, ERRORPAGEPROFILE, ERRORPAGEBODY, L4POLICYSET, SERVICEENGINE, DEBUGSERVICEENGINE, - - DEBUGCONTROLLER, DEBUGVIRTUALSERVICE, SERVICEENGINEGROUP, SEPROPERTIES, NETWORK, CONTROLLERNODE, CONTROLLERPROPERTIES, SYSTEMCONFIGURATION, - - VRFCONTEXT, USER, ALERTCONFIG, ALERTSYSLOGCONFIG, ALERTEMAILCONFIG, ALERTTYPECONFIG, APPLICATION, ROLE, CLOUDPROPERTIES, SNMPTRAPPROFILE, - - ACTIONGROUPPROFILE, MICROSERVICE, ALERTPARAMS, ACTIONGROUPCONFIG, CLOUDCONNECTORUSER, GSLB, GSLBDNSUPDATE, GSLBSITEOPS, GLBMGRWARMSTART, - - IPAMDNSRECORD, GSLBDNSGSSTATUS, GSLBDNSGEOFILEOPS, GSLBDNSGEOUPDATE, GSLBDNSGEOCLUSTEROPS, GSLBDNSCLEANUP, GSLBSITEOPSRESYNC, TCPSTATRUNTIME, - - UDPSTATRUNTIME, IPSTATRUNTIME, ARPSTATRUNTIME, MBSTATRUNTIME, IPSTKQSTATSRUNTIME, MALLOCSTATRUNTIME, SHMALLOCSTATRUNTIME, CPUUSAGERUNTIME, - - L7GLOBALSTATSRUNTIME, L7VIRTUALSERVICESTATSRUNTIME, SEAGENTVNICDBRUNTIME, SEAGENTGRAPHDBRUNTIME, SEAGENTSTATERUNTIME, INTERFACERUNTIME, - - ARPTABLERUNTIME, DISPATCHERSTATRUNTIME, DISPATCHERSTATCLEARRUNTIME, DISPATCHERTABLEDUMPRUNTIME, DISPATCHERREMOTETIMERLISTDUMPRUNTIME, - - METRICSAGENTMESSAGE, HEALTHMONITORSTATRUNTIME, METRICSENTITYRUNTIME, PERSISTENCEINTERNAL, HTTPPOLICYSETINTERNAL, DNSPOLICYINTERNAL, - - CONNECTIONDUMPRUNTIME, SHAREDDBSTATS, SHAREDDBSTATSCLEAR, ICMPSTATRUNTIME, ROUTETABLERUNTIME, VIRTUALMACHINE, POOLSERVER, SEVSLIST, - - MEMINFORUNTIME, RTERINGSTATRUNTIME, ALGOSTATRUNTIME, HEALTHMONITORRUNTIME, CPUSTATRUNTIME, SEVM, HOST, PORTGROUP, CLUSTER, DATACENTER, VCENTER, - - HTTPPOLICYSETSTATS, DNSPOLICYSTATS, METRICSSESTATS, RATELIMITERSTATRUNTIME, NETWORKSECURITYPOLICYSTATS, TCPCONNRUNTIME, POOLSTATS, - - CONNPOOLINTERNAL, CONNPOOLSTATS, VSHASHSHOWRUNTIME, SELOGSTATSRUNTIME, NETWORKSECURITYPOLICYDETAIL, LICENSERUNTIME, SERVERRUNTIME, - - METRICSRUNTIMESUMMARY, METRICSRUNTIMEDETAIL, DISPATCHERSEHMPROBETEMPDISABLERUNTIME, POOLDEBUG, VSLOGMGRMAP, SERUMINSERTIONSTATS, HTTPCACHE, - - HTTPCACHESTATS, SEDOSSTATRUNTIME, VSDOSSTATRUNTIME, SERVERUPDATEREQ, VSSCALEOUTLIST, SEMEMDISTRUNTIME, TCPCONNRUNTIMEDETAIL, SEUPGRADESTATUS, - - SEUPGRADEPREVIEW, SEFAULTINJECTEXHAUSTM, SEFAULTINJECTEXHAUSTMCL, SEFAULTINJECTEXHAUSTMCLSMALL, SEFAULTINJECTEXHAUSTCONN, SEHEADLESSONLINEREQ, - - SEUPGRADE, SEUPGRADESTATUSDETAIL, SERESERVEDVS, SERESERVEDVSCLEAR, VSCANDIDATESEHOSTLIST, SEGROUPUPGRADE, REBALANCE, SEGROUPREBALANCE, - - SEAUTHSTATSRUNTIME, AUTOSCALESTATE, VIRTUALSERVICEAUTHSTATS, NETWORKSECURITYPOLICYDOS, KEYVALINTERNAL, KEYVALSUMMARYINTERNAL, + - Enum options - VIRTUALSERVICE, POOL, HEALTHMONITOR, NETWORKPROFILE, APPLICATIONPROFILE, HTTPPOLICYSET, DNSPOLICY, SECURITYPOLICY, IPADDRGROUP, + - STRINGGROUP, SSLPROFILE, SSLKEYANDCERTIFICATE, NETWORKSECURITYPOLICY, APPLICATIONPERSISTENCEPROFILE, ANALYTICSPROFILE, VSDATASCRIPTSET, TENANT, + - PKIPROFILE, AUTHPROFILE, CLOUD, SERVERAUTOSCALEPOLICY, AUTOSCALELAUNCHCONFIG, MICROSERVICEGROUP, IPAMPROFILE, HARDWARESECURITYMODULEGROUP, + - POOLGROUP, PRIORITYLABELS, POOLGROUPDEPLOYMENTPOLICY, GSLBSERVICE, GSLBSERVICERUNTIME, SCHEDULER, GSLBGEODBPROFILE, + - GSLBAPPLICATIONPERSISTENCEPROFILE, TRAFFICCLONEPROFILE, VSVIP, WAFPOLICY, WAFPROFILE, ERRORPAGEPROFILE, ERRORPAGEBODY, L4POLICYSET, + - GSLBSERVICERUNTIMEBATCH, WAFPOLICYPSMGROUP, PINGACCESSAGENT, SERVICEENGINEPOLICY, NATPOLICY, SSOPOLICY, PROTOCOLPARSER, SERVICEENGINE, + - DEBUGSERVICEENGINE, DEBUGCONTROLLER, DEBUGVIRTUALSERVICE, SERVICEENGINEGROUP, SEPROPERTIES, NETWORK, CONTROLLERNODE, CONTROLLERPROPERTIES, + - SYSTEMCONFIGURATION, VRFCONTEXT, USER, ALERTCONFIG, ALERTSYSLOGCONFIG, ALERTEMAILCONFIG, ALERTTYPECONFIG, APPLICATION, ROLE, CLOUDPROPERTIES, + - SNMPTRAPPROFILE, ACTIONGROUPPROFILE, MICROSERVICE, ALERTPARAMS, ACTIONGROUPCONFIG, CLOUDCONNECTORUSER, GSLB, GSLBDNSUPDATE, GSLBSITEOPS, + - GLBMGRWARMSTART, IPAMDNSRECORD, GSLBDNSGSSTATUS, GSLBDNSGEOFILEOPS, GSLBDNSGEOUPDATE, GSLBDNSGEOCLUSTEROPS, GSLBDNSCLEANUP, GSLBSITEOPSRESYNC, + - IPAMDNSPROVIDERPROFILE, TCPSTATRUNTIME, UDPSTATRUNTIME, IPSTATRUNTIME, ARPSTATRUNTIME, MBSTATRUNTIME, IPSTKQSTATSRUNTIME, MALLOCSTATRUNTIME, + - SHMALLOCSTATRUNTIME, CPUUSAGERUNTIME, L7GLOBALSTATSRUNTIME, L7VIRTUALSERVICESTATSRUNTIME, SEAGENTVNICDBRUNTIME, SEAGENTGRAPHDBRUNTIME, + - SEAGENTSTATERUNTIME, INTERFACERUNTIME, ARPTABLERUNTIME, DISPATCHERSTATRUNTIME, DISPATCHERSTATCLEARRUNTIME, DISPATCHERTABLEDUMPRUNTIME, + - DISPATCHERREMOTETIMERLISTDUMPRUNTIME, METRICSAGENTMESSAGE, HEALTHMONITORSTATRUNTIME, METRICSENTITYRUNTIME, PERSISTENCEINTERNAL, + - HTTPPOLICYSETINTERNAL, DNSPOLICYINTERNAL, CONNECTIONDUMPRUNTIME, SHAREDDBSTATS, SHAREDDBSTATSCLEAR, ICMPSTATRUNTIME, ROUTETABLERUNTIME, + - VIRTUALMACHINE, POOLSERVER, SEVSLIST, MEMINFORUNTIME, RTERINGSTATRUNTIME, ALGOSTATRUNTIME, HEALTHMONITORRUNTIME, CPUSTATRUNTIME, SEVM, HOST, + - PORTGROUP, CLUSTER, DATACENTER, VCENTER, HTTPPOLICYSETSTATS, DNSPOLICYSTATS, METRICSSESTATS, RATELIMITERSTATRUNTIME, NETWORKSECURITYPOLICYSTATS, + - TCPCONNRUNTIME, POOLSTATS, CONNPOOLINTERNAL, CONNPOOLSTATS, VSHASHSHOWRUNTIME, SELOGSTATSRUNTIME, NETWORKSECURITYPOLICYDETAIL, LICENSERUNTIME, + - SERVERRUNTIME, METRICSRUNTIMESUMMARY, METRICSRUNTIMEDETAIL, DISPATCHERSEHMPROBETEMPDISABLERUNTIME, POOLDEBUG, VSLOGMGRMAP, SERUMINSERTIONSTATS, + - HTTPCACHE, HTTPCACHESTATS, SEDOSSTATRUNTIME, VSDOSSTATRUNTIME, SERVERUPDATEREQ, VSSCALEOUTLIST, SEMEMDISTRUNTIME, TCPCONNRUNTIMEDETAIL, + - SEUPGRADESTATUS, SEUPGRADEPREVIEW, SEFAULTINJECTEXHAUSTM, SEFAULTINJECTEXHAUSTMCL, SEFAULTINJECTEXHAUSTMCLSMALL, SEFAULTINJECTEXHAUSTCONN, + - SEHEADLESSONLINEREQ, SEUPGRADE, SEUPGRADESTATUSDETAIL, SERESERVEDVS, SERESERVEDVSCLEAR, VSCANDIDATESEHOSTLIST, SEGROUPUPGRADE, REBALANCE, + - SEGROUPREBALANCE, SEAUTHSTATSRUNTIME, AUTOSCALESTATE, VIRTUALSERVICEAUTHSTATS, NETWORKSECURITYPOLICYDOS, KEYVALINTERNAL, KEYVALSUMMARYINTERNAL, - SERVERSTATEUPDATEINFO, CLTRACKINTERNAL, CLTRACKSUMMARYINTERNAL, MICROSERVICERUNTIME, SEMICROSERVICE, VIRTUALSERVICEANALYSIS, CLIENTINTERNAL, - CLIENTSUMMARYINTERNAL, MICROSERVICEGROUPRUNTIME, BGPRUNTIME, REQUESTQUEUERUNTIME, MIGRATEALL, MIGRATEALLSTATUSSUMMARY, MIGRATEALLSTATUSDETAIL, - INTERFACESUMMARYRUNTIME, INTERFACELACPRUNTIME, DNSTABLE, GSLBSERVICEDETAIL, GSLBSERVICEINTERNAL, GSLBSERVICEHMONSTAT, SETROLESREQUEST, - TRAFFICCLONERUNTIME, GEOLOCATIONINFO, SEVSHBSTATRUNTIME, GEODBINTERNAL, GSLBSITEINTERNAL, WAFSTATS, USERDEFINEDDATASCRIPTCOUNTERS, LLDPRUNTIME, - - VSESSHARINGPOOL, SEVSSPLACEMENT, L4POLICYSETSTATS, L4POLICYSETINTERNAL, SERESOURCEPROTO, SECONSUMERPROTO, SECREATEPENDINGPROTO, PLACEMENTSTATS, - - SEVIPPROTO, RMVRFPROTO, VCENTERMAP, VIMGRVCENTERRUNTIME, INTERESTEDVMS, INTERESTEDHOSTS, VCENTERSUPPORTEDCOUNTERS, ENTITYCOUNTERS, - - TRANSACTIONSTATS, SEVMCREATEPROGRESS, PLACEMENTSTATUS, VISUBFOLDERS, VIDATASTORE, VIHOSTRESOURCES, CLOUDCONNECTOR, VINETWORKSUBNETVMS, - - VIDATASTORECONTENTS, VIMGRVCENTERCLOUDRUNTIME, VIVCENTERPORTGROUPS, VIVCENTERDATACENTERS, VIMGRHOSTRUNTIME, PLACEMENTGLOBALS, APICCONFIGURATION, - - CIFTABLE, APICTRANSACTION, VIRTUALSERVICESTATEDBCACHESUMMARY, POOLSTATEDBCACHESUMMARY, SERVERSTATEDBCACHESUMMARY, APICAGENTINTERNAL, - - APICTRANSACTIONFLAP, APICGRAPHINSTANCES, APICEPGS, APICEPGEPS, APICDEVICEPKGVER, APICTENANTS, APICVMMDOMAINS, NSXCONFIGURATION, NSXSGTABLE, - - NSXAGENTINTERNAL, NSXSGINFO, NSXSGIPS, NSXAGENTINTERNALCLI, MAXOBJECTS. + - VSESSHARINGPOOL, NDTABLERUNTIME, IP6STATRUNTIME, ICMP6STATRUNTIME, SEVSSPLACEMENT, L4POLICYSETSTATS, L4POLICYSETINTERNAL, BGPDEBUGINFO, SHARD, + - CPUSTATRUNTIMEDETAIL, SEASSERTSTATRUNTIME, SEFAULTINJECTINFRA, SEAGENTASSERTSTATRUNTIME, SEDATASTORESTATUS, DIFFQUEUESTATUS, IP6ROUTETABLERUNTIME, + - SECURITYMGRSTATE, VIRTUALSERVICESESCALEOUTSTATUS, SHARDSERVERSTATUS, SEAGENTSHARDCLIENTRESOURCEMAP, SEAGENTCONSISTENTHASH, SEAGENTVNICDBHISTORY, + - SEAGENTSHARDCLIENTAPPMAP, SEAGENTSHARDCLIENTEVENTHISTORY, SENATSTATRUNTIME, SENATFLOWRUNTIME, SERESOURCEPROTO, SECONSUMERPROTO, + - SECREATEPENDINGPROTO, PLACEMENTSTATS, SEVIPPROTO, RMVRFPROTO, VCENTERMAP, VIMGRVCENTERRUNTIME, INTERESTEDVMS, INTERESTEDHOSTS, + - VCENTERSUPPORTEDCOUNTERS, ENTITYCOUNTERS, TRANSACTIONSTATS, SEVMCREATEPROGRESS, PLACEMENTSTATUS, VISUBFOLDERS, VIDATASTORE, VIHOSTRESOURCES, + - CLOUDCONNECTOR, VINETWORKSUBNETVMS, VIDATASTORECONTENTS, VIMGRVCENTERCLOUDRUNTIME, VIVCENTERPORTGROUPS, VIVCENTERDATACENTERS, VIMGRHOSTRUNTIME, + - PLACEMENTGLOBALS, APICCONFIGURATION, CIFTABLE, APICTRANSACTION, VIRTUALSERVICESTATEDBCACHESUMMARY, POOLSTATEDBCACHESUMMARY, + - SERVERSTATEDBCACHESUMMARY, APICAGENTINTERNAL, APICTRANSACTIONFLAP, APICGRAPHINSTANCES, APICEPGS, APICEPGEPS, APICDEVICEPKGVER, APICTENANTS, + - APICVMMDOMAINS, NSXCONFIGURATION, NSXSGTABLE, NSXAGENTINTERNAL, NSXSGINFO, NSXSGIPS, NSXAGENTINTERNALCLI, MAXOBJECTS. recommendation: description: - Recommendation of alertconfig. @@ -127,7 +130,6 @@ options: - Only if the number of events is reached or exceeded within the time window will an alert be generated. - Allowed values are 1-31536000. - Default value when not specified in API or module is interpreted by Avi Controller as 300. - - Units(SEC). source: description: - Signifies system events or the type of client logsused in this alert configuration. @@ -149,7 +151,6 @@ options: - Alerts are suppressed (throttled) for this duration of time since the last alert was raised for this alert config. - Allowed values are 0-31536000. - Default value when not specified in API or module is interpreted by Avi Controller as 600. - - Units(SEC). url: description: - Avi controller URL of the object. @@ -180,7 +181,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -217,7 +218,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'alertconfig', set([])) diff --git a/lib/ansible/modules/network/avi/avi_alertemailconfig.py b/lib/ansible/modules/network/avi/avi_alertemailconfig.py index 8964213d7dd..41a091f5b31 100644 --- a/lib/ansible/modules/network/avi/avi_alertemailconfig.py +++ b/lib/ansible/modules/network/avi/avi_alertemailconfig.py @@ -88,7 +88,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -113,7 +113,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'alertemailconfig', set([])) diff --git a/lib/ansible/modules/network/avi/avi_alertscriptconfig.py b/lib/ansible/modules/network/avi/avi_alertscriptconfig.py index 556d1aafe26..94083b9fc4e 100644 --- a/lib/ansible/modules/network/avi/avi_alertscriptconfig.py +++ b/lib/ansible/modules/network/avi/avi_alertscriptconfig.py @@ -83,7 +83,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -106,7 +106,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'alertscriptconfig', set([])) diff --git a/lib/ansible/modules/network/avi/avi_alertsyslogconfig.py b/lib/ansible/modules/network/avi/avi_alertsyslogconfig.py index f446d1b1a0b..4cb52f9fabd 100644 --- a/lib/ansible/modules/network/avi/avi_alertsyslogconfig.py +++ b/lib/ansible/modules/network/avi/avi_alertsyslogconfig.py @@ -88,7 +88,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -112,7 +112,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'alertsyslogconfig', set([])) diff --git a/lib/ansible/modules/network/avi/avi_analyticsprofile.py b/lib/ansible/modules/network/avi/avi_analyticsprofile.py index c0ee585db65..ae1a525bef6 100644 --- a/lib/ansible/modules/network/avi/avi_analyticsprofile.py +++ b/lib/ansible/modules/network/avi/avi_analyticsprofile.py @@ -49,7 +49,6 @@ options: - Greater than this number and the client's request is considered frustrated. - Allowed values are 1-30000. - Default value when not specified in API or module is interpreted by Avi Controller as 500. - - Units(MILLISECONDS). apdex_response_tolerated_factor: description: - Client tolerated response latency factor. @@ -61,7 +60,6 @@ options: - Satisfactory client to avi round trip time(rtt). - Allowed values are 1-2000. - Default value when not specified in API or module is interpreted by Avi Controller as 250. - - Units(MILLISECONDS). apdex_rtt_tolerated_factor: description: - Tolerated client to avi round trip time(rtt) factor. @@ -76,7 +74,6 @@ options: - A pageload includes the time for dns lookup, download of all http objects, and page render time. - Allowed values are 1-30000. - Default value when not specified in API or module is interpreted by Avi Controller as 5000. - - Units(MILLISECONDS). apdex_rum_tolerated_factor: description: - Virtual service threshold factor for tolerated page load time (plt) as multiple of apdex_rum_threshold. @@ -89,7 +86,6 @@ options: - Greater than this number and the server response is considered frustrated. - Allowed values are 1-30000. - Default value when not specified in API or module is interpreted by Avi Controller as 400. - - Units(MILLISECONDS). apdex_server_response_tolerated_factor: description: - Server tolerated response latency factor. @@ -101,7 +97,6 @@ options: - Satisfactory client to avi round trip time(rtt). - Allowed values are 1-2000. - Default value when not specified in API or module is interpreted by Avi Controller as 125. - - Units(MILLISECONDS). apdex_server_rtt_tolerated_factor: description: - Tolerated client to avi round trip time(rtt) factor. @@ -121,52 +116,52 @@ options: - A connection between client and avi is considered lossy when more than this percentage of out of order packets are received. - Allowed values are 1-100. - Default value when not specified in API or module is interpreted by Avi Controller as 50. - - Units(PERCENT). conn_lossy_timeo_rexmt_threshold: description: - A connection between client and avi is considered lossy when more than this percentage of packets are retransmitted due to timeout. - Allowed values are 1-100. - Default value when not specified in API or module is interpreted by Avi Controller as 20. - - Units(PERCENT). conn_lossy_total_rexmt_threshold: description: - A connection between client and avi is considered lossy when more than this percentage of packets are retransmitted. - Allowed values are 1-100. - Default value when not specified in API or module is interpreted by Avi Controller as 50. - - Units(PERCENT). conn_lossy_zero_win_size_event_threshold: description: - A client connection is considered lossy when percentage of times a packet could not be trasmitted due to tcp zero window is above this threshold. - Allowed values are 0-100. - Default value when not specified in API or module is interpreted by Avi Controller as 2. - - Units(PERCENT). conn_server_lossy_ooo_threshold: description: - A connection between avi and server is considered lossy when more than this percentage of out of order packets are received. - Allowed values are 1-100. - Default value when not specified in API or module is interpreted by Avi Controller as 50. - - Units(PERCENT). conn_server_lossy_timeo_rexmt_threshold: description: - A connection between avi and server is considered lossy when more than this percentage of packets are retransmitted due to timeout. - Allowed values are 1-100. - Default value when not specified in API or module is interpreted by Avi Controller as 20. - - Units(PERCENT). conn_server_lossy_total_rexmt_threshold: description: - A connection between avi and server is considered lossy when more than this percentage of packets are retransmitted. - Allowed values are 1-100. - Default value when not specified in API or module is interpreted by Avi Controller as 50. - - Units(PERCENT). conn_server_lossy_zero_win_size_event_threshold: description: - A server connection is considered lossy when percentage of times a packet could not be trasmitted due to tcp zero window is above this threshold. - Allowed values are 0-100. - Default value when not specified in API or module is interpreted by Avi Controller as 2. - - Units(PERCENT). description: description: - User defined description for the object. + disable_ondemand_metrics: + description: + - Virtual service (vs) metrics are processed only when there is live data traffic on the vs. + - In case, vs is idle for a period of time as specified by ondemand_metrics_idle_timeout then metrics processing is suspended for that vs. + - Field introduced in 18.1.1. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool disable_se_analytics: description: - Disable node (service engine) level analytics forvs metrics. @@ -175,9 +170,27 @@ options: disable_server_analytics: description: - Disable analytics on backend servers. - - This may be desired in container environment when there are large number of ephemeral servers. + - This may be desired in container environment when there are large number of ephemeral servers. + - Additionally, no healthscore of servers is computed when server analytics is disabled. - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool + disable_vs_analytics: + description: + - Disable virtualservice (frontend) analytics. + - This flag disables metrics and healthscore for virtualservice. + - Field introduced in 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool + enable_advanced_analytics: + description: + - Enables advanced analytics features like anomaly detection. + - If set to false, anomaly computation (and associated rules/events) for vs, pool and server metrics will be disabled. + - However, setting it to false reduces cpu and memory requirements for analytics subsystem. + - Field introduced in 17.2.13, 18.1.5, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as True. + version_added: "2.9" + type: bool exclude_client_close_before_request_as_error: description: - Exclude client closed connection before an http request could be completed from being classified as an error. @@ -235,6 +248,11 @@ options: - It is common for applications like ms exchange. - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool + exclude_sip_error_codes: + description: + - List of sip status codes to be excluded from being classified as an error. + - Field introduced in 17.2.13, 18.1.5, 18.2.1. + version_added: "2.9" exclude_syn_retransmit_as_error: description: - Exclude 'server unanswered syns' from the list of errors. @@ -250,6 +268,14 @@ options: - Exclude unsupported dns queries from the list of errors. - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool + healthscore_max_server_limit: + description: + - Skips health score computation of pool servers when number of servers in a pool is more than this setting. + - Allowed values are 0-5000. + - Special values are 0- 'server health score is disabled'. + - Field introduced in 17.2.13, 18.1.4. + - Default value when not specified in API or module is interpreted by Avi Controller as 20. + version_added: "2.9" hs_event_throttle_window: description: - Time window (in secs) within which only unique health change events should occur. @@ -381,6 +407,13 @@ options: description: - The name of the analytics profile. required: true + ondemand_metrics_idle_timeout: + description: + - This flag sets the time duration of no live data traffic after which virtual service metrics processing is suspended. + - It is applicable only when disable_ondemand_metrics is set to false. + - Field introduced in 18.1.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 1800. + version_added: "2.9" ranges: description: - List of http status code ranges to be excluded from being classified as an error. @@ -388,6 +421,19 @@ options: description: - Block of http response codes to be excluded from being classified as an error. - Enum options - AP_HTTP_RSP_4XX, AP_HTTP_RSP_5XX. + sensitive_log_profile: + description: + - Rules applied to the http application log for filtering sensitive information. + - Field introduced in 17.2.10, 18.1.2. + version_added: "2.9" + sip_log_depth: + description: + - Maximum number of sip messages added in logs for a sip transaction. + - By default, this value is 20. + - Allowed values are 1-1000. + - Field introduced in 17.2.13, 18.1.5, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 20. + version_added: "2.9" tenant_ref: description: - It is a reference to an object of type tenant. @@ -472,7 +518,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -505,8 +551,11 @@ def main(): conn_server_lossy_total_rexmt_threshold=dict(type='int',), conn_server_lossy_zero_win_size_event_threshold=dict(type='int',), description=dict(type='str',), + disable_ondemand_metrics=dict(type='bool',), disable_se_analytics=dict(type='bool',), disable_server_analytics=dict(type='bool',), + disable_vs_analytics=dict(type='bool',), + enable_advanced_analytics=dict(type='bool',), exclude_client_close_before_request_as_error=dict(type='bool',), exclude_dns_policy_drop_as_significant=dict(type='bool',), exclude_gs_down_as_error=dict(type='bool',), @@ -518,9 +567,11 @@ def main(): exclude_persistence_change_as_error=dict(type='bool',), exclude_server_dns_error_as_error=dict(type='bool',), exclude_server_tcp_reset_as_error=dict(type='bool',), + exclude_sip_error_codes=dict(type='list',), exclude_syn_retransmit_as_error=dict(type='bool',), exclude_tcp_reset_as_error=dict(type='bool',), exclude_unsupported_dns_query_as_error=dict(type='bool',), + healthscore_max_server_limit=dict(type='int',), hs_event_throttle_window=dict(type='int',), hs_max_anomaly_penalty=dict(type='int',), hs_max_resources_penalty=dict(type='int',), @@ -548,8 +599,11 @@ def main(): hs_security_tls12_score=dict(type='float',), hs_security_weak_signature_algo_penalty=dict(type='float',), name=dict(type='str', required=True), + ondemand_metrics_idle_timeout=dict(type='int',), ranges=dict(type='list',), resp_code_block=dict(type='list',), + sensitive_log_profile=dict(type='dict',), + sip_log_depth=dict(type='int',), tenant_ref=dict(type='str',), url=dict(type='str',), uuid=dict(type='str',), @@ -559,7 +613,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'analyticsprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_api_session.py b/lib/ansible/modules/network/avi/avi_api_session.py index 3cf5bc4e59d..7239fe61268 100644 --- a/lib/ansible/modules/network/avi/avi_api_session.py +++ b/lib/ansible/modules/network/avi/avi_api_session.py @@ -11,6 +11,7 @@ # """ + ANSIBLE_METADATA = {'metadata_version': '1.1', 'status': ['preview'], 'supported_by': 'community'} @@ -108,6 +109,7 @@ obj: type: dict ''' + import json import time from ansible.module_utils.basic import AnsibleModule @@ -115,10 +117,10 @@ from copy import deepcopy try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, ansible_return, HAS_AVI) - from avi.sdk.avi_api import ApiSession, AviCredentials - from avi.sdk.utils.ansible_utils import avi_obj_cmp, cleanup_absent_fields - + avi_common_argument_spec, ansible_return, avi_obj_cmp, + cleanup_absent_fields, HAS_AVI) + from ansible.module_utils.network.avi.avi_api import ( + ApiSession, AviCredentials) except ImportError: HAS_AVI = False @@ -135,12 +137,10 @@ def main(): ) argument_specs.update(avi_common_argument_spec()) module = AnsibleModule(argument_spec=argument_specs) - if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) - api_creds = AviCredentials() api_creds.update_from_ansible_module(module) api = ApiSession.get_session( @@ -167,33 +167,42 @@ def main(): gparams = deepcopy(params) if params else {} gparams.update({'include_refs': '', 'include_name': ''}) - if method == 'post': + # API methods not allowed + api_get_not_allowed = ["cluster", "gslbsiteops"] + api_post_not_allowed = ["alert", "fileservice"] + api_put_not_allowed = ["backup"] + + if method == 'post' and not any(path.startswith(uri) for uri in api_post_not_allowed): + # TODO: Above condition should be updated after AV-38981 is fixed # need to check if object already exists. In that case # change the method to be put try: using_collection = False - if not path.startswith('cluster'): - gparams['name'] = data['name'] + if not any(path.startswith(uri) for uri in api_get_not_allowed): + if 'name' in data: + gparams['name'] = data['name'] using_collection = True - rsp = api.get(path, tenant=tenant, tenant_uuid=tenant_uuid, - params=gparams, api_version=api_version) - existing_obj = rsp.json() - if using_collection: - existing_obj = existing_obj['results'][0] - except IndexError: + if not any(path.startswith(uri) for uri in api_get_not_allowed): + rsp = api.get(path, tenant=tenant, tenant_uuid=tenant_uuid, + params=gparams, api_version=api_version) + existing_obj = rsp.json() + if using_collection: + existing_obj = existing_obj['results'][0] + except (IndexError, KeyError): # object is not found pass else: - # object is present - method = 'put' - path += '/' + existing_obj['uuid'] + if not any(path.startswith(uri) for uri in api_get_not_allowed): + # object is present + method = 'put' + path += '/' + existing_obj['uuid'] - if method == 'put': + if method == 'put' and not any(path.startswith(uri) for uri in api_put_not_allowed): # put can happen with when full path is specified or it is put + post if existing_obj is None: using_collection = False if ((len(path.split('/')) == 1) and ('name' in data) and - (not path.startswith('cluster'))): + (not any(path.startswith(uri) for uri in api_get_not_allowed))): gparams['name'] = data['name'] using_collection = True rsp = api.get(path, tenant=tenant, tenant_uuid=tenant_uuid, diff --git a/lib/ansible/modules/network/avi/avi_api_version.py b/lib/ansible/modules/network/avi/avi_api_version.py index 00d8e9c01b1..1e36cc0df3e 100644 --- a/lib/ansible/modules/network/avi/avi_api_version.py +++ b/lib/ansible/modules/network/avi/avi_api_version.py @@ -1,5 +1,4 @@ #!/usr/bin/python -# -*- coding: utf-8 -*- """ # Created on July 24, 2017 # @@ -7,12 +6,13 @@ # # module_check: not supported # -# Copyright: (c) 2017, Gaurav Rastogi -# Copyright: (c) 2017, Vilian Atmadzhov +# Copyright: (c) 2017 Gaurav Rastogi, +# Vilian Atmadzhov, # GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) # """ + ANSIBLE_METADATA = {'metadata_version': '1.1', 'status': ['preview'], 'supported_by': 'community'} @@ -21,7 +21,7 @@ ANSIBLE_METADATA = {'metadata_version': '1.1', DOCUMENTATION = ''' --- module: avi_api_version -author: Vilian Atmadzhov (@grastogi23) +author: Vilian Atmadzhov (@vivobg) short_description: Avi API Version Module description: @@ -55,17 +55,20 @@ from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI) - from avi.sdk.avi_api import ApiSession, AviCredentials + avi_common_argument_spec, ansible_return, HAS_AVI) + from ansible.module_utils.network.avi.avi_api import ( + ApiSession, AviCredentials) except ImportError: HAS_AVI = False def main(): - module = AnsibleModule(argument_spec=avi_common_argument_spec()) + argument_specs = dict() + argument_specs.update(avi_common_argument_spec()) + module = AnsibleModule(argument_spec=argument_specs) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) try: api_creds = AviCredentials() @@ -84,7 +87,7 @@ def main(): api.close() module.exit_json(changed=False, obj=remote) except Exception as e: - module.fail_json(msg="Unable to get an AVI session. {0}".format(e)) + module.fail_json(msg=("Unable to get an AVI session. %s" % e)) if __name__ == '__main__': diff --git a/lib/ansible/modules/network/avi/avi_applicationpersistenceprofile.py b/lib/ansible/modules/network/avi/avi_applicationpersistenceprofile.py index 9723ee956c4..7947cc7a7be 100644 --- a/lib/ansible/modules/network/avi/avi_applicationpersistenceprofile.py +++ b/lib/ansible/modules/network/avi/avi_applicationpersistenceprofile.py @@ -128,7 +128,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -158,7 +158,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'applicationpersistenceprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_applicationprofile.py b/lib/ansible/modules/network/avi/avi_applicationprofile.py index 468083adc60..48b6fa9230e 100644 --- a/lib/ansible/modules/network/avi/avi_applicationprofile.py +++ b/lib/ansible/modules/network/avi/avi_applicationprofile.py @@ -42,6 +42,17 @@ options: - Patch operation to use when using avi_api_update_method as patch. version_added: "2.5" choices: ["add", "replace", "delete"] + cloud_config_cksum: + description: + - Checksum of application profiles. + - Internally set by cloud connector. + - Field introduced in 17.2.14, 18.1.5, 18.2.1. + version_added: "2.9" + created_by: + description: + - Name of the application profile creator. + - Field introduced in 17.2.14, 18.1.5, 18.2.1. + version_added: "2.9" description: description: - User defined description for the object. @@ -66,11 +77,16 @@ options: type: bool preserve_client_port: description: - - Specifies if we need to preserve client port while preseving client ip for backend connections. + - Specifies if we need to preserve client port while preserving client ip for backend connections. - Field introduced in 17.2.7. - Default value when not specified in API or module is interpreted by Avi Controller as False. version_added: "2.6" type: bool + sip_service_profile: + description: + - Specifies various sip service related controls for virtual service. + - Field introduced in 17.2.8, 18.1.3, 18.2.1. + version_added: "2.9" tcp_app_profile: description: - Specifies the tcp application proxy profile parameters. @@ -81,7 +97,7 @@ options: description: - Specifies which application layer proxy is enabled for the virtual service. - Enum options - APPLICATION_PROFILE_TYPE_L4, APPLICATION_PROFILE_TYPE_HTTP, APPLICATION_PROFILE_TYPE_SYSLOG, APPLICATION_PROFILE_TYPE_DNS, - - APPLICATION_PROFILE_TYPE_SSL. + - APPLICATION_PROFILE_TYPE_SSL, APPLICATION_PROFILE_TYPE_SIP. required: true url: description: @@ -165,7 +181,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -177,6 +193,8 @@ def main(): avi_api_update_method=dict(default='put', choices=['put', 'patch']), avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), + cloud_config_cksum=dict(type='str',), + created_by=dict(type='str',), description=dict(type='str',), dns_service_profile=dict(type='dict',), dos_rl_profile=dict(type='dict',), @@ -184,6 +202,7 @@ def main(): name=dict(type='str', required=True), preserve_client_ip=dict(type='bool',), preserve_client_port=dict(type='bool',), + sip_service_profile=dict(type='dict',), tcp_app_profile=dict(type='dict',), tenant_ref=dict(type='str',), type=dict(type='str', required=True), @@ -195,7 +214,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'applicationprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_authprofile.py b/lib/ansible/modules/network/avi/avi_authprofile.py index a5449bdb2c9..3cbf7f2fb03 100644 --- a/lib/ansible/modules/network/avi/avi_authprofile.py +++ b/lib/ansible/modules/network/avi/avi_authprofile.py @@ -55,6 +55,12 @@ options: description: - Name of the auth profile. required: true + pa_agent_ref: + description: + - Pingaccessagent uuid. + - It is a reference to an object of type pingaccessagent. + - Field introduced in 18.2.3. + version_added: "2.9" saml: description: - Saml settings. @@ -69,7 +75,7 @@ options: type: description: - Type of the auth profile. - - Enum options - AUTH_PROFILE_LDAP, AUTH_PROFILE_TACACS_PLUS, AUTH_PROFILE_SAML. + - Enum options - AUTH_PROFILE_LDAP, AUTH_PROFILE_TACACS_PLUS, AUTH_PROFILE_SAML, AUTH_PROFILE_PINGACCESS. required: true url: description: @@ -124,7 +130,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -140,6 +146,7 @@ def main(): http=dict(type='dict',), ldap=dict(type='dict',), name=dict(type='str', required=True), + pa_agent_ref=dict(type='str',), saml=dict(type='dict',), tacacs_plus=dict(type='dict',), tenant_ref=dict(type='str',), @@ -152,7 +159,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'authprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_autoscalelaunchconfig.py b/lib/ansible/modules/network/avi/avi_autoscalelaunchconfig.py index 9c34446d973..d9dd1617ae8 100644 --- a/lib/ansible/modules/network/avi/avi_autoscalelaunchconfig.py +++ b/lib/ansible/modules/network/avi/avi_autoscalelaunchconfig.py @@ -96,7 +96,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -123,7 +123,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'autoscalelaunchconfig', set([])) diff --git a/lib/ansible/modules/network/avi/avi_backup.py b/lib/ansible/modules/network/avi/avi_backup.py index 06d39b440fe..0dcedc57912 100644 --- a/lib/ansible/modules/network/avi/avi_backup.py +++ b/lib/ansible/modules/network/avi/avi_backup.py @@ -96,7 +96,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -123,7 +123,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'backup', set([])) diff --git a/lib/ansible/modules/network/avi/avi_backupconfiguration.py b/lib/ansible/modules/network/avi/avi_backupconfiguration.py index 9eeaaf29c73..6d5ee96b71e 100644 --- a/lib/ansible/modules/network/avi/avi_backupconfiguration.py +++ b/lib/ansible/modules/network/avi/avi_backupconfiguration.py @@ -41,6 +41,21 @@ options: - Patch operation to use when using avi_api_update_method as patch. version_added: "2.5" choices: ["add", "replace", "delete"] + aws_access_key: + description: + - Aws access key id. + - Field introduced in 18.2.3. + version_added: "2.9" + aws_bucket_id: + description: + - Aws bucket. + - Field introduced in 18.2.3. + version_added: "2.9" + aws_secret_access: + description: + - Aws secret access key. + - Field introduced in 18.2.3. + version_added: "2.9" backup_file_prefix: description: - Prefix of the exported configuration file. @@ -78,6 +93,12 @@ options: description: - Remote backup. type: bool + upload_to_s3: + description: + - Cloud backup. + - Field introduced in 18.2.3. + version_added: "2.9" + type: bool url: description: - Avi controller URL of the object. @@ -108,7 +129,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -120,6 +141,9 @@ def main(): avi_api_update_method=dict(default='put', choices=['put', 'patch']), avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), + aws_access_key=dict(type='str', no_log=True,), + aws_bucket_id=dict(type='str',), + aws_secret_access=dict(type='str', no_log=True,), backup_file_prefix=dict(type='str',), backup_passphrase=dict(type='str', no_log=True,), maximum_backups_stored=dict(type='int',), @@ -130,6 +154,7 @@ def main(): ssh_user_ref=dict(type='str',), tenant_ref=dict(type='str',), upload_to_remote_host=dict(type='bool',), + upload_to_s3=dict(type='bool',), url=dict(type='str',), uuid=dict(type='str',), ) @@ -138,10 +163,10 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'backupconfiguration', - set(['backup_passphrase'])) + set(['backup_passphrase', 'aws_access_key', 'aws_secret_access'])) if __name__ == '__main__': diff --git a/lib/ansible/modules/network/avi/avi_certificatemanagementprofile.py b/lib/ansible/modules/network/avi/avi_certificatemanagementprofile.py index d416c9d9170..b0406f22580 100644 --- a/lib/ansible/modules/network/avi/avi_certificatemanagementprofile.py +++ b/lib/ansible/modules/network/avi/avi_certificatemanagementprofile.py @@ -86,7 +86,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -110,7 +110,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'certificatemanagementprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_cloud.py b/lib/ansible/modules/network/avi/avi_cloud.py index d6487044380..ea1cc83c3c8 100644 --- a/lib/ansible/modules/network/avi/avi_cloud.py +++ b/lib/ansible/modules/network/avi/avi_cloud.py @@ -50,6 +50,12 @@ options: - Boolean flag to set apic_mode. - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool + autoscale_polling_interval: + description: + - Cloudconnector polling interval for external autoscale groups. + - Field introduced in 18.2.2. + - Default value when not specified in API or module is interpreted by Avi Controller as 60. + version_added: "2.9" aws_configuration: description: - Awsconfiguration settings for cloud. @@ -93,6 +99,18 @@ options: - Use static routes for vip side network resolution during virtualservice placement. - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool + gcp_configuration: + description: + - Google cloud platform configuration. + - Field introduced in 18.2.1. + version_added: "2.9" + ip6_autocfg_enabled: + description: + - Enable ipv6 auto configuration. + - Field introduced in 18.1.1. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool ipam_provider_ref: description: - Ipam profile for the cloud. @@ -108,18 +126,17 @@ options: description: - If no license type is specified then default license enforcement for the cloud type is chosen. - The default mappings are container cloud is max ses, openstack and vmware is cores and linux it is sockets. - - Enum options - LIC_BACKEND_SERVERS, LIC_SOCKETS, LIC_CORES, LIC_HOSTS, LIC_SE_BANDWIDTH. + - Enum options - LIC_BACKEND_SERVERS, LIC_SOCKETS, LIC_CORES, LIC_HOSTS, LIC_SE_BANDWIDTH, LIC_METERED_SE_BANDWIDTH. linuxserver_configuration: description: - Linuxserverconfiguration settings for cloud. mesos_configuration: description: - - Mesosconfiguration settings for cloud. + - Field deprecated in 18.2.2. mtu: description: - Mtu setting for the cloud. - Default value when not specified in API or module is interpreted by Avi Controller as 1500. - - Units(BYTES). name: description: - Name of the object. @@ -175,7 +192,7 @@ options: description: - Cloud type. - Enum options - CLOUD_NONE, CLOUD_VCENTER, CLOUD_OPENSTACK, CLOUD_AWS, CLOUD_VCA, CLOUD_APIC, CLOUD_MESOS, CLOUD_LINUXSERVER, CLOUD_DOCKER_UCP, - - CLOUD_RANCHER, CLOUD_OSHIFT_K8S, CLOUD_AZURE. + - CLOUD_RANCHER, CLOUD_OSHIFT_K8S, CLOUD_AZURE, CLOUD_GCP. - Default value when not specified in API or module is interpreted by Avi Controller as CLOUD_NONE. required: true extends_documentation_fragment: @@ -216,7 +233,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -230,6 +247,7 @@ def main(): avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), apic_configuration=dict(type='dict',), apic_mode=dict(type='bool',), + autoscale_polling_interval=dict(type='int',), aws_configuration=dict(type='dict',), azure_configuration=dict(type='dict',), cloudstack_configuration=dict(type='dict',), @@ -240,6 +258,8 @@ def main(): east_west_dns_provider_ref=dict(type='str',), east_west_ipam_provider_ref=dict(type='str',), enable_vip_static_routes=dict(type='bool',), + gcp_configuration=dict(type='dict',), + ip6_autocfg_enabled=dict(type='bool',), ipam_provider_ref=dict(type='str',), license_tier=dict(type='str',), license_type=dict(type='str',), @@ -267,7 +287,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'cloud', set([])) diff --git a/lib/ansible/modules/network/avi/avi_cloudconnectoruser.py b/lib/ansible/modules/network/avi/avi_cloudconnectoruser.py index 78f61d53981..51210edcd14 100644 --- a/lib/ansible/modules/network/avi/avi_cloudconnectoruser.py +++ b/lib/ansible/modules/network/avi/avi_cloudconnectoruser.py @@ -50,10 +50,20 @@ options: description: - Field introduced in 17.2.1. version_added: "2.5" + gcp_credentials: + description: + - Credentials for google cloud platform. + - Field introduced in 18.2.1. + version_added: "2.9" name: description: - Name of the object. required: true + oci_credentials: + description: + - Credentials for oracle cloud infrastructure. + - Field introduced in 18.2.1,18.1.3. + version_added: "2.9" private_key: description: - Private_key of cloudconnectoruser. @@ -63,6 +73,11 @@ options: tenant_ref: description: - It is a reference to an object of type tenant. + tencent_credentials: + description: + - Credentials for tencent cloud. + - Field introduced in 18.2.3. + version_added: "2.9" url: description: - Avi controller URL of the object. @@ -97,7 +112,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -111,10 +126,13 @@ def main(): avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), azure_serviceprincipal=dict(type='dict',), azure_userpass=dict(type='dict',), + gcp_credentials=dict(type='dict',), name=dict(type='str', required=True), + oci_credentials=dict(type='dict',), private_key=dict(type='str', no_log=True,), public_key=dict(type='str',), tenant_ref=dict(type='str',), + tencent_credentials=dict(type='dict',), url=dict(type='str',), uuid=dict(type='str',), ) @@ -123,7 +141,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'cloudconnectoruser', set(['private_key'])) diff --git a/lib/ansible/modules/network/avi/avi_cloudproperties.py b/lib/ansible/modules/network/avi/avi_cloudproperties.py index 80d1458ec16..7a809b92c03 100644 --- a/lib/ansible/modules/network/avi/avi_cloudproperties.py +++ b/lib/ansible/modules/network/avi/avi_cloudproperties.py @@ -49,7 +49,7 @@ options: description: - Cloud types supported by cloudconnector. - Enum options - CLOUD_NONE, CLOUD_VCENTER, CLOUD_OPENSTACK, CLOUD_AWS, CLOUD_VCA, CLOUD_APIC, CLOUD_MESOS, CLOUD_LINUXSERVER, CLOUD_DOCKER_UCP, - - CLOUD_RANCHER, CLOUD_OSHIFT_K8S, CLOUD_AZURE. + - CLOUD_RANCHER, CLOUD_OSHIFT_K8S, CLOUD_AZURE, CLOUD_GCP. hyp_props: description: - Hypervisor properties. @@ -86,7 +86,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -110,7 +110,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'cloudproperties', set([])) diff --git a/lib/ansible/modules/network/avi/avi_cluster.py b/lib/ansible/modules/network/avi/avi_cluster.py index 5b5d7fd0ba0..0b7e5ee2604 100644 --- a/lib/ansible/modules/network/avi/avi_cluster.py +++ b/lib/ansible/modules/network/avi/avi_cluster.py @@ -90,7 +90,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -115,7 +115,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'cluster', set([])) diff --git a/lib/ansible/modules/network/avi/avi_clusterclouddetails.py b/lib/ansible/modules/network/avi/avi_clusterclouddetails.py index 81450f50d37..0070838199b 100644 --- a/lib/ansible/modules/network/avi/avi_clusterclouddetails.py +++ b/lib/ansible/modules/network/avi/avi_clusterclouddetails.py @@ -83,7 +83,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -106,7 +106,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'clusterclouddetails', set([])) diff --git a/lib/ansible/modules/network/avi/avi_controllerproperties.py b/lib/ansible/modules/network/avi/avi_controllerproperties.py index a0ece5513ef..f88787ed24d 100644 --- a/lib/ansible/modules/network/avi/avi_controllerproperties.py +++ b/lib/ansible/modules/network/avi/avi_controllerproperties.py @@ -61,7 +61,13 @@ options: description: - Allowed values are 0-1440. - Default value when not specified in API or module is interpreted by Avi Controller as 15. - - Units(MIN). + api_perf_logging_threshold: + description: + - Threshold to log request timing in portal_performance.log and server-timing response header. + - Any stage taking longer than 1% of the threshold will be included in the server-timing header. + - Field introduced in 18.1.4, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 10000. + version_added: "2.9" appviewx_compat_mode: description: - Export configuration in appviewx compatibility mode. @@ -72,7 +78,6 @@ options: description: - Number of attach_ip_retry_interval. - Default value when not specified in API or module is interpreted by Avi Controller as 360. - - Units(SEC). attach_ip_retry_limit: description: - Number of attach_ip_retry_limit. @@ -84,29 +89,57 @@ options: - Default value when not specified in API or module is interpreted by Avi Controller as True. version_added: "2.5" type: bool + cleanup_expired_authtoken_timeout_period: + description: + - Period for auth token cleanup job. + - Field introduced in 18.1.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 60. + version_added: "2.9" + cleanup_sessions_timeout_period: + description: + - Period for sessions cleanup job. + - Field introduced in 18.1.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 60. + version_added: "2.9" + cloud_reconcile: + description: + - Enable/disable periodic reconcile for all the clouds. + - Field introduced in 17.2.14,18.1.5,18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as True. + version_added: "2.9" + type: bool cluster_ip_gratuitous_arp_period: description: - - Number of cluster_ip_gratuitous_arp_period. + - Period for cluster ip gratuitous arp job. - Default value when not specified in API or module is interpreted by Avi Controller as 60. - - Units(MIN). + consistency_check_timeout_period: + description: + - Period for consistency check job. + - Field introduced in 18.1.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 60. + version_added: "2.9" crashed_se_reboot: description: - Number of crashed_se_reboot. - Default value when not specified in API or module is interpreted by Avi Controller as 900. - - Units(SEC). dead_se_detection_timer: description: - Number of dead_se_detection_timer. - Default value when not specified in API or module is interpreted by Avi Controller as 360. - - Units(SEC). dns_refresh_period: description: - - Number of dns_refresh_period. + - Period for refresh pool and gslb dns job. - Default value when not specified in API or module is interpreted by Avi Controller as 60. - - Units(MIN). dummy: description: - Number of dummy. + enable_api_sharding: + description: + - This setting enables the controller leader to shard api requests to the followers (if any). + - Field introduced in 18.1.5, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as True. + version_added: "2.9" + type: bool enable_memory_balancer: description: - Enable/disable memory balancer. @@ -118,7 +151,6 @@ options: description: - Number of fatal_error_lease_time. - Default value when not specified in API or module is interpreted by Avi Controller as 120. - - Units(SEC). max_dead_se_in_grp: description: - Number of max_dead_se_in_grp. @@ -139,20 +171,31 @@ options: - Default value when not specified in API or module is interpreted by Avi Controller as 3. persistence_key_rotate_period: description: + - Period for rotate app persistence keys job. - Allowed values are 1-1051200. - Special values are 0 - 'disabled'. - - Default value when not specified in API or module is interpreted by Avi Controller as 60. - - Units(MIN). + - Default value when not specified in API or module is interpreted by Avi Controller as 0. portal_token: description: - Token used for uploading tech-support to portal. - Field introduced in 16.4.6,17.1.2. version_added: "2.4" + process_locked_useraccounts_timeout_period: + description: + - Period for process locked user accounts job. + - Field introduced in 18.1.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 1. + version_added: "2.9" + process_pki_profile_timeout_period: + description: + - Period for process pki profile job. + - Field introduced in 18.1.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 1440. + version_added: "2.9" query_host_fail: description: - Number of query_host_fail. - Default value when not specified in API or module is interpreted by Avi Controller as 180. - - Units(SEC). safenet_hsm_version: description: - Version of the safenet package installed on the controller. @@ -162,37 +205,38 @@ options: description: - Number of se_create_timeout. - Default value when not specified in API or module is interpreted by Avi Controller as 900. - - Units(SEC). se_failover_attempt_interval: description: - Interval between attempting failovers to an se. - Default value when not specified in API or module is interpreted by Avi Controller as 300. - - Units(SEC). + se_from_marketplace: + description: + - This setting decides whether se is to be deployed from the cloud marketplace or to be created by the controller. + - The setting is applicable only when byol license is selected. + - Enum options - MARKETPLACE, IMAGE. + - Field introduced in 18.1.4, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as IMAGE. + version_added: "2.9" se_offline_del: description: - Number of se_offline_del. - Default value when not specified in API or module is interpreted by Avi Controller as 172000. - - Units(SEC). se_vnic_cooldown: description: - Number of se_vnic_cooldown. - Default value when not specified in API or module is interpreted by Avi Controller as 120. - - Units(SEC). secure_channel_cleanup_timeout: description: - - Number of secure_channel_cleanup_timeout. + - Period for secure channel cleanup job. - Default value when not specified in API or module is interpreted by Avi Controller as 60. - - Units(MIN). secure_channel_controller_token_timeout: description: - Number of secure_channel_controller_token_timeout. - Default value when not specified in API or module is interpreted by Avi Controller as 60. - - Units(MIN). secure_channel_se_token_timeout: description: - Number of secure_channel_se_token_timeout. - Default value when not specified in API or module is interpreted by Avi Controller as 60. - - Units(MIN). seupgrade_fabric_pool_size: description: - Pool size used for all fabric commands during se upgrade. @@ -201,28 +245,23 @@ options: description: - Time to wait before marking segroup upgrade as stuck. - Default value when not specified in API or module is interpreted by Avi Controller as 360. - - Units(SEC). ssl_certificate_expiry_warning_days: description: - Number of days for ssl certificate expiry warning. - - Units(DAYS). unresponsive_se_reboot: description: - Number of unresponsive_se_reboot. - Default value when not specified in API or module is interpreted by Avi Controller as 300. - - Units(SEC). upgrade_dns_ttl: description: - Time to account for dns ttl during upgrade. - This is in addition to vs_scalein_timeout_for_upgrade in se_group. - Field introduced in 17.1.1. - Default value when not specified in API or module is interpreted by Avi Controller as 5. - - Units(SEC). upgrade_lease_time: description: - Number of upgrade_lease_time. - Default value when not specified in API or module is interpreted by Avi Controller as 360. - - Units(SEC). url: description: - Avi controller URL of the object. @@ -233,60 +272,62 @@ options: description: - Number of vnic_op_fail_time. - Default value when not specified in API or module is interpreted by Avi Controller as 180. - - Units(SEC). vs_apic_scaleout_timeout: description: - Time to wait for the scaled out se to become ready before marking the scaleout done, applies to apic configuration only. - Default value when not specified in API or module is interpreted by Avi Controller as 360. - - Units(SEC). vs_awaiting_se_timeout: description: - Number of vs_awaiting_se_timeout. - Default value when not specified in API or module is interpreted by Avi Controller as 60. - - Units(SEC). vs_key_rotate_period: description: + - Period for rotate vs keys job. - Allowed values are 1-1051200. - Special values are 0 - 'disabled'. + - Default value when not specified in API or module is interpreted by Avi Controller as 360. + vs_scaleout_ready_check_interval: + description: + - Interval for checking scaleout_ready status while controller is waiting for scaleoutready rpc from the service engine. + - Field introduced in 18.2.2. - Default value when not specified in API or module is interpreted by Avi Controller as 60. - - Units(MIN). + version_added: "2.9" vs_se_attach_ip_fail: description: - Time to wait before marking attach ip operation on an se as failed. - Field introduced in 17.2.2. - - Default value when not specified in API or module is interpreted by Avi Controller as 3600. - - Units(SEC). + - Default value when not specified in API or module is interpreted by Avi Controller as 600. version_added: "2.5" vs_se_bootup_fail: description: - Number of vs_se_bootup_fail. - Default value when not specified in API or module is interpreted by Avi Controller as 480. - - Units(SEC). vs_se_create_fail: description: - Number of vs_se_create_fail. - Default value when not specified in API or module is interpreted by Avi Controller as 1500. - - Units(SEC). vs_se_ping_fail: description: - Number of vs_se_ping_fail. - Default value when not specified in API or module is interpreted by Avi Controller as 60. - - Units(SEC). vs_se_vnic_fail: description: - Number of vs_se_vnic_fail. - Default value when not specified in API or module is interpreted by Avi Controller as 300. - - Units(SEC). vs_se_vnic_ip_fail: description: - Number of vs_se_vnic_ip_fail. - Default value when not specified in API or module is interpreted by Avi Controller as 120. - - Units(SEC). warmstart_se_reconnect_wait_time: description: - Number of warmstart_se_reconnect_wait_time. + - Default value when not specified in API or module is interpreted by Avi Controller as 480. + warmstart_vs_resync_wait_time: + description: + - Timeout for warmstart vs resync. + - Field introduced in 18.1.4, 18.2.1. - Default value when not specified in API or module is interpreted by Avi Controller as 300. - - Units(SEC). + version_added: "2.9" extends_documentation_fragment: - avi ''' @@ -311,7 +352,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -327,15 +368,21 @@ def main(): allow_unauthenticated_apis=dict(type='bool',), allow_unauthenticated_nodes=dict(type='bool',), api_idle_timeout=dict(type='int',), + api_perf_logging_threshold=dict(type='int',), appviewx_compat_mode=dict(type='bool',), attach_ip_retry_interval=dict(type='int',), attach_ip_retry_limit=dict(type='int',), bm_use_ansible=dict(type='bool',), + cleanup_expired_authtoken_timeout_period=dict(type='int',), + cleanup_sessions_timeout_period=dict(type='int',), + cloud_reconcile=dict(type='bool',), cluster_ip_gratuitous_arp_period=dict(type='int',), + consistency_check_timeout_period=dict(type='int',), crashed_se_reboot=dict(type='int',), dead_se_detection_timer=dict(type='int',), dns_refresh_period=dict(type='int',), dummy=dict(type='int',), + enable_api_sharding=dict(type='bool',), enable_memory_balancer=dict(type='bool',), fatal_error_lease_time=dict(type='int',), max_dead_se_in_grp=dict(type='int',), @@ -344,10 +391,13 @@ def main(): max_seq_vnic_failures=dict(type='int',), persistence_key_rotate_period=dict(type='int',), portal_token=dict(type='str', no_log=True,), + process_locked_useraccounts_timeout_period=dict(type='int',), + process_pki_profile_timeout_period=dict(type='int',), query_host_fail=dict(type='int',), safenet_hsm_version=dict(type='str',), se_create_timeout=dict(type='int',), se_failover_attempt_interval=dict(type='int',), + se_from_marketplace=dict(type='str',), se_offline_del=dict(type='int',), se_vnic_cooldown=dict(type='int',), secure_channel_cleanup_timeout=dict(type='int',), @@ -365,6 +415,7 @@ def main(): vs_apic_scaleout_timeout=dict(type='int',), vs_awaiting_se_timeout=dict(type='int',), vs_key_rotate_period=dict(type='int',), + vs_scaleout_ready_check_interval=dict(type='int',), vs_se_attach_ip_fail=dict(type='int',), vs_se_bootup_fail=dict(type='int',), vs_se_create_fail=dict(type='int',), @@ -372,13 +423,14 @@ def main(): vs_se_vnic_fail=dict(type='int',), vs_se_vnic_ip_fail=dict(type='int',), warmstart_se_reconnect_wait_time=dict(type='int',), + warmstart_vs_resync_wait_time=dict(type='int',), ) argument_specs.update(avi_common_argument_spec()) module = AnsibleModule( argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'controllerproperties', set(['portal_token'])) diff --git a/lib/ansible/modules/network/avi/avi_customipamdnsprofile.py b/lib/ansible/modules/network/avi/avi_customipamdnsprofile.py index 155b1a974ec..6ffca67b013 100644 --- a/lib/ansible/modules/network/avi/avi_customipamdnsprofile.py +++ b/lib/ansible/modules/network/avi/avi_customipamdnsprofile.py @@ -89,7 +89,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -113,7 +113,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'customipamdnsprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_dnspolicy.py b/lib/ansible/modules/network/avi/avi_dnspolicy.py index da131415484..82e403daef5 100644 --- a/lib/ansible/modules/network/avi/avi_dnspolicy.py +++ b/lib/ansible/modules/network/avi/avi_dnspolicy.py @@ -93,7 +93,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -118,7 +118,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'dnspolicy', set([])) diff --git a/lib/ansible/modules/network/avi/avi_errorpagebody.py b/lib/ansible/modules/network/avi/avi_errorpagebody.py index e3324e6b4d5..fe8811add51 100644 --- a/lib/ansible/modules/network/avi/avi_errorpagebody.py +++ b/lib/ansible/modules/network/avi/avi_errorpagebody.py @@ -45,6 +45,13 @@ options: description: - Error page body sent to client when match. - Field introduced in 17.2.4. + format: + description: + - Format of an error page body html or json. + - Enum options - ERROR_PAGE_FORMAT_HTML, ERROR_PAGE_FORMAT_JSON. + - Field introduced in 18.2.3. + - Default value when not specified in API or module is interpreted by Avi Controller as ERROR_PAGE_FORMAT_HTML. + version_added: "2.9" name: description: - Field introduced in 17.2.4. @@ -83,7 +90,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -96,6 +103,7 @@ def main(): choices=['put', 'patch']), avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), error_page_body=dict(type='str',), + format=dict(type='str',), name=dict(type='str', required=True), tenant_ref=dict(type='str',), url=dict(type='str',), @@ -106,7 +114,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'errorpagebody', set([])) diff --git a/lib/ansible/modules/network/avi/avi_errorpageprofile.py b/lib/ansible/modules/network/avi/avi_errorpageprofile.py index 5667dcf4cdc..132407270b0 100644 --- a/lib/ansible/modules/network/avi/avi_errorpageprofile.py +++ b/lib/ansible/modules/network/avi/avi_errorpageprofile.py @@ -44,11 +44,13 @@ options: app_name: description: - Name of the virtual service which generated the error page. + - Field deprecated in 18.1.1. - Field introduced in 17.2.4. - Default value when not specified in API or module is interpreted by Avi Controller as VS Name. company_name: description: - Name of the company to show in error page. + - Field deprecated in 18.1.1. - Field introduced in 17.2.4. - Default value when not specified in API or module is interpreted by Avi Controller as Avi Networks. error_pages: @@ -58,6 +60,7 @@ options: host_name: description: - Fully qualified domain name for which the error page is generated. + - Field deprecated in 18.1.1. - Field introduced in 17.2.4. - Default value when not specified in API or module is interpreted by Avi Controller as Host Header. name: @@ -98,7 +101,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -124,7 +127,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'errorpageprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_gslb.py b/lib/ansible/modules/network/avi/avi_gslb.py index 99285bd1130..93d08dba691 100644 --- a/lib/ansible/modules/network/avi/avi_gslb.py +++ b/lib/ansible/modules/network/avi/avi_gslb.py @@ -42,6 +42,14 @@ options: - Patch operation to use when using avi_api_update_method as patch. version_added: "2.5" choices: ["add", "replace", "delete"] + async_interval: + description: + - Frequency with which messages are propagated to vs mgr. + - Value of 0 disables async behavior and rpc are sent inline. + - Allowed values are 0-5. + - Field introduced in 18.2.3. + - Default value when not specified in API or module is interpreted by Avi Controller as 0. + version_added: "2.9" clear_on_max_retries: description: - Max retries after which the remote site is treated as a fresh start. @@ -92,7 +100,14 @@ options: - Frequency with which group members communicate. - Allowed values are 1-3600. - Default value when not specified in API or module is interpreted by Avi Controller as 15. - - Units(SEC). + send_interval_prior_to_maintenance_mode: + description: + - The user can specify a send-interval while entering maintenance mode. + - The validity of this 'maintenance send-interval' is only during maintenance mode. + - When the user leaves maintenance mode, the original send-interval is reinstated. + - This internal variable is used to store the original send-interval. + - Field introduced in 18.2.3. + version_added: "2.9" sites: description: - Select avi site member belonging to this gslb. @@ -121,11 +136,107 @@ extends_documentation_fragment: EXAMPLES = """ - name: Example to create Gslb object avi_gslb: - controller: 10.10.25.42 - username: admin - password: something - state: present - name: sample_gslb + name: "test-gslb" + avi_credentials: + username: '{{ username }}' + password: '{{ password }}' + controller: '{{ controller }}' + sites: + - name: "test-site1" + username: "gslb_username" + password: "gslb_password" + ip_addresses: + - type: "V4" + addr: "10.10.28.83" + enabled: True + member_type: "GSLB_ACTIVE_MEMBER" + port: 443 + cluster_uuid: "cluster-d4ee5fcc-3e0a-4d4f-9ae6-4182bc605829" + - name: "test-site2" + username: "gslb_username" + password: "gslb_password" + ip_addresses: + - type: "V4" + addr: "10.10.28.86" + enabled: True + member_type: "GSLB_ACTIVE_MEMBER" + port: 443 + cluster_uuid: "cluster-0c37ae8d-ab62-410c-ad3e-06fa831950b1" + dns_configs: + - domain_name: "test1.com" + - domain_name: "test2.com" + leader_cluster_uuid: "cluster-d4ee5fcc-3e0a-4d4f-9ae6-4182bc605829" + +- name: Update Gslb site's configurations (Patch Add Operation) + avi_gslb: + avi_credentials: + username: '{{ username }}' + password: '{{ password }}' + controller: '{{ controller }}' + avi_api_update_method: patch + avi_api_patch_op: add + leader_cluster_uuid: "cluster-d4ee5fcc-3e0a-4d4f-9ae6-4182bc605829" + name: "test-gslb" + dns_configs: + - domain_name: "temp1.com" + - domain_name: "temp2.com" + gslb_sites_config: + - ip_addr: "10.10.28.83" + dns_vses: + - dns_vs_uuid: "virtualservice-f2a711cd-5e78-473f-8f47-d12de660fd62" + domain_names: + - "test1.com" + - "test2.com" + - ip_addr: "10.10.28.86" + dns_vses: + - dns_vs_uuid: "virtualservice-c1a63a16-f2a1-4f41-aab4-1e90f92a5e49" + domain_names: + - "temp1.com" + - "temp2.com" + +- name: Update Gslb site's configurations (Patch Replace Operation) + avi_gslb: + avi_credentials: + username: "{{ username }}" + password: "{{ password }}" + controller: "{{ controller }}" + # On basis of cluster leader uuid dns_configs is set for that perticular leader cluster + leader_cluster_uuid: "cluster-84aa795f-8f09-42bb-97a4-5103f4a53da9" + name: "test-gslb" + avi_api_update_method: patch + avi_api_patch_op: replace + dns_configs: + - domain_name: "test3.com" + - domain_name: "temp3.com" + gslb_sites_config: + # Ip address is mapping key for dns_vses field update. For the given IP address, + # dns_vses is updated. + - ip_addr: "10.10.28.83" + dns_vses: + - dns_vs_uuid: "virtualservice-7c947ed4-77f3-4a52-909c-4f12afaf5bb0" + domain_names: + - "test3.com" + - ip_addr: "10.10.28.86" + dns_vses: + - dns_vs_uuid: "virtualservice-799b2c6d-7f2d-4c3f-94c6-6e813b20b674" + domain_names: + - "temp3.com" + +- name: Update Gslb site's configurations (Patch Delete Operation) + avi_gslb: + avi_credentials: + username: "{{ username }}" + password: "{{ password }}" + controller: "{{ controller }}" + # On basis of cluster leader uuid dns_configs is set for that perticular leader cluster + leader_cluster_uuid: "cluster-84aa795f-8f09-42bb-97a4-5103f4a53da9" + name: "test-gslb" + avi_api_update_method: patch + avi_api_patch_op: delete + dns_configs: + gslb_sites_config: + - ip_addr: "10.10.28.83" + - ip_addr: "10.10.28.86" """ RETURN = ''' @@ -138,7 +249,8 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) + from ansible.module_utils.network.avi.avi_api import ApiSession, AviCredentials except ImportError: HAS_AVI = False @@ -150,6 +262,7 @@ def main(): avi_api_update_method=dict(default='put', choices=['put', 'patch']), avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), + async_interval=dict(type='int',), clear_on_max_retries=dict(type='int',), client_ip_addr_group=dict(type='dict',), description=dict(type='str',), @@ -159,6 +272,7 @@ def main(): maintenance_mode=dict(type='bool',), name=dict(type='str', required=True), send_interval=dict(type='int',), + send_interval_prior_to_maintenance_mode=dict(type='int',), sites=dict(type='list',), tenant_ref=dict(type='str',), third_party_sites=dict(type='list',), @@ -171,8 +285,74 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) + api_method = module.params['avi_api_update_method'] + if str(api_method).lower() == 'patch': + patch_op = module.params['avi_api_patch_op'] + # Create controller session + api_creds = AviCredentials() + api_creds.update_from_ansible_module(module) + api = ApiSession.get_session( + api_creds.controller, api_creds.username, password=api_creds.password, + timeout=api_creds.timeout, tenant=api_creds.tenant, + tenant_uuid=api_creds.tenant_uuid, token=api_creds.token, + port=api_creds.port) + # Get existing gslb objects + rsp = api.get('gslb', api_version=api_creds.api_version) + existing_gslb = rsp.json() + gslb = existing_gslb['results'] + sites = module.params['gslb_sites_config'] + for gslb_obj in gslb: + # Update/Delete domain names in dns_configs fields in gslb object. + if 'dns_configs' in module.params: + if gslb_obj['leader_cluster_uuid'] == module.params['leader_cluster_uuid']: + if str(patch_op).lower() == 'delete': + gslb_obj['dns_configs'] = [] + elif str(patch_op).lower() == 'add': + if module.params['dns_configs'] not in gslb_obj['dns_configs']: + gslb_obj['dns_configs'].extend(module.params['dns_configs']) + else: + gslb_obj['dns_configs'] = module.params['dns_configs'] + # Update/Delete sites configuration + if sites: + for site_obj in gslb_obj['sites']: + dns_vses = site_obj.get('dns_vses', []) + for obj in sites: + config_for = obj.get('ip_addr', None) + if not config_for: + return module.fail_json(msg=( + "ip_addr of site in a configuration is mandatory. " + "Please provide ip_addr i.e. gslb site's ip.")) + if config_for == site_obj['ip_addresses'][0]['addr']: + if str(patch_op).lower() == 'delete': + site_obj['dns_vses'] = [] + else: + # Modify existing gslb sites object + for key, val in obj.items(): + if key == 'dns_vses' and str(patch_op).lower() == 'add': + found = False + # Check dns_vses field already exists on the controller + for v in dns_vses: + if val[0]['dns_vs_uuid'] != v['dns_vs_uuid']: + found = True + break + if not found: + dns_vses.extend(val) + else: + site_obj[key] = val + if str(patch_op).lower() == 'add': + site_obj['dns_vses'] = dns_vses + uni_dns_configs = [dict(tupleized) for tupleized in set(tuple(item.items()) + for item in gslb_obj['dns_configs'])] + gslb_obj['dns_configs'] = uni_dns_configs + module.params.update(gslb_obj) + module.params.update( + { + 'avi_api_update_method': 'put', + 'state': 'present' + } + ) return avi_ansible_api(module, 'gslb', set([])) diff --git a/lib/ansible/modules/network/avi/avi_gslbapplicationpersistenceprofile.py b/lib/ansible/modules/network/avi/avi_gslbapplicationpersistenceprofile.py deleted file mode 100644 index 46245f10745..00000000000 --- a/lib/ansible/modules/network/avi/avi_gslbapplicationpersistenceprofile.py +++ /dev/null @@ -1,117 +0,0 @@ -#!/usr/bin/python -# -# Created on Aug 25, 2016 -# @author: Gaurav Rastogi (grastogi@avinetworks.com) -# Eric Anderson (eanderson@avinetworks.com) -# module_check: supported -# Avi Version: 17.1.1 -# -# -# This file is part of Ansible -# -# Ansible is free software: you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation, either version 3 of the License, or -# (at your option) any later version. -# -# Ansible is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with Ansible. If not, see . -# - -ANSIBLE_METADATA = {'metadata_version': '1.1', - 'status': ['preview'], - 'supported_by': 'community'} - -DOCUMENTATION = ''' ---- -module: avi_gslbapplicationpersistenceprofile -author: Gaurav Rastogi (@grastogi23) - -short_description: Module for setup of GslbApplicationPersistenceProfile Avi RESTful Object -description: - - This module is used to configure GslbApplicationPersistenceProfile object - - more examples at U(https://github.com/avinetworks/devops) -requirements: [ avisdk ] -version_added: "2.4" -options: - state: - description: - - The state that should be applied on the entity. - default: present - choices: ["absent","present"] - description: - description: - - Field introduced in 17.1.1. - name: - description: - - A user-friendly name for the persistence profile. - - Field introduced in 17.1.1. - required: true - tenant_ref: - description: - - It is a reference to an object of type tenant. - - Field introduced in 17.1.1. - url: - description: - - Avi controller URL of the object. - uuid: - description: - - Uuid of the persistence profile. - - Field introduced in 17.1.1. -extends_documentation_fragment: - - avi -''' - -EXAMPLES = """ -- name: Example to create GslbApplicationPersistenceProfile object - avi_gslbapplicationpersistenceprofile: - controller: 10.10.25.42 - username: admin - password: something - state: present - name: sample_gslbapplicationpersistenceprofile -""" - -RETURN = ''' -obj: - description: GslbApplicationPersistenceProfile (api/gslbapplicationpersistenceprofile) object - returned: success, changed - type: dict -''' - -from ansible.module_utils.basic import AnsibleModule -try: - from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) -except ImportError: - HAS_AVI = False - - -def main(): - argument_specs = dict( - state=dict(default='present', - choices=['absent', 'present']), - description=dict(type='str',), - name=dict(type='str', required=True), - tenant_ref=dict(type='str',), - url=dict(type='str',), - uuid=dict(type='str',), - ) - argument_specs.update(avi_common_argument_spec()) - module = AnsibleModule( - argument_spec=argument_specs, supports_check_mode=True) - if not HAS_AVI: - return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' - 'For more details visit https://github.com/avinetworks/sdk.')) - return avi_ansible_api(module, 'gslbapplicationpersistenceprofile', - set([])) - - -if __name__ == '__main__': - main() diff --git a/lib/ansible/modules/network/avi/avi_gslbgeodbprofile.py b/lib/ansible/modules/network/avi/avi_gslbgeodbprofile.py index 2cdf4c93b48..63b52dcc406 100644 --- a/lib/ansible/modules/network/avi/avi_gslbgeodbprofile.py +++ b/lib/ansible/modules/network/avi/avi_gslbgeodbprofile.py @@ -96,7 +96,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -121,7 +121,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'gslbgeodbprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_gslbhealthmonitor.py b/lib/ansible/modules/network/avi/avi_gslbhealthmonitor.py deleted file mode 100644 index 88a02800350..00000000000 --- a/lib/ansible/modules/network/avi/avi_gslbhealthmonitor.py +++ /dev/null @@ -1,178 +0,0 @@ -#!/usr/bin/python -# -# Created on Aug 25, 2016 -# @author: Gaurav Rastogi (grastogi@avinetworks.com) -# Eric Anderson (eanderson@avinetworks.com) -# module_check: supported -# Avi Version: 17.1.1 -# -# -# This file is part of Ansible -# -# Ansible is free software: you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation, either version 3 of the License, or -# (at your option) any later version. -# -# Ansible is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with Ansible. If not, see . -# - -ANSIBLE_METADATA = {'metadata_version': '1.1', - 'status': ['preview'], - 'supported_by': 'community'} - -DOCUMENTATION = ''' ---- -module: avi_gslbhealthmonitor -author: Gaurav Rastogi (@grastogi23) - -short_description: Module for setup of GslbHealthMonitor Avi RESTful Object -description: - - This module is used to configure GslbHealthMonitor object - - more examples at U(https://github.com/avinetworks/devops) -requirements: [ avisdk ] -version_added: "2.4" -options: - state: - description: - - The state that should be applied on the entity. - default: present - choices: ["absent","present"] - description: - description: - - User defined description for the object. - dns_monitor: - description: - - Healthmonitordns settings for gslbhealthmonitor. - external_monitor: - description: - - Healthmonitorexternal settings for gslbhealthmonitor. - failed_checks: - description: - - Number of continuous failed health checks before the server is marked down. - - Allowed values are 1-50. - - Default value when not specified in API or module is interpreted by Avi Controller as 2. - http_monitor: - description: - - Healthmonitorhttp settings for gslbhealthmonitor. - https_monitor: - description: - - Healthmonitorhttp settings for gslbhealthmonitor. - monitor_port: - description: - - Use this port instead of the port defined for the server in the pool. - - If the monitor succeeds to this port, the load balanced traffic will still be sent to the port of the server defined within the pool. - - Allowed values are 1-65535. - - Special values are 0 - 'use server port'. - name: - description: - - A user friendly name for this health monitor. - required: true - receive_timeout: - description: - - A valid response from the server is expected within the receive timeout window. - - This timeout must be less than the send interval. - - If server status is regularly flapping up and down, consider increasing this value. - - Allowed values are 1-300. - - Default value when not specified in API or module is interpreted by Avi Controller as 4. - send_interval: - description: - - Frequency, in seconds, that monitors are sent to a server. - - Allowed values are 1-3600. - - Default value when not specified in API or module is interpreted by Avi Controller as 5. - successful_checks: - description: - - Number of continuous successful health checks before server is marked up. - - Allowed values are 1-50. - - Default value when not specified in API or module is interpreted by Avi Controller as 2. - tcp_monitor: - description: - - Healthmonitortcp settings for gslbhealthmonitor. - tenant_ref: - description: - - It is a reference to an object of type tenant. - type: - description: - - Type of the health monitor. - - Enum options - HEALTH_MONITOR_PING, HEALTH_MONITOR_TCP, HEALTH_MONITOR_HTTP, HEALTH_MONITOR_HTTPS, HEALTH_MONITOR_EXTERNAL, HEALTH_MONITOR_UDP, - - HEALTH_MONITOR_DNS, HEALTH_MONITOR_GSLB. - required: true - udp_monitor: - description: - - Healthmonitorudp settings for gslbhealthmonitor. - url: - description: - - Avi controller URL of the object. - uuid: - description: - - Uuid of the health monitor. -extends_documentation_fragment: - - avi -''' - -EXAMPLES = """ -- name: Example to create GslbHealthMonitor object - avi_gslbhealthmonitor: - controller: 10.10.25.42 - username: admin - password: something - state: present - name: sample_gslbhealthmonitor -""" - -RETURN = ''' -obj: - description: GslbHealthMonitor (api/gslbhealthmonitor) object - returned: success, changed - type: dict -''' - -from ansible.module_utils.basic import AnsibleModule -try: - from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) -except ImportError: - HAS_AVI = False - - -def main(): - argument_specs = dict( - state=dict(default='present', - choices=['absent', 'present']), - description=dict(type='str',), - dns_monitor=dict(type='dict',), - external_monitor=dict(type='dict',), - failed_checks=dict(type='int',), - http_monitor=dict(type='dict',), - https_monitor=dict(type='dict',), - monitor_port=dict(type='int',), - name=dict(type='str', required=True), - receive_timeout=dict(type='int',), - send_interval=dict(type='int',), - successful_checks=dict(type='int',), - tcp_monitor=dict(type='dict',), - tenant_ref=dict(type='str',), - type=dict(type='str', required=True), - udp_monitor=dict(type='dict',), - url=dict(type='str',), - uuid=dict(type='str',), - ) - argument_specs.update(avi_common_argument_spec()) - module = AnsibleModule( - argument_spec=argument_specs, supports_check_mode=True) - if not HAS_AVI: - return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' - 'For more details visit https://github.com/avinetworks/sdk.')) - return avi_ansible_api(module, 'gslbhealthmonitor', - set([])) - - -if __name__ == '__main__': - main() diff --git a/lib/ansible/modules/network/avi/avi_gslbservice.py b/lib/ansible/modules/network/avi/avi_gslbservice.py index 7cda8673ba4..f46f0710df5 100644 --- a/lib/ansible/modules/network/avi/avi_gslbservice.py +++ b/lib/ansible/modules/network/avi/avi_gslbservice.py @@ -90,6 +90,12 @@ options: - In such a case, avi members can have controller derived status while non-avi members can be probed by via health monitor probes in dataplane. - Enum options - GSLB_SERVICE_HEALTH_MONITOR_ALL_MEMBERS, GSLB_SERVICE_HEALTH_MONITOR_ONLY_NON_AVI_MEMBERS. - Default value when not specified in API or module is interpreted by Avi Controller as GSLB_SERVICE_HEALTH_MONITOR_ALL_MEMBERS. + hm_off: + description: + - This field is an internal field and is used in se. + - Field introduced in 18.2.2. + version_added: "2.9" + type: bool is_federated: description: - This field indicates that this object is replicated across gslb federation. @@ -134,8 +140,7 @@ options: ttl: description: - Ttl value (in seconds) for records served for this gslb service by the dns service. - - Allowed values are 1-86400. - - Units(SEC). + - Allowed values are 0-86400. url: description: - Avi controller URL of the object. @@ -181,7 +186,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -203,6 +208,7 @@ def main(): groups=dict(type='list',), health_monitor_refs=dict(type='list',), health_monitor_scope=dict(type='str',), + hm_off=dict(type='bool',), is_federated=dict(type='bool',), min_members=dict(type='int',), name=dict(type='str', required=True), @@ -221,7 +227,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'gslbservice', set([])) diff --git a/lib/ansible/modules/network/avi/avi_gslbservice_patch_member.py b/lib/ansible/modules/network/avi/avi_gslbservice_patch_member.py index c304eb7bcc0..32e2d14c1ee 100644 --- a/lib/ansible/modules/network/avi/avi_gslbservice_patch_member.py +++ b/lib/ansible/modules/network/avi/avi_gslbservice_patch_member.py @@ -110,14 +110,12 @@ import time from ansible.module_utils.basic import AnsibleModule from copy import deepcopy -HAS_AVI = True try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI) - from avi.sdk.avi_api import ApiSession, AviCredentials - from avi.sdk.utils.ansible_utils import ( - avi_obj_cmp, cleanup_absent_fields, ansible_return, - AviCheckModeResponse) + avi_common_argument_spec, avi_obj_cmp, cleanup_absent_fields, + ansible_return, AviCheckModeResponse, HAS_AVI) + from ansible.module_utils.network.avi.avi_api import ( + ApiSession, AviCredentials) except ImportError: HAS_AVI = False @@ -238,10 +236,9 @@ def main(): ) argument_specs.update(avi_common_argument_spec()) module = AnsibleModule(argument_spec=argument_specs) - if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or ansible>=2.8 is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) api_creds = AviCredentials() api_creds.update_from_ansible_module(module) diff --git a/lib/ansible/modules/network/avi/avi_hardwaresecuritymodulegroup.py b/lib/ansible/modules/network/avi/avi_hardwaresecuritymodulegroup.py index cbe57999e44..310c42ad272 100644 --- a/lib/ansible/modules/network/avi/avi_hardwaresecuritymodulegroup.py +++ b/lib/ansible/modules/network/avi/avi_hardwaresecuritymodulegroup.py @@ -82,7 +82,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -105,7 +105,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'hardwaresecuritymodulegroup', set([])) diff --git a/lib/ansible/modules/network/avi/avi_healthmonitor.py b/lib/ansible/modules/network/avi/avi_healthmonitor.py index 34f5d01e1b4..4fe96d289ec 100644 --- a/lib/ansible/modules/network/avi/avi_healthmonitor.py +++ b/lib/ansible/modules/network/avi/avi_healthmonitor.py @@ -81,6 +81,11 @@ options: description: - A user friendly name for this health monitor. required: true + radius_monitor: + description: + - Health monitor for radius. + - Field introduced in 18.2.3. + version_added: "2.9" receive_timeout: description: - A valid response from the server is expected within the receive timeout window. @@ -88,13 +93,16 @@ options: - If server status is regularly flapping up and down, consider increasing this value. - Allowed values are 1-2400. - Default value when not specified in API or module is interpreted by Avi Controller as 4. - - Units(SEC). send_interval: description: - Frequency, in seconds, that monitors are sent to a server. - Allowed values are 1-3600. - Default value when not specified in API or module is interpreted by Avi Controller as 10. - - Units(SEC). + sip_monitor: + description: + - Health monitor for sip. + - Field introduced in 17.2.8, 18.1.3, 18.2.1. + version_added: "2.9" successful_checks: description: - Number of continuous successful health checks before server is marked up. @@ -110,7 +118,7 @@ options: description: - Type of the health monitor. - Enum options - HEALTH_MONITOR_PING, HEALTH_MONITOR_TCP, HEALTH_MONITOR_HTTP, HEALTH_MONITOR_HTTPS, HEALTH_MONITOR_EXTERNAL, HEALTH_MONITOR_UDP, - - HEALTH_MONITOR_DNS, HEALTH_MONITOR_GSLB. + - HEALTH_MONITOR_DNS, HEALTH_MONITOR_GSLB, HEALTH_MONITOR_SIP, HEALTH_MONITOR_RADIUS. required: true udp_monitor: description: @@ -154,7 +162,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -175,8 +183,10 @@ def main(): is_federated=dict(type='bool',), monitor_port=dict(type='int',), name=dict(type='str', required=True), + radius_monitor=dict(type='dict',), receive_timeout=dict(type='int',), send_interval=dict(type='int',), + sip_monitor=dict(type='dict',), successful_checks=dict(type='int',), tcp_monitor=dict(type='dict',), tenant_ref=dict(type='str',), @@ -190,7 +200,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'healthmonitor', set([])) diff --git a/lib/ansible/modules/network/avi/avi_httppolicyset.py b/lib/ansible/modules/network/avi/avi_httppolicyset.py index d31b75d6306..2ee9ae497f5 100644 --- a/lib/ansible/modules/network/avi/avi_httppolicyset.py +++ b/lib/ansible/modules/network/avi/avi_httppolicyset.py @@ -132,7 +132,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -161,7 +161,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'httppolicyset', set([])) diff --git a/lib/ansible/modules/network/avi/avi_ipaddrgroup.py b/lib/ansible/modules/network/avi/avi_ipaddrgroup.py index 033bbdbefc3..345bae5707d 100644 --- a/lib/ansible/modules/network/avi/avi_ipaddrgroup.py +++ b/lib/ansible/modules/network/avi/avi_ipaddrgroup.py @@ -120,7 +120,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -151,7 +151,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'ipaddrgroup', set([])) diff --git a/lib/ansible/modules/network/avi/avi_ipamdnsproviderprofile.py b/lib/ansible/modules/network/avi/avi_ipamdnsproviderprofile.py index 2cbc1270ac7..0d45535a5ef 100644 --- a/lib/ansible/modules/network/avi/avi_ipamdnsproviderprofile.py +++ b/lib/ansible/modules/network/avi/avi_ipamdnsproviderprofile.py @@ -74,6 +74,11 @@ options: description: - Name for the ipam/dns provider profile. required: true + oci_profile: + description: + - Provider details for oracle cloud. + - Field introduced in 18.2.1,18.1.3. + version_added: "2.9" openstack_profile: description: - Provider details if type is openstack. @@ -83,11 +88,17 @@ options: tenant_ref: description: - It is a reference to an object of type tenant. + tencent_profile: + description: + - Provider details for tencent cloud. + - Field introduced in 18.2.3. + version_added: "2.9" type: description: - Provider type for the ipam/dns provider profile. - Enum options - IPAMDNS_TYPE_INFOBLOX, IPAMDNS_TYPE_AWS, IPAMDNS_TYPE_OPENSTACK, IPAMDNS_TYPE_GCP, IPAMDNS_TYPE_INFOBLOX_DNS, IPAMDNS_TYPE_CUSTOM, - - IPAMDNS_TYPE_CUSTOM_DNS, IPAMDNS_TYPE_AZURE, IPAMDNS_TYPE_INTERNAL, IPAMDNS_TYPE_INTERNAL_DNS, IPAMDNS_TYPE_AWS_DNS, IPAMDNS_TYPE_AZURE_DNS. + - IPAMDNS_TYPE_CUSTOM_DNS, IPAMDNS_TYPE_AZURE, IPAMDNS_TYPE_OCI, IPAMDNS_TYPE_TENCENT, IPAMDNS_TYPE_INTERNAL, IPAMDNS_TYPE_INTERNAL_DNS, + - IPAMDNS_TYPE_AWS_DNS, IPAMDNS_TYPE_AZURE_DNS. required: true url: description: @@ -131,7 +142,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -151,9 +162,11 @@ def main(): infoblox_profile=dict(type='dict',), internal_profile=dict(type='dict',), name=dict(type='str', required=True), + oci_profile=dict(type='dict',), openstack_profile=dict(type='dict',), proxy_configuration=dict(type='dict',), tenant_ref=dict(type='str',), + tencent_profile=dict(type='dict',), type=dict(type='str', required=True), url=dict(type='str',), uuid=dict(type='str',), @@ -163,7 +176,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'ipamdnsproviderprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_l4policyset.py b/lib/ansible/modules/network/avi/avi_l4policyset.py index 02b820aa379..a02b85692d6 100644 --- a/lib/ansible/modules/network/avi/avi_l4policyset.py +++ b/lib/ansible/modules/network/avi/avi_l4policyset.py @@ -95,7 +95,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -121,7 +121,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'l4policyset', set([])) diff --git a/lib/ansible/modules/network/avi/avi_microservicegroup.py b/lib/ansible/modules/network/avi/avi_microservicegroup.py index 55f6f2f471b..4cf731a7d68 100644 --- a/lib/ansible/modules/network/avi/avi_microservicegroup.py +++ b/lib/ansible/modules/network/avi/avi_microservicegroup.py @@ -89,7 +89,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -114,7 +114,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'microservicegroup', set([])) diff --git a/lib/ansible/modules/network/avi/avi_network.py b/lib/ansible/modules/network/avi/avi_network.py index 57547664a59..48226d9d678 100644 --- a/lib/ansible/modules/network/avi/avi_network.py +++ b/lib/ansible/modules/network/avi/avi_network.py @@ -58,6 +58,13 @@ options: - When selected, excludes all discovered subnets in this network from consideration for virtual service placement. - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool + ip6_autocfg_enabled: + description: + - Enable ipv6 auto configuration. + - Field introduced in 18.1.1. + - Default value when not specified in API or module is interpreted by Avi Controller as True. + version_added: "2.9" + type: bool name: description: - Name of the object. @@ -111,7 +118,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -127,6 +134,7 @@ def main(): configured_subnets=dict(type='list',), dhcp_enabled=dict(type='bool',), exclude_discovered_subnets=dict(type='bool',), + ip6_autocfg_enabled=dict(type='bool',), name=dict(type='str', required=True), synced_from_se=dict(type='bool',), tenant_ref=dict(type='str',), @@ -141,7 +149,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'network', set([])) diff --git a/lib/ansible/modules/network/avi/avi_networkprofile.py b/lib/ansible/modules/network/avi/avi_networkprofile.py index 479560190d1..8ca6272b8c1 100644 --- a/lib/ansible/modules/network/avi/avi_networkprofile.py +++ b/lib/ansible/modules/network/avi/avi_networkprofile.py @@ -42,6 +42,14 @@ options: - Patch operation to use when using avi_api_update_method as patch. version_added: "2.5" choices: ["add", "replace", "delete"] + connection_mirror: + description: + - When enabled, avi mirrors all tcp fastpath connections to standby. + - Applicable only in legacy ha mode. + - Field introduced in 18.1.3,18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool description: description: - User defined description for the object. @@ -92,7 +100,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -104,6 +112,7 @@ def main(): avi_api_update_method=dict(default='put', choices=['put', 'patch']), avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), + connection_mirror=dict(type='bool',), description=dict(type='str',), name=dict(type='str', required=True), profile=dict(type='dict', required=True), @@ -116,7 +125,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'networkprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_networksecuritypolicy.py b/lib/ansible/modules/network/avi/avi_networksecuritypolicy.py index e87f1a03876..baa9823e66e 100644 --- a/lib/ansible/modules/network/avi/avi_networksecuritypolicy.py +++ b/lib/ansible/modules/network/avi/avi_networksecuritypolicy.py @@ -103,7 +103,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -129,7 +129,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'networksecuritypolicy', set([])) diff --git a/lib/ansible/modules/network/avi/avi_pkiprofile.py b/lib/ansible/modules/network/avi/avi_pkiprofile.py index d2b27b2207b..bd13b2f1e6d 100644 --- a/lib/ansible/modules/network/avi/avi_pkiprofile.py +++ b/lib/ansible/modules/network/avi/avi_pkiprofile.py @@ -114,7 +114,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -143,7 +143,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'pkiprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_pool.py b/lib/ansible/modules/network/avi/avi_pool.py index 3118617c857..25b21e9e684 100644 --- a/lib/ansible/modules/network/avi/avi_pool.py +++ b/lib/ansible/modules/network/avi/avi_pool.py @@ -45,13 +45,27 @@ options: a_pool: description: - Name of container cloud application that constitutes a pool in a a-b pool configuration, if different from vs app. + - Field deprecated in 18.1.2. ab_pool: description: - A/b pool configuration. + - Field deprecated in 18.1.2. ab_priority: description: - Priority of this pool in a a-b pool pair. - Internally used. + - Field deprecated in 18.1.2. + analytics_policy: + description: + - Determines analytics settings for the pool. + - Field introduced in 18.1.5, 18.2.1. + version_added: "2.9" + analytics_profile_ref: + description: + - Specifies settings related to analytics. + - It is a reference to an object of type analyticsprofile. + - Field introduced in 18.1.4,18.2.1. + version_added: "2.9" apic_epg_name: description: - Synchronize cisco apic epg members with pool servers. @@ -82,7 +96,6 @@ options: - Allowed values are 1-5000. - Special values are 0 - 'automatic'. - Default value when not specified in API or module is interpreted by Avi Controller as 0. - - Units(MILLISECONDS). cloud_config_cksum: description: - Checksum of cloud configuration for pool. @@ -90,6 +103,11 @@ options: cloud_ref: description: - It is a reference to an object of type cloud. + conn_pool_properties: + description: + - Connnection pool properties. + - Field introduced in 18.2.1. + version_added: "2.9" connection_ramp_duration: description: - Duration for which new connections will be gradually ramped up to a server recently brought online. @@ -97,7 +115,6 @@ options: - Allowed values are 1-300. - Special values are 0 - 'immediate'. - Default value when not specified in API or module is interpreted by Avi Controller as 10. - - Units(MIN). created_by: description: - Creator name. @@ -107,6 +124,16 @@ options: - The ssl checkbox enables avi to server encryption. - Allowed values are 1-65535. - Default value when not specified in API or module is interpreted by Avi Controller as 80. + delete_server_on_dns_refresh: + description: + - Indicates whether existing ips are disabled(false) or deleted(true) on dns hostname refreshdetail -- on a dns refresh, some ips set on pool may + - no longer be returned by the resolver. + - These ips are deleted from the pool when this knob is set to true. + - They are disabled, if the knob is set to false. + - Field introduced in 18.2.3. + - Default value when not specified in API or module is interpreted by Avi Controller as True. + version_added: "2.9" + type: bool description: description: - A description of the pool. @@ -138,7 +165,6 @@ options: - Periodicity of feedback for fewest tasks server selection algorithm. - Allowed values are 1-300. - Default value when not specified in API or module is interpreted by Avi Controller as 10. - - Units(SEC). graceful_disable_timeout: description: - Used to gracefully disable a server. @@ -146,7 +172,6 @@ options: - Allowed values are 1-7200. - Special values are 0 - 'immediate', -1 - 'infinite'. - Default value when not specified in API or module is interpreted by Avi Controller as 1. - - Units(MIN). gslb_sp_enabled: description: - Indicates if the pool is a site-persistence pool. @@ -181,7 +206,7 @@ options: - The load balancing algorithm will pick a server within the pool's list of available servers. - Enum options - LB_ALGORITHM_LEAST_CONNECTIONS, LB_ALGORITHM_ROUND_ROBIN, LB_ALGORITHM_FASTEST_RESPONSE, LB_ALGORITHM_CONSISTENT_HASH, - LB_ALGORITHM_LEAST_LOAD, LB_ALGORITHM_FEWEST_SERVERS, LB_ALGORITHM_RANDOM, LB_ALGORITHM_FEWEST_TASKS, LB_ALGORITHM_NEAREST_SERVER, - - LB_ALGORITHM_CORE_AFFINITY. + - LB_ALGORITHM_CORE_AFFINITY, LB_ALGORITHM_TOPOLOGY. - Default value when not specified in API or module is interpreted by Avi Controller as LB_ALGORITHM_LEAST_CONNECTIONS. lb_algorithm_consistent_hash_hdr: description: @@ -197,7 +222,8 @@ options: description: - Criteria used as a key for determining the hash between the client and server. - Enum options - LB_ALGORITHM_CONSISTENT_HASH_SOURCE_IP_ADDRESS, LB_ALGORITHM_CONSISTENT_HASH_SOURCE_IP_ADDRESS_AND_PORT, - - LB_ALGORITHM_CONSISTENT_HASH_URI, LB_ALGORITHM_CONSISTENT_HASH_CUSTOM_HEADER, LB_ALGORITHM_CONSISTENT_HASH_CUSTOM_STRING. + - LB_ALGORITHM_CONSISTENT_HASH_URI, LB_ALGORITHM_CONSISTENT_HASH_CUSTOM_HEADER, LB_ALGORITHM_CONSISTENT_HASH_CUSTOM_STRING, + - LB_ALGORITHM_CONSISTENT_HASH_CALLID. - Default value when not specified in API or module is interpreted by Avi Controller as LB_ALGORITHM_CONSISTENT_HASH_SOURCE_IP_ADDRESS. lookup_server_by_name: description: @@ -215,6 +241,16 @@ options: max_conn_rate_per_server: description: - Rate limit connections to each server. + min_health_monitors_up: + description: + - Minimum number of health monitors in up state to mark server up. + - Field introduced in 18.2.1, 17.2.12. + version_added: "2.9" + min_servers_up: + description: + - Minimum number of servers in up state for marking the pool up. + - Field introduced in 18.2.1, 17.2.12. + version_added: "2.9" name: description: - The name of the pool. @@ -240,6 +276,7 @@ options: prst_hdr_name: description: - Header name for custom header persistence. + - Field deprecated in 18.1.2. request_queue_depth: description: - Minimum number of requests to be queued when pool is full. @@ -264,12 +301,11 @@ options: description: - Server autoscale. - Not used anymore. - - Default value when not specified in API or module is interpreted by Avi Controller as False. + - Field deprecated in 18.1.2. type: bool server_count: description: - - Number of server_count. - - Default value when not specified in API or module is interpreted by Avi Controller as 0. + - Field deprecated in 18.2.1. server_name: description: - Fully qualified dns hostname which will be used in the tls sni extension in server connections if sni is enabled. @@ -277,10 +313,26 @@ options: server_reselect: description: - Server reselect configuration for http requests. + server_timeout: + description: + - Server timeout value specifies the time within which a server connection needs to be established and a request-response exchange completes + - between avi and the server. + - Value of 0 results in using default timeout of 60 minutes. + - Allowed values are 0-3600000. + - Field introduced in 18.1.5,18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 0. + version_added: "2.9" servers: description: - The pool directs load balanced traffic to this list of destination servers. - The servers can be configured by ip address, name, network or via ip address group. + service_metadata: + description: + - Metadata pertaining to the service provided by this pool. + - In openshift/kubernetes environments, app metadata info is stored. + - Any user input to this field will be overwritten by avi vantage. + - Field introduced in 17.2.14,18.1.5,18.2.1. + version_added: "2.9" sni_enabled: description: - Enable tls sni for server connections. @@ -365,7 +417,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -380,6 +432,8 @@ def main(): a_pool=dict(type='str',), ab_pool=dict(type='dict',), ab_priority=dict(type='int',), + analytics_policy=dict(type='dict',), + analytics_profile_ref=dict(type='str',), apic_epg_name=dict(type='str',), application_persistence_profile_ref=dict(type='str',), autoscale_launch_config_ref=dict(type='str',), @@ -389,9 +443,11 @@ def main(): capacity_estimation_ttfb_thresh=dict(type='int',), cloud_config_cksum=dict(type='str',), cloud_ref=dict(type='str',), + conn_pool_properties=dict(type='dict',), connection_ramp_duration=dict(type='int',), created_by=dict(type='str',), default_server_port=dict(type='int',), + delete_server_on_dns_refresh=dict(type='bool',), description=dict(type='str',), domain_name=dict(type='list',), east_west=dict(type='bool',), @@ -412,6 +468,8 @@ def main(): lookup_server_by_name=dict(type='bool',), max_concurrent_connections_per_server=dict(type='int',), max_conn_rate_per_server=dict(type='dict',), + min_health_monitors_up=dict(type='int',), + min_servers_up=dict(type='int',), name=dict(type='str', required=True), networks=dict(type='list',), nsx_securitygroup=dict(type='list',), @@ -426,7 +484,9 @@ def main(): server_count=dict(type='int',), server_name=dict(type='str',), server_reselect=dict(type='dict',), + server_timeout=dict(type='int',), servers=dict(type='list',), + service_metadata=dict(type='str',), sni_enabled=dict(type='bool',), ssl_key_and_certificate_ref=dict(type='str',), ssl_profile_ref=dict(type='str',), @@ -441,7 +501,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'pool', set([])) diff --git a/lib/ansible/modules/network/avi/avi_poolgroup.py b/lib/ansible/modules/network/avi/avi_poolgroup.py index 47390ef6fc2..95365ca58f1 100644 --- a/lib/ansible/modules/network/avi/avi_poolgroup.py +++ b/lib/ansible/modules/network/avi/avi_poolgroup.py @@ -88,6 +88,13 @@ options: - Uuid of the priority labels. - If not provided, pool group member priority label will be interpreted as a number with a larger number considered higher priority. - It is a reference to an object of type prioritylabels. + service_metadata: + description: + - Metadata pertaining to the service provided by this poolgroup. + - In openshift/kubernetes environments, app metadata info is stored. + - Any user input to this field will be overwritten by avi vantage. + - Field introduced in 17.2.14,18.1.5,18.2.1. + version_added: "2.9" tenant_ref: description: - It is a reference to an object of type tenant. @@ -121,7 +128,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -144,6 +151,7 @@ def main(): min_servers=dict(type='int',), name=dict(type='str', required=True), priority_labels_ref=dict(type='str',), + service_metadata=dict(type='str',), tenant_ref=dict(type='str',), url=dict(type='str',), uuid=dict(type='str',), @@ -153,7 +161,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'poolgroup', set([])) diff --git a/lib/ansible/modules/network/avi/avi_poolgroupdeploymentpolicy.py b/lib/ansible/modules/network/avi/avi_poolgroupdeploymentpolicy.py index 3f1bc1da573..95a1cddf2d6 100644 --- a/lib/ansible/modules/network/avi/avi_poolgroupdeploymentpolicy.py +++ b/lib/ansible/modules/network/avi/avi_poolgroupdeploymentpolicy.py @@ -46,9 +46,6 @@ options: - It will automatically disable old production pools once there is a new production candidate. - Default value when not specified in API or module is interpreted by Avi Controller as True. type: bool - cloud_ref: - description: - - It is a reference to an object of type cloud. description: description: - User defined description for the object. @@ -57,7 +54,6 @@ options: - Duration of evaluation period for automatic deployment. - Allowed values are 60-86400. - Default value when not specified in API or module is interpreted by Avi Controller as 300. - - Units(SEC). name: description: - The name of the pool group deployment policy. @@ -75,7 +71,6 @@ options: - Target traffic ratio before pool is made production. - Allowed values are 1-100. - Default value when not specified in API or module is interpreted by Avi Controller as 100. - - Units(RATIO). tenant_ref: description: - It is a reference to an object of type tenant. @@ -121,7 +116,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -134,7 +129,6 @@ def main(): choices=['put', 'patch']), avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), auto_disable_old_prod_pools=dict(type='bool',), - cloud_ref=dict(type='str',), description=dict(type='str',), evaluation_duration=dict(type='int',), name=dict(type='str', required=True), @@ -152,7 +146,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'poolgroupdeploymentpolicy', set([])) diff --git a/lib/ansible/modules/network/avi/avi_prioritylabels.py b/lib/ansible/modules/network/avi/avi_prioritylabels.py index 6e5668201cf..ff199a2db8a 100644 --- a/lib/ansible/modules/network/avi/avi_prioritylabels.py +++ b/lib/ansible/modules/network/avi/avi_prioritylabels.py @@ -87,7 +87,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -112,7 +112,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'prioritylabels', set([])) diff --git a/lib/ansible/modules/network/avi/avi_role.py b/lib/ansible/modules/network/avi/avi_role.py index 511b2e1b093..a1764603940 100644 --- a/lib/ansible/modules/network/avi/avi_role.py +++ b/lib/ansible/modules/network/avi/avi_role.py @@ -82,7 +82,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -105,7 +105,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'role', set([])) diff --git a/lib/ansible/modules/network/avi/avi_scheduler.py b/lib/ansible/modules/network/avi/avi_scheduler.py index 66efe3ecd97..93d0954e425 100644 --- a/lib/ansible/modules/network/avi/avi_scheduler.py +++ b/lib/ansible/modules/network/avi/avi_scheduler.py @@ -115,7 +115,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -146,7 +146,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'scheduler', set([])) diff --git a/lib/ansible/modules/network/avi/avi_seproperties.py b/lib/ansible/modules/network/avi/avi_seproperties.py index 02e4e10a1e0..db261b87e9c 100644 --- a/lib/ansible/modules/network/avi/avi_seproperties.py +++ b/lib/ansible/modules/network/avi/avi_seproperties.py @@ -82,7 +82,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -105,7 +105,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'seproperties', set([])) diff --git a/lib/ansible/modules/network/avi/avi_serverautoscalepolicy.py b/lib/ansible/modules/network/avi/avi_serverautoscalepolicy.py index e935bebe2d1..d6e2c823628 100644 --- a/lib/ansible/modules/network/avi/avi_serverautoscalepolicy.py +++ b/lib/ansible/modules/network/avi/avi_serverautoscalepolicy.py @@ -91,7 +91,6 @@ options: description: - Cooldown period during which no new scalein is triggered to allow previous scalein to successfully complete. - Default value when not specified in API or module is interpreted by Avi Controller as 300. - - Units(SEC). scaleout_alertconfig_refs: description: - Trigger scaleout when alerts due to any of these alert configurations are raised. @@ -100,7 +99,6 @@ options: description: - Cooldown period during which no new scaleout is triggered to allow previous scaleout to successfully complete. - Default value when not specified in API or module is interpreted by Avi Controller as 300. - - Units(SEC). tenant_ref: description: - It is a reference to an object of type tenant. @@ -139,7 +137,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -174,7 +172,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'serverautoscalepolicy', set([])) diff --git a/lib/ansible/modules/network/avi/avi_serviceengine.py b/lib/ansible/modules/network/avi/avi_serviceengine.py index 53a0703dffc..1d17c02bbf7 100644 --- a/lib/ansible/modules/network/avi/avi_serviceengine.py +++ b/lib/ansible/modules/network/avi/avi_serviceengine.py @@ -127,7 +127,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -163,7 +163,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'serviceengine', set([])) diff --git a/lib/ansible/modules/network/avi/avi_serviceenginegroup.py b/lib/ansible/modules/network/avi/avi_serviceenginegroup.py index b809394c96c..6cae7467240 100644 --- a/lib/ansible/modules/network/avi/avi_serviceenginegroup.py +++ b/lib/ansible/modules/network/avi/avi_serviceenginegroup.py @@ -42,11 +42,26 @@ options: - Patch operation to use when using avi_api_update_method as patch. version_added: "2.5" choices: ["add", "replace", "delete"] + accelerated_networking: + description: + - Enable accelerated networking option for azure se. + - Accelerated networking enables single root i/o virtualization (sr-iov) to a se vm. + - This improves networking performance. + - Field introduced in 17.2.14,18.1.5,18.2.1. + version_added: "2.9" + type: bool active_standby: description: - Service engines in active/standby mode for ha failover. - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool + additional_config_memory: + description: + - Indicates the percent of config memory used for config updates. + - Allowed values are 0-90. + - Field deprecated in 18.1.2. + - Field introduced in 18.1.1. + version_added: "2.9" advertise_backend_networks: description: - Advertise reach-ability of backend server networks via adc through bgp for default gateway feature. @@ -68,12 +83,28 @@ options: - Field introduced in 17.2.5. version_added: "2.5" type: bool + app_cache_percent: + description: + - A percent value of total se memory reserved for application caching. + - This is an se bootup property and requires se restart. + - Allowed values are 0 - 100. + - Special values are 0- 'disable'. + - Field introduced in 18.2.3. + - Default value when not specified in API or module is interpreted by Avi Controller as 0. + version_added: "2.9" + app_learning_memory_percent: + description: + - A percent value of total se memory reserved for application learning. + - This is an se bootup property and requires se restart. + - Allowed values are 0 - 10. + - Field introduced in 18.2.3. + - Default value when not specified in API or module is interpreted by Avi Controller as 0. + version_added: "2.9" archive_shm_limit: description: - Amount of se memory in gb until which shared memory is collected in core archive. - Field introduced in 17.1.3. - Default value when not specified in API or module is interpreted by Avi Controller as 8. - - Units(GB). async_ssl: description: - Ssl handshakes will be handled by dedicated ssl threads. @@ -107,13 +138,19 @@ options: description: - Frequency of rebalance, if 'auto rebalance' is enabled. - Default value when not specified in API or module is interpreted by Avi Controller as 300. - - Units(SEC). auto_redistribute_active_standby_load: description: - Redistribution of virtual services from the takeover se to the replacement se can cause momentary traffic loss. - If the auto-redistribute load option is left in its default off state, any desired rebalancing requires calls to rest api. - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool + bgp_state_update_interval: + description: + - Bgp peer state update interval. + - Allowed values are 5-100. + - Field introduced in 17.2.14,18.1.5,18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 10. + version_added: "2.9" buffer_se: description: - Excess service engine capacity provisioned for ha failover. @@ -121,13 +158,19 @@ options: cloud_ref: description: - It is a reference to an object of type cloud. + config_debugs_on_all_cores: + description: + - Enable config debugs on all cores of se. + - Field introduced in 17.2.13,18.1.5,18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool connection_memory_percentage: description: - Percentage of memory for connection state. - This will come at the expense of memory used for http in-memory cache. - Allowed values are 10-90. - Default value when not specified in API or module is interpreted by Avi Controller as 50. - - Units(PERCENT). cpu_reserve: description: - Boolean flag to set cpu_reserve. @@ -151,6 +194,19 @@ options: description: - Custom tag will be used to create the tags for se instance in aws. - Note this is not the same as the prefix for se name. + data_network_id: + description: + - Subnet used to spin up the data nic for service engines, used only for azure cloud. + - Overrides the cloud level setting for service engine subnet. + - Field introduced in 18.2.3. + version_added: "2.9" + datascript_timeout: + description: + - Number of instructions before datascript times out. + - Allowed values are 0-100000000. + - Field introduced in 18.2.3. + - Default value when not specified in API or module is interpreted by Avi Controller as 1000000. + version_added: "2.9" dedicated_dispatcher_core: description: - Dedicate the core that handles packet receive/transmit from the network to just the dispatching function. @@ -160,10 +216,20 @@ options: description: description: - User defined description for the object. + disable_avi_securitygroups: + description: + - By default, avi creates and manages security groups along with custom sg provided by user. + - Set this to true to disallow avi to create and manage new security groups. + - Avi will only make use of custom security groups provided by user. + - This option is only supported for aws cloud type. + - Field introduced in 17.2.13,18.1.4,18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool disable_csum_offloads: description: - Stop using tcp/udp and ip checksum offload features of nics. - - Field introduced in 17.1.14, 17.2.5. + - Field introduced in 17.1.14, 17.2.5, 18.1.1. - Default value when not specified in API or module is interpreted by Avi Controller as False. version_added: "2.5" type: bool @@ -171,15 +237,22 @@ options: description: - Disable generic receive offload (gro) in dpdk poll-mode driver packet receive path. - Gro is on by default on nics that do not support lro (large receive offload) or do not gain performance boost from lro. - - Field introduced in 17.2.5. + - Field introduced in 17.2.5, 18.1.1. - Default value when not specified in API or module is interpreted by Avi Controller as True. version_added: "2.5" type: bool + disable_se_memory_check: + description: + - If set, disable the config memory check done in service engine. + - Field introduced in 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool disable_tso: description: - Disable tcp segmentation offload (tso) in dpdk poll-mode driver packet transmit path. - Tso is on by default on nics that support it. - - Field introduced in 17.2.5. + - Field introduced in 17.2.5, 18.1.1. - Default value when not specified in API or module is interpreted by Avi Controller as True. version_added: "2.5" type: bool @@ -187,21 +260,35 @@ options: description: - Amount of disk space for each of the service engine virtual machines. - Default value when not specified in API or module is interpreted by Avi Controller as 10. - - Units(GB). distribute_load_active_standby: description: - Use both the active and standby service engines for virtual service placement in the legacy active standby ha mode. - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool + distribute_queues: + description: + - Distributes queue ownership among cores so multiple cores handle dispatcher duties. + - Field introduced in 17.2.8. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool enable_hsm_priming: description: - (this is a beta feature). - Enable hsm key priming. - If enabled, key handles on the hsm will be synced to se before processing client connections. - - Field introduced in 17.2.7. + - Field introduced in 17.2.7, 18.1.1. - Default value when not specified in API or module is interpreted by Avi Controller as False. version_added: "2.6" type: bool + enable_multi_lb: + description: + - Applicable only for azure cloud with basic sku lb. + - If set, additional azure lbs will be automatically created if resources in existing lb are exhausted. + - Field introduced in 17.2.10, 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool enable_routing: description: - Enable routing for this serviceenginegroup . @@ -218,6 +305,16 @@ options: - Use virtual mac address for interfaces on which floating interface ips are placed. - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool + ephemeral_portrange_end: + description: + - End local ephemeral port number for outbound connections. + - Field introduced in 17.2.13, 18.1.5, 18.2.1. + version_added: "2.9" + ephemeral_portrange_start: + description: + - Start local ephemeral port number for outbound connections. + - Field introduced in 17.2.13, 18.1.5, 18.2.1. + version_added: "2.9" extra_config_multiplier: description: - Multiplier for extra config to support large vs/pool config. @@ -227,7 +324,6 @@ options: - Extra config memory to support large geo db configuration. - Field introduced in 17.1.1. - Default value when not specified in API or module is interpreted by Avi Controller as 0. - - Units(MB). floating_intf_ip: description: - If serviceenginegroup is configured for legacy 1+1 active standby ha mode, floating ip's will be advertised only by the active se in the pair. @@ -244,6 +340,12 @@ options: - Field introduced in 17.2.5. - Default value when not specified in API or module is interpreted by Avi Controller as 0. version_added: "2.5" + free_list_size: + description: + - Number of entries in the free list. + - Field introduced in 17.2.10, 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as 1024. + version_added: "2.9" ha_mode: description: - High availability mode for all the virtual services using this service engine group. @@ -252,6 +354,13 @@ options: hardwaresecuritymodulegroup_ref: description: - It is a reference to an object of type hardwaresecuritymodulegroup. + heap_minimum_config_memory: + description: + - Minimum required heap memory to apply any configuration. + - Allowed values are 0-100. + - Field introduced in 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as 8. + version_added: "2.9" hm_on_standby: description: - Enable active health monitoring from the standby se for all placed virtual services. @@ -288,7 +397,6 @@ options: - Ignore rtt samples if it is above threshold. - Field introduced in 17.1.6,17.2.2. - Default value when not specified in API or module is interpreted by Avi Controller as 5000. - - Units(MILLISECONDS). version_added: "2.5" ingress_access_data: description: @@ -306,7 +414,7 @@ options: version_added: "2.5" instance_flavor: description: - - Instance/flavor type for se instance. + - Instance/flavor name for se instance. iptables: description: - Iptable rules. @@ -325,7 +433,7 @@ options: license_type: description: - If no license type is specified then default license enforcement for the cloud type is chosen. - - Enum options - LIC_BACKEND_SERVERS, LIC_SOCKETS, LIC_CORES, LIC_HOSTS, LIC_SE_BANDWIDTH. + - Enum options - LIC_BACKEND_SERVERS, LIC_SOCKETS, LIC_CORES, LIC_HOSTS, LIC_SE_BANDWIDTH, LIC_METERED_SE_BANDWIDTH. - Field introduced in 17.2.5. version_added: "2.5" log_disksz: @@ -333,14 +441,32 @@ options: - Maximum disk capacity (in mb) to be allocated to an se. - This is exclusively used for debug and log data. - Default value when not specified in API or module is interpreted by Avi Controller as 10000. - - Units(MB). max_cpu_usage: description: - When cpu usage on an se exceeds this threshold, virtual services hosted on this se may be rebalanced to other ses to reduce load. - A new se may be created as part of this process. - Allowed values are 40-90. - Default value when not specified in API or module is interpreted by Avi Controller as 80. - - Units(PERCENT). + max_memory_per_mempool: + description: + - Max bytes that can be allocated in a single mempool. + - Field introduced in 18.1.5. + - Default value when not specified in API or module is interpreted by Avi Controller as 64. + version_added: "2.9" + max_public_ips_per_lb: + description: + - Applicable to azure platform only. + - Maximum number of public ips per azure lb. + - Field introduced in 17.2.12, 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as 30. + version_added: "2.9" + max_rules_per_lb: + description: + - Applicable to azure platform only. + - Maximum number of rules per azure lb. + - Field introduced in 17.2.12, 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as 150. + version_added: "2.9" max_scaleout_per_vs: description: - Maximum number of active service engines for the virtual service. @@ -362,6 +488,13 @@ options: - Boolean flag to set mem_reserve. - Default value when not specified in API or module is interpreted by Avi Controller as True. type: bool + memory_for_config_update: + description: + - Indicates the percent of memory reserved for config updates. + - Allowed values are 0-100. + - Field introduced in 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as 15. + version_added: "2.9" memory_per_se: description: - Amount of memory for each of the service engine virtual machines. @@ -379,12 +512,39 @@ options: - After consolidation, unused service engines may then be eligible for deletion. - Allowed values are 20-60. - Default value when not specified in API or module is interpreted by Avi Controller as 30. - - Units(PERCENT). min_scaleout_per_vs: description: - Minimum number of active service engines for the virtual service. - Allowed values are 1-64. - Default value when not specified in API or module is interpreted by Avi Controller as 1. + min_se: + description: + - Minimum number of services engines in this group (relevant for se autorebalance only). + - Allowed values are 0-1000. + - Field introduced in 17.2.13,18.1.3,18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 1. + version_added: "2.9" + minimum_connection_memory: + description: + - Indicates the percent of memory reserved for connections. + - Allowed values are 0-100. + - Field introduced in 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as 20. + version_added: "2.9" + minimum_required_config_memory: + description: + - Required available config memory to apply any configuration. + - Allowed values are 0-90. + - Field deprecated in 18.1.2. + - Field introduced in 18.1.1. + version_added: "2.9" + n_log_streaming_threads: + description: + - Number of threads to use for log streaming. + - Allowed values are 1-100. + - Field introduced in 17.2.12, 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as 1. + version_added: "2.9" name: description: - Name of the object. @@ -396,7 +556,14 @@ options: - Set it to zero (0) to disable throttling. - Field introduced in 17.1.3. - Default value when not specified in API or module is interpreted by Avi Controller as 100. - - Units(PER_SECOND). + num_dispatcher_cores: + description: + - Number of dispatcher cores (0,1,2,4,8 or 16). + - If set to 0, then number of dispatcher cores is deduced automatically. + - Allowed values are 0,1,2,4,8,16. + - Field introduced in 17.2.12, 18.1.3, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 0. + version_added: "2.9" num_flow_cores_sum_changes_to_ignore: description: - Number of changes in num flow cores sum to ignore. @@ -432,6 +599,13 @@ options: realtime_se_metrics: description: - Enable or disable real time se metrics. + reboot_on_stop: + description: + - Reboot the system if the se is stopped. + - Field introduced in 17.2.16,18.2.3. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool se_bandwidth_type: description: - Select the se bandwidth for the bandwidth license. @@ -445,10 +619,31 @@ options: - If this value is set to 0, controller will never delete any ses and administrator has to manually cleanup unused ses. - Allowed values are 0-525600. - Default value when not specified in API or module is interpreted by Avi Controller as 120. - - Units(MIN). se_dos_profile: description: - Dosthresholdprofile settings for serviceenginegroup. + se_dpdk_pmd: + description: + - Determines if dpdk pool mode driver should be used or not 0 automatically determine based on hypervisor/nic type 1 unconditionally use dpdk + - poll mode driver 2 don't use dpdk poll mode driver. + - Allowed values are 0-2. + - Field introduced in 18.1.3. + - Default value when not specified in API or module is interpreted by Avi Controller as 0. + version_added: "2.9" + se_flow_probe_retries: + description: + - Flow probe retry count if no replies are received. + - Allowed values are 0-5. + - Field introduced in 18.1.4, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 2. + version_added: "2.9" + se_flow_probe_timer: + description: + - Timeout in milliseconds for flow probe entries. + - Allowed values are 10-200. + - Field introduced in 18.1.4, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 100. + version_added: "2.9" se_ipc_udp_port: description: - Udp port for se_dp ipc in docker bridge mode. @@ -459,6 +654,33 @@ options: description: - Prefix to use for virtual machine name of service engines. - Default value when not specified in API or module is interpreted by Avi Controller as Avi. + se_pcap_lookahead: + description: + - Enables lookahead mode of packet receive in pcap mode. + - Introduced to overcome an issue with hv_netvsc driver. + - Lookahead mode attempts to ensure that application and kernel's view of the receive rings are consistent. + - Field introduced in 18.2.3. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool + se_pcap_reinit_frequency: + description: + - Frequency in seconds at which periodically a pcap reinit check is triggered. + - May be used in conjunction with the configuration pcap_reinit_threshold. + - (valid range 15 mins - 12 hours, 0 - disables). + - Allowed values are 900-43200. + - Special values are 0- 'disable'. + - Field introduced in 17.2.13, 18.1.3, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 0. + version_added: "2.9" + se_pcap_reinit_threshold: + description: + - Threshold for input packet receive errors in pcap mode exceeding which a pcap reinit is triggered. + - If not set, an unconditional reinit is performed. + - This value is checked every pcap_reinit_frequency interval. + - Field introduced in 17.2.13, 18.1.3, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 0. + version_added: "2.9" se_probe_port: description: - Tcp port on se where echo service will be run. @@ -471,6 +693,15 @@ options: - Field introduced in 17.1.2. - Default value when not specified in API or module is interpreted by Avi Controller as 1501. version_added: "2.4" + se_routing: + description: + - Enable routing via service engine datapath. + - When disabled, routing is done by the linux kernel. + - Ip routing needs to be enabled in service engine group for se routing to be effective. + - Field introduced in 18.2.3. + - Default value when not specified in API or module is interpreted by Avi Controller as True. + version_added: "2.9" + type: bool se_sb_dedicated_core: description: - Sideband traffic will be handled by a dedicated core. @@ -490,11 +721,17 @@ options: - Multiplier for se threads based on vcpu. - Allowed values are 1-10. - Default value when not specified in API or module is interpreted by Avi Controller as 1. + se_tracert_port_range: + description: + - Traceroute port range. + - Field introduced in 17.2.8. + version_added: "2.9" se_tunnel_mode: description: - Determines if dsr from secondary se is active or not 0 automatically determine based on hypervisor type. - 1 disable dsr unconditionally. - - ~[0,1] enable dsr unconditionally. + - 2 enable dsr unconditionally. + - Allowed values are 0-2. - Field introduced in 17.1.1. - Default value when not specified in API or module is interpreted by Avi Controller as 0. se_tunnel_udp_port: @@ -504,29 +741,57 @@ options: - Default value when not specified in API or module is interpreted by Avi Controller as 1550. se_udp_encap_ipc: description: - - Determines if se-se ipc messages are encapsulated in an udp header 0 automatically determine based on hypervisor type. + - Determines if se-se ipc messages are encapsulated in a udp header 0 automatically determine based on hypervisor type. - 1 use udp encap unconditionally. - - ~[0,1] don't use udp encap. + - Allowed values are 0-1. - Field introduced in 17.1.2. - Default value when not specified in API or module is interpreted by Avi Controller as 0. version_added: "2.4" + se_use_dpdk: + description: + - Determines if dpdk library should be used or not 0 automatically determine based on hypervisor type 1 use dpdk if pcap is not enabled 2 + - don't use dpdk. + - Allowed values are 0-2. + - Field introduced in 18.1.3. + - Default value when not specified in API or module is interpreted by Avi Controller as 0. + version_added: "2.9" se_vs_hb_max_pkts_in_batch: description: - Maximum number of aggregated vs heartbeat packets to send in a batch. - Allowed values are 1-256. - Field introduced in 17.1.1. - - Default value when not specified in API or module is interpreted by Avi Controller as 8. + - Default value when not specified in API or module is interpreted by Avi Controller as 64. se_vs_hb_max_vs_in_pkt: description: - Maximum number of virtualservices for which heartbeat messages are aggregated in one packet. - Allowed values are 1-1024. - Field introduced in 17.1.1. - Default value when not specified in API or module is interpreted by Avi Controller as 256. + self_se_election: + description: + - Enable ses to elect a primary amongst themselves in the absence of a connectivity to controller. + - Field introduced in 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool + service_ip6_subnets: + description: + - Ipv6 subnets assigned to the se group. + - Required for vs group placement. + - Field introduced in 18.1.1. + version_added: "2.9" service_ip_subnets: description: - Subnets assigned to the se group. - Required for vs group placement. - Field introduced in 17.1.1. + shm_minimum_config_memory: + description: + - Minimum required shared memory to apply any configuration. + - Allowed values are 0-100. + - Field introduced in 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as 4. + version_added: "2.9" significant_log_throttle: description: - This setting limits the number of significant logs generated per second per core on this se. @@ -534,7 +799,14 @@ options: - Set it to zero (0) to disable throttling. - Field introduced in 17.1.3. - Default value when not specified in API or module is interpreted by Avi Controller as 100. - - Units(PER_SECOND). + ssl_preprocess_sni_hostname: + description: + - (beta) preprocess ssl client hello for sni hostname extension.if set to true, this will apply sni child's ssl protocol(s), if they are different + - from sni parent's allowed ssl protocol(s). + - Field introduced in 17.2.12, 18.1.3. + - Default value when not specified in API or module is interpreted by Avi Controller as True. + version_added: "2.9" + type: bool tenant_ref: description: - It is a reference to an object of type tenant. @@ -546,10 +818,17 @@ options: - Set it to zero (0) to disable throttling. - Field introduced in 17.1.3. - Default value when not specified in API or module is interpreted by Avi Controller as 100. - - Units(PER_SECOND). url: description: - Avi controller URL of the object. + use_standard_alb: + description: + - Use standard sku azure load balancer. + - By default cloud level flag is set. + - If not set, it inherits/uses the use_standard_alb flag from the cloud. + - Field introduced in 18.2.3. + version_added: "2.9" + type: bool uuid: description: - Unique object identifier of the object. @@ -579,6 +858,11 @@ options: description: - Number of vcpus for each of the service engine virtual machines. - Default value when not specified in API or module is interpreted by Avi Controller as 1. + vip_asg: + description: + - When vip_asg is set, vip configuration will be managed by avi.user will be able to configure vip_asg or vips individually at the time of create. + - Field introduced in 17.2.12, 18.1.2. + version_added: "2.9" vs_host_redundancy: description: - Ensure primary and secondary service engines are deployed on different physical hosts. @@ -588,22 +872,64 @@ options: description: - Time to wait for the scaled in se to drain existing flows before marking the scalein done. - Default value when not specified in API or module is interpreted by Avi Controller as 30. - - Units(SEC). vs_scalein_timeout_for_upgrade: description: - During se upgrade, time to wait for the scaled-in se to drain existing flows before marking the scalein done. - Default value when not specified in API or module is interpreted by Avi Controller as 30. - - Units(SEC). vs_scaleout_timeout: description: - Time to wait for the scaled out se to become ready before marking the scaleout done. - - Default value when not specified in API or module is interpreted by Avi Controller as 30. - - Units(SEC). + - Default value when not specified in API or module is interpreted by Avi Controller as 600. + vs_se_scaleout_additional_wait_time: + description: + - Wait time for sending scaleout ready notification after virtual service is marked up. + - In certain deployments, there may be an additional delay to accept traffic. + - For example, for bgp, some time is needed for route advertisement. + - Allowed values are 0-20. + - Field introduced in 18.1.5,18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 0. + version_added: "2.9" + vs_se_scaleout_ready_timeout: + description: + - Timeout in seconds for service engine to sendscaleout ready notification of a virtual service. + - Allowed values are 0-60. + - Field introduced in 18.1.5,18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 25. + version_added: "2.9" + vs_switchover_timeout: + description: + - During se upgrade in a legacy active/standby segroup, time to wait for the new primary se to accept flows before marking the switchover done. + - Field introduced in 17.2.13,18.1.4,18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as 300. + version_added: "2.9" vss_placement: description: - - If set, virtual services will be placed on only a subset of the cores of an se. + - Parameters to place virtual services on only a subset of the cores of an se. - Field introduced in 17.2.5. version_added: "2.5" + vss_placement_enabled: + description: + - If set, virtual services will be placed on only a subset of the cores of an se. + - Field introduced in 18.1.1. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool + waf_learning_interval: + description: + - Frequency with which se publishes waf learning. + - Allowed values are 1-43200. + - Field deprecated in 18.2.3. + - Field introduced in 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as 10. + version_added: "2.9" + waf_learning_memory: + description: + - Amount of memory reserved on se for waf learning. + - This can be atmost 5% of se memory. + - Field deprecated in 18.2.3. + - Field introduced in 18.1.2. + - Default value when not specified in API or module is interpreted by Avi Controller as 0. + version_added: "2.9" waf_mempool: description: - Enable memory pool for waf. @@ -616,7 +942,6 @@ options: - Memory pool size used for waf. - Field introduced in 17.2.3. - Default value when not specified in API or module is interpreted by Avi Controller as 64. - - Units(KB). version_added: "2.5" extends_documentation_fragment: - avi @@ -642,7 +967,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -654,11 +979,15 @@ def main(): avi_api_update_method=dict(default='put', choices=['put', 'patch']), avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), + accelerated_networking=dict(type='bool',), active_standby=dict(type='bool',), + additional_config_memory=dict(type='int',), advertise_backend_networks=dict(type='bool',), aggressive_failure_detection=dict(type='bool',), algo=dict(type='str',), allow_burst=dict(type='bool',), + app_cache_percent=dict(type='int',), + app_learning_memory_percent=dict(type='int',), archive_shm_limit=dict(type='int',), async_ssl=dict(type='bool',), async_ssl_threads=dict(type='int',), @@ -667,32 +996,44 @@ def main(): auto_rebalance_criteria=dict(type='list',), auto_rebalance_interval=dict(type='int',), auto_redistribute_active_standby_load=dict(type='bool',), + bgp_state_update_interval=dict(type='int',), buffer_se=dict(type='int',), cloud_ref=dict(type='str',), + config_debugs_on_all_cores=dict(type='bool',), connection_memory_percentage=dict(type='int',), cpu_reserve=dict(type='bool',), cpu_socket_affinity=dict(type='bool',), custom_securitygroups_data=dict(type='list',), custom_securitygroups_mgmt=dict(type='list',), custom_tag=dict(type='list',), + data_network_id=dict(type='str',), + datascript_timeout=dict(type='int',), dedicated_dispatcher_core=dict(type='bool',), description=dict(type='str',), + disable_avi_securitygroups=dict(type='bool',), disable_csum_offloads=dict(type='bool',), disable_gro=dict(type='bool',), + disable_se_memory_check=dict(type='bool',), disable_tso=dict(type='bool',), disk_per_se=dict(type='int',), distribute_load_active_standby=dict(type='bool',), + distribute_queues=dict(type='bool',), enable_hsm_priming=dict(type='bool',), + enable_multi_lb=dict(type='bool',), enable_routing=dict(type='bool',), enable_vip_on_all_interfaces=dict(type='bool',), enable_vmac=dict(type='bool',), + ephemeral_portrange_end=dict(type='int',), + ephemeral_portrange_start=dict(type='int',), extra_config_multiplier=dict(type='float',), extra_shared_config_memory=dict(type='int',), floating_intf_ip=dict(type='list',), floating_intf_ip_se_2=dict(type='list',), flow_table_new_syn_max_entries=dict(type='int',), + free_list_size=dict(type='int',), ha_mode=dict(type='str',), hardwaresecuritymodulegroup_ref=dict(type='str',), + heap_minimum_config_memory=dict(type='int',), hm_on_standby=dict(type='bool',), host_attribute_key=dict(type='str',), host_attribute_value=dict(type='str',), @@ -708,17 +1049,26 @@ def main(): license_type=dict(type='str',), log_disksz=dict(type='int',), max_cpu_usage=dict(type='int',), + max_memory_per_mempool=dict(type='int',), + max_public_ips_per_lb=dict(type='int',), + max_rules_per_lb=dict(type='int',), max_scaleout_per_vs=dict(type='int',), max_se=dict(type='int',), max_vs_per_se=dict(type='int',), mem_reserve=dict(type='bool',), + memory_for_config_update=dict(type='int',), memory_per_se=dict(type='int',), mgmt_network_ref=dict(type='str',), mgmt_subnet=dict(type='dict',), min_cpu_usage=dict(type='int',), min_scaleout_per_vs=dict(type='int',), + min_se=dict(type='int',), + minimum_connection_memory=dict(type='int',), + minimum_required_config_memory=dict(type='int',), + n_log_streaming_threads=dict(type='int',), name=dict(type='str', required=True), non_significant_log_throttle=dict(type='int',), + num_dispatcher_cores=dict(type='int',), num_flow_cores_sum_changes_to_ignore=dict(type='int',), openstack_availability_zone=dict(type='str',), openstack_availability_zones=dict(type='list',), @@ -728,26 +1078,41 @@ def main(): per_app=dict(type='bool',), placement_mode=dict(type='str',), realtime_se_metrics=dict(type='dict',), + reboot_on_stop=dict(type='bool',), se_bandwidth_type=dict(type='str',), se_deprovision_delay=dict(type='int',), se_dos_profile=dict(type='dict',), + se_dpdk_pmd=dict(type='int',), + se_flow_probe_retries=dict(type='int',), + se_flow_probe_timer=dict(type='int',), se_ipc_udp_port=dict(type='int',), se_name_prefix=dict(type='str',), + se_pcap_lookahead=dict(type='bool',), + se_pcap_reinit_frequency=dict(type='int',), + se_pcap_reinit_threshold=dict(type='int',), se_probe_port=dict(type='int',), se_remote_punt_udp_port=dict(type='int',), + se_routing=dict(type='bool',), se_sb_dedicated_core=dict(type='bool',), se_sb_threads=dict(type='int',), se_thread_multiplier=dict(type='int',), + se_tracert_port_range=dict(type='dict',), se_tunnel_mode=dict(type='int',), se_tunnel_udp_port=dict(type='int',), se_udp_encap_ipc=dict(type='int',), + se_use_dpdk=dict(type='int',), se_vs_hb_max_pkts_in_batch=dict(type='int',), se_vs_hb_max_vs_in_pkt=dict(type='int',), + self_se_election=dict(type='bool',), + service_ip6_subnets=dict(type='list',), service_ip_subnets=dict(type='list',), + shm_minimum_config_memory=dict(type='int',), significant_log_throttle=dict(type='int',), + ssl_preprocess_sni_hostname=dict(type='bool',), tenant_ref=dict(type='str',), udf_log_throttle=dict(type='int',), url=dict(type='str',), + use_standard_alb=dict(type='bool',), uuid=dict(type='str',), vcenter_clusters=dict(type='dict',), vcenter_datastore_mode=dict(type='str',), @@ -756,11 +1121,18 @@ def main(): vcenter_folder=dict(type='str',), vcenter_hosts=dict(type='dict',), vcpus_per_se=dict(type='int',), + vip_asg=dict(type='dict',), vs_host_redundancy=dict(type='bool',), vs_scalein_timeout=dict(type='int',), vs_scalein_timeout_for_upgrade=dict(type='int',), vs_scaleout_timeout=dict(type='int',), + vs_se_scaleout_additional_wait_time=dict(type='int',), + vs_se_scaleout_ready_timeout=dict(type='int',), + vs_switchover_timeout=dict(type='int',), vss_placement=dict(type='dict',), + vss_placement_enabled=dict(type='bool',), + waf_learning_interval=dict(type='int',), + waf_learning_memory=dict(type='int',), waf_mempool=dict(type='bool',), waf_mempool_size=dict(type='int',), ) @@ -769,7 +1141,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'serviceenginegroup', set([])) diff --git a/lib/ansible/modules/network/avi/avi_snmptrapprofile.py b/lib/ansible/modules/network/avi/avi_snmptrapprofile.py index 140f1b282c8..c49e04c4464 100644 --- a/lib/ansible/modules/network/avi/avi_snmptrapprofile.py +++ b/lib/ansible/modules/network/avi/avi_snmptrapprofile.py @@ -81,7 +81,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -104,7 +104,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'snmptrapprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_sslkeyandcertificate.py b/lib/ansible/modules/network/avi/avi_sslkeyandcertificate.py index f500bd65d46..8b96fae24c1 100644 --- a/lib/ansible/modules/network/avi/avi_sslkeyandcertificate.py +++ b/lib/ansible/modules/network/avi/avi_sslkeyandcertificate.py @@ -49,6 +49,13 @@ options: description: - Sslcertificate settings for sslkeyandcertificate. required: true + certificate_base64: + description: + - States if the certificate is base64 encoded. + - Field introduced in 18.1.2, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool certificate_management_profile_ref: description: - It is a reference to an object of type certificatemanagementprofile. @@ -66,15 +73,34 @@ options: description: - Name of the encrypted private key (e.g. - Those generated by an hsm such as thales nshield). + format: + description: + - Format of the key/certificate file. + - Enum options - SSL_PEM, SSL_PKCS12. + - Field introduced in 18.1.2, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as SSL_PEM. + version_added: "2.9" hardwaresecuritymodulegroup_ref: description: - It is a reference to an object of type hardwaresecuritymodulegroup. key: description: - Private key. + key_base64: + description: + - States if the private key is base64 encoded. + - Field introduced in 18.1.2, 18.2.1. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool key_params: description: - Sslkeyparams settings for sslkeyandcertificate. + key_passphrase: + description: + - Passphrase used to encrypt the private key. + - Field introduced in 18.1.2, 18.2.1. + version_added: "2.9" name: description: - Name of the object. @@ -89,7 +115,6 @@ options: type: description: - Enum options - ssl_certificate_type_virtualservice, ssl_certificate_type_system, ssl_certificate_type_ca. - - Default value when not specified in API or module is interpreted by Avi Controller as SSL_CERTIFICATE_TYPE_VIRTUALSERVICE. url: description: - Avi controller URL of the object. @@ -130,7 +155,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -144,14 +169,18 @@ def main(): avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), ca_certs=dict(type='list',), certificate=dict(type='dict', required=True), + certificate_base64=dict(type='bool',), certificate_management_profile_ref=dict(type='str',), created_by=dict(type='str',), dynamic_params=dict(type='list',), enckey_base64=dict(type='str',), enckey_name=dict(type='str',), + format=dict(type='str',), hardwaresecuritymodulegroup_ref=dict(type='str',), key=dict(type='str', no_log=True,), + key_base64=dict(type='bool',), key_params=dict(type='dict',), + key_passphrase=dict(type='str', no_log=True,), name=dict(type='str', required=True), status=dict(type='str',), tenant_ref=dict(type='str',), @@ -164,10 +193,10 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'sslkeyandcertificate', - set(['key'])) + set(['key_passphrase', 'key'])) if __name__ == '__main__': diff --git a/lib/ansible/modules/network/avi/avi_sslprofile.py b/lib/ansible/modules/network/avi/avi_sslprofile.py index 9203cf11556..a4034622992 100644 --- a/lib/ansible/modules/network/avi/avi_sslprofile.py +++ b/lib/ansible/modules/network/avi/avi_sslprofile.py @@ -88,9 +88,8 @@ options: - Sslrating settings for sslprofile. ssl_session_timeout: description: - - The amount of time before an ssl session expires. + - The amount of time in seconds before an ssl session expires. - Default value when not specified in API or module is interpreted by Avi Controller as 86400. - - Units(SEC). tags: description: - List of tag. @@ -169,7 +168,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -203,7 +202,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'sslprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_stringgroup.py b/lib/ansible/modules/network/avi/avi_stringgroup.py index 44c065351df..6e1ed7fdfca 100644 --- a/lib/ansible/modules/network/avi/avi_stringgroup.py +++ b/lib/ansible/modules/network/avi/avi_stringgroup.py @@ -102,7 +102,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -127,7 +127,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'stringgroup', set([])) diff --git a/lib/ansible/modules/network/avi/avi_systemconfiguration.py b/lib/ansible/modules/network/avi/avi_systemconfiguration.py index 10782e9b108..9f74d3e8f5c 100644 --- a/lib/ansible/modules/network/avi/avi_systemconfiguration.py +++ b/lib/ansible/modules/network/avi/avi_systemconfiguration.py @@ -87,6 +87,11 @@ options: proxy_configuration: description: - Proxyconfiguration settings for systemconfiguration. + secure_channel_configuration: + description: + - Configure secure channel properties. + - Field introduced in 18.1.4, 18.2.1. + version_added: "2.9" snmp_configuration: description: - Snmpconfiguration settings for systemconfiguration. @@ -94,18 +99,23 @@ options: description: - Allowed ciphers list for ssh to the management interface on the controller and service engines. - If this is not specified, all the default ciphers are allowed. - - Ssh -q cipher provides the list of default ciphers supported. ssh_hmacs: description: - Allowed hmac list for ssh to the management interface on the controller and service engines. - If this is not specified, all the default hmacs are allowed. - - Ssh -q mac provides the list of default hmacs supported. url: description: - Avi controller URL of the object. uuid: description: - Unique object identifier of the object. + welcome_workflow_complete: + description: + - This flag is set once the initial controller setup workflow is complete. + - Field introduced in 18.2.3. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool extends_documentation_fragment: - avi ''' @@ -130,7 +140,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -154,18 +164,20 @@ def main(): ntp_configuration=dict(type='dict',), portal_configuration=dict(type='dict',), proxy_configuration=dict(type='dict',), + secure_channel_configuration=dict(type='dict',), snmp_configuration=dict(type='dict',), ssh_ciphers=dict(type='list',), ssh_hmacs=dict(type='list',), url=dict(type='str',), uuid=dict(type='str',), + welcome_workflow_complete=dict(type='bool',), ) argument_specs.update(avi_common_argument_spec()) module = AnsibleModule( argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'systemconfiguration', set([])) diff --git a/lib/ansible/modules/network/avi/avi_tenant.py b/lib/ansible/modules/network/avi/avi_tenant.py index e9db144ede6..6bad385d6b8 100644 --- a/lib/ansible/modules/network/avi/avi_tenant.py +++ b/lib/ansible/modules/network/avi/avi_tenant.py @@ -95,7 +95,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -120,7 +120,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'tenant', set([])) diff --git a/lib/ansible/modules/network/avi/avi_trafficcloneprofile.py b/lib/ansible/modules/network/avi/avi_trafficcloneprofile.py index 512d013a96b..b8aa2eb93d4 100644 --- a/lib/ansible/modules/network/avi/avi_trafficcloneprofile.py +++ b/lib/ansible/modules/network/avi/avi_trafficcloneprofile.py @@ -94,7 +94,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -119,7 +119,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'trafficcloneprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_useraccount.py b/lib/ansible/modules/network/avi/avi_useraccount.py index 600f07d7fab..99ed2b2d7d1 100644 --- a/lib/ansible/modules/network/avi/avi_useraccount.py +++ b/lib/ansible/modules/network/avi/avi_useraccount.py @@ -23,16 +23,15 @@ # """ + ANSIBLE_METADATA = {'metadata_version': '1.1', 'status': ['preview'], 'supported_by': 'community'} - DOCUMENTATION = ''' --- module: avi_useraccount author: Chaitanya Deshpande (@chaitanyaavi) - short_description: Avi UserAccount Module description: - This module can be used for updating the password of a user. @@ -43,13 +42,17 @@ options: old_password: description: - Old password for update password or default password for bootstrap. + force_change: + description: + - If specifically set to true then old password is tried first for controller and then the new password is + tried. If not specified this flag then the new password is tried first. + version_added: "2.9" extends_documentation_fragment: - avi ''' EXAMPLES = ''' - - name: Update user password avi_useraccount: controller: "" @@ -57,11 +60,13 @@ EXAMPLES = ''' password: new_password old_password: "" api_version: "" + force_change: false - name: Update user password using avi_credentials avi_useraccount: avi_credentials: "" old_password: "" + force_change: false ''' RETURN = ''' @@ -78,56 +83,70 @@ from copy import deepcopy try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, ansible_return, HAS_AVI) - from avi.sdk.avi_api import ApiSession, AviCredentials - from avi.sdk.utils.ansible_utils import avi_obj_cmp, cleanup_absent_fields - + avi_common_argument_spec, ansible_return, avi_obj_cmp, + cleanup_absent_fields, HAS_AVI) + from ansible.module_utils.network.avi.avi_api import ( + ApiSession, AviCredentials) except ImportError: HAS_AVI = False def main(): argument_specs = dict( - old_password=dict(type='str', required=True, no_log=True) + old_password=dict(type='str', required=True, no_log=True), + # Flag to specify priority of old/new password while establishing session with controller. + # To handle both Saas and conventional (Entire state in playbook) scenario. + force_change=dict(type='bool', default=False) ) argument_specs.update(avi_common_argument_spec()) module = AnsibleModule(argument_spec=argument_specs) - if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) - api_creds = AviCredentials() api_creds.update_from_ansible_module(module) - password_updated = False old_password = module.params.get('old_password') + force_change = module.params.get('force_change', False) data = { 'old_password': old_password, 'password': api_creds.password } + # First try old password if 'force_change' is set to true + if force_change: + first_pwd = old_password + second_pwd = api_creds.password + # First try new password if 'force_change' is set to false or not specified in playbook. + else: + first_pwd = api_creds.password + second_pwd = old_password password_changed = False try: api = ApiSession.get_session( api_creds.controller, api_creds.username, - password=api_creds.password, timeout=api_creds.timeout, + password=first_pwd, timeout=api_creds.timeout, tenant=api_creds.tenant, tenant_uuid=api_creds.tenant_uuid, token=api_creds.token, port=api_creds.port) - password_changed = True - return ansible_return(module, None, False, req=data) + if force_change: + rsp = api.put('useraccount', data=data) + if rsp: + password_changed = True except Exception: pass - if not password_changed: api = ApiSession.get_session( - api_creds.controller, api_creds.username, password=old_password, + api_creds.controller, api_creds.username, password=second_pwd, timeout=api_creds.timeout, tenant=api_creds.tenant, tenant_uuid=api_creds.tenant_uuid, token=api_creds.token, port=api_creds.port) - rsp = api.put('useraccount', data=data) - if rsp: - return ansible_return(module, rsp, True, req=data) - return module.exit_json(changed=False, obj=data) + if not force_change: + rsp = api.put('useraccount', data=data) + if rsp: + password_changed = True + if password_changed: + return ansible_return(module, rsp, True, req=data) + else: + return ansible_return(module, rsp, False, req=data) if __name__ == '__main__': diff --git a/lib/ansible/modules/network/avi/avi_useraccountprofile.py b/lib/ansible/modules/network/avi/avi_useraccountprofile.py index 65db0b5fc01..ce11486fdaa 100644 --- a/lib/ansible/modules/network/avi/avi_useraccountprofile.py +++ b/lib/ansible/modules/network/avi/avi_useraccountprofile.py @@ -47,13 +47,11 @@ options: - Lock timeout period (in minutes). - Default is 30 minutes. - Default value when not specified in API or module is interpreted by Avi Controller as 30. - - Units(MIN). credentials_timeout_threshold: description: - The time period after which credentials expire. - Default is 180 days. - Default value when not specified in API or module is interpreted by Avi Controller as 180. - - Units(DAYS). max_concurrent_sessions: description: - Maximum number of concurrent sessions allowed. @@ -103,7 +101,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -129,7 +127,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'useraccountprofile', set([])) diff --git a/lib/ansible/modules/network/avi/avi_virtualservice.py b/lib/ansible/modules/network/avi/avi_virtualservice.py index e9e75a49744..f4cb483a4f1 100644 --- a/lib/ansible/modules/network/avi/avi_virtualservice.py +++ b/lib/ansible/modules/network/avi/avi_virtualservice.py @@ -52,6 +52,14 @@ options: - Redistribution is based on the auto redistribute property of the serviceenginegroup. - Enum options - ACTIVE_STANDBY_SE_1, ACTIVE_STANDBY_SE_2. - Default value when not specified in API or module is interpreted by Avi Controller as ACTIVE_STANDBY_SE_1. + allow_invalid_client_cert: + description: + - Process request even if invalid client certificate is presented. + - Datascript apis need to be used for processing of such requests. + - Field introduced in 18.2.3. + - Default value when not specified in API or module is interpreted by Avi Controller as False. + version_added: "2.9" + type: bool analytics_policy: description: - Determines analytics settings for the application. @@ -59,6 +67,13 @@ options: description: - Specifies settings related to analytics. - It is a reference to an object of type analyticsprofile. + apic_contract_graph: + description: + - The name of the contract/graph associated with the virtual service. + - Should be in the format. + - This is applicable only for service integration mode with cisco apic controller. + - Field introduced in 17.2.12,18.1.2. + version_added: "2.9" application_profile_ref: description: - Enable application layer specific features for the virtual service. @@ -67,13 +82,11 @@ options: description: - Auto-allocate floating/elastic ip from the cloud infrastructure. - Field deprecated in 17.1.1. - - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool auto_allocate_ip: description: - Auto-allocate vip from the provided subnet. - Field deprecated in 17.1.1. - - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool availability_zone: description: @@ -83,14 +96,19 @@ options: description: - (internal-use) fip allocated by avi in the cloud infrastructure. - Field deprecated in 17.1.1. - - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool avi_allocated_vip: description: - (internal-use) vip allocated by avi in the cloud infrastructure. - Field deprecated in 17.1.1. - - Default value when not specified in API or module is interpreted by Avi Controller as False. type: bool + azure_availability_set: + description: + - (internal-use)applicable for azure only. + - Azure availability set to which this vs is associated. + - Internally set by the cloud connector. + - Field introduced in 17.2.12, 18.1.2. + version_added: "2.9" bulk_sync_kvcache: description: - (this is a beta feature). @@ -121,7 +139,7 @@ options: cloud_type: description: - Enum options - cloud_none, cloud_vcenter, cloud_openstack, cloud_aws, cloud_vca, cloud_apic, cloud_mesos, cloud_linuxserver, cloud_docker_ucp, - - cloud_rancher, cloud_oshift_k8s, cloud_azure. + - cloud_rancher, cloud_oshift_k8s, cloud_azure, cloud_gcp. - Default value when not specified in API or module is interpreted by Avi Controller as CLOUD_NONE. connections_rate_limit: description: @@ -259,6 +277,11 @@ options: description: - Microservice representing the virtual service. - It is a reference to an object of type microservice. + min_pools_up: + description: + - Minimum number of up pools to mark vs up. + - Field introduced in 18.2.1, 17.2.12. + version_added: "2.9" name: description: - Name for the virtual service. @@ -304,6 +327,11 @@ options: requests_rate_limit: description: - Rate limit the incoming requests to this virtual service. + saml_sp_config: + description: + - Application-specific saml config. + - Field introduced in 18.2.3. + version_added: "2.9" scaleout_ecmp: description: - Disable re-distribution of flows across service engines for a virtual service. @@ -315,6 +343,13 @@ options: - The service engine group to use for this virtual service. - Moving to a new se group is disruptive to existing connections for this vs. - It is a reference to an object of type serviceenginegroup. + security_policy_ref: + description: + - Security policy applied on the traffic of the virtual service. + - This policy is used to perform security actions such as distributed denial of service (ddos) attack mitigation, etc. + - It is a reference to an object of type securitypolicy. + - Field introduced in 18.2.1. + version_added: "2.9" server_network_profile_ref: description: - Determines the network settings profile for the server side of tcp proxied connections. @@ -355,11 +390,28 @@ options: description: - Determines the set of ssl versions and ciphers to accept for ssl/tls terminated connections. - It is a reference to an object of type sslprofile. + ssl_profile_selectors: + description: + - Select ssl profile based on client ip address match. + - Field introduced in 18.2.3. + version_added: "2.9" ssl_sess_cache_avg_size: description: - Expected number of ssl session cache entries (may be exceeded). - Allowed values are 1024-16383. - Default value when not specified in API or module is interpreted by Avi Controller as 1024. + sso_policy: + description: + - Client authentication and authorization policy for the virtualservice. + - Field deprecated in 18.2.3. + - Field introduced in 18.2.1. + version_added: "2.9" + sso_policy_ref: + description: + - The sso policy attached to the virtualservice. + - It is a reference to an object of type ssopolicy. + - Field introduced in 18.2.3. + version_added: "2.9" static_dns_records: description: - List of static dns records applied to this virtual service. @@ -376,6 +428,11 @@ options: tenant_ref: description: - It is a reference to an object of type tenant. + topology_policies: + description: + - Topology policies applied on the dns traffic of the virtual service based ongslb topology algorithm. + - Field introduced in 18.2.3. + version_added: "2.9" traffic_clone_profile_ref: description: - Server network or list of servers for cloning traffic. @@ -436,6 +493,12 @@ options: vs_datascripts: description: - Datascripts applied on the data traffic of the virtual service. + vsvip_cloud_config_cksum: + description: + - Checksum of cloud configuration for vsvip. + - Internally set by cloud connector. + - Field introduced in 17.2.9, 18.1.2. + version_added: "2.9" vsvip_ref: description: - Mostly used during the creation of shared vs, this field refers to entities that can be shared across virtual services. @@ -492,7 +555,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -505,14 +568,17 @@ def main(): choices=['put', 'patch']), avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), active_standby_se_tag=dict(type='str',), + allow_invalid_client_cert=dict(type='bool',), analytics_policy=dict(type='dict',), analytics_profile_ref=dict(type='str',), + apic_contract_graph=dict(type='str',), application_profile_ref=dict(type='str',), auto_allocate_floating_ip=dict(type='bool',), auto_allocate_ip=dict(type='bool',), availability_zone=dict(type='str',), avi_allocated_fip=dict(type='bool',), avi_allocated_vip=dict(type='bool',), + azure_availability_set=dict(type='str',), bulk_sync_kvcache=dict(type='bool',), client_auth=dict(type='dict',), close_client_conn_on_config_update=dict(type='bool',), @@ -549,6 +615,7 @@ def main(): limit_doser=dict(type='bool',), max_cps_per_client=dict(type='int',), microservice_ref=dict(type='str',), + min_pools_up=dict(type='int',), name=dict(type='str', required=True), network_profile_ref=dict(type='str',), network_ref=dict(type='str',), @@ -560,8 +627,10 @@ def main(): port_uuid=dict(type='str',), remove_listening_port_on_vs_down=dict(type='bool',), requests_rate_limit=dict(type='dict',), + saml_sp_config=dict(type='dict',), scaleout_ecmp=dict(type='bool',), se_group_ref=dict(type='str',), + security_policy_ref=dict(type='str',), server_network_profile_ref=dict(type='str',), service_metadata=dict(type='str',), service_pool_select=dict(type='list',), @@ -571,11 +640,15 @@ def main(): sp_pool_refs=dict(type='list',), ssl_key_and_certificate_refs=dict(type='list',), ssl_profile_ref=dict(type='str',), + ssl_profile_selectors=dict(type='list',), ssl_sess_cache_avg_size=dict(type='int',), + sso_policy=dict(type='dict',), + sso_policy_ref=dict(type='str',), static_dns_records=dict(type='list',), subnet=dict(type='dict',), subnet_uuid=dict(type='str',), tenant_ref=dict(type='str',), + topology_policies=dict(type='list',), traffic_clone_profile_ref=dict(type='str',), traffic_enabled=dict(type='bool',), type=dict(type='str',), @@ -588,6 +661,7 @@ def main(): vip=dict(type='list',), vrf_context_ref=dict(type='str',), vs_datascripts=dict(type='list',), + vsvip_cloud_config_cksum=dict(type='str',), vsvip_ref=dict(type='str',), waf_policy_ref=dict(type='str',), weight=dict(type='int',), @@ -597,7 +671,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'virtualservice', set([])) diff --git a/lib/ansible/modules/network/avi/avi_vrfcontext.py b/lib/ansible/modules/network/avi/avi_vrfcontext.py index c3b131325e7..b1cb187158c 100644 --- a/lib/ansible/modules/network/avi/avi_vrfcontext.py +++ b/lib/ansible/modules/network/avi/avi_vrfcontext.py @@ -107,7 +107,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -137,7 +137,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'vrfcontext', set([])) diff --git a/lib/ansible/modules/network/avi/avi_vsdatascriptset.py b/lib/ansible/modules/network/avi/avi_vsdatascriptset.py index 23c2073b3b7..917aa7c4aa3 100644 --- a/lib/ansible/modules/network/avi/avi_vsdatascriptset.py +++ b/lib/ansible/modules/network/avi/avi_vsdatascriptset.py @@ -69,6 +69,12 @@ options: description: - Uuid of pools that could be referred by vsdatascriptset objects. - It is a reference to an object of type pool. + protocol_parser_refs: + description: + - List of protocol parsers that could be referred by vsdatascriptset objects. + - It is a reference to an object of type protocolparser. + - Field introduced in 18.2.3. + version_added: "2.9" string_group_refs: description: - Uuid of string groups that could be referred by vsdatascriptset objects. @@ -106,7 +112,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -125,6 +131,7 @@ def main(): name=dict(type='str', required=True), pool_group_refs=dict(type='list',), pool_refs=dict(type='list',), + protocol_parser_refs=dict(type='list',), string_group_refs=dict(type='list',), tenant_ref=dict(type='str',), url=dict(type='str',), @@ -135,7 +142,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'vsdatascriptset', set([])) diff --git a/lib/ansible/modules/network/avi/avi_vsvip.py b/lib/ansible/modules/network/avi/avi_vsvip.py index 8a4fff4c567..5aa5a619d70 100644 --- a/lib/ansible/modules/network/avi/avi_vsvip.py +++ b/lib/ansible/modules/network/avi/avi_vsvip.py @@ -68,6 +68,14 @@ options: url: description: - Avi controller URL of the object. + use_standard_alb: + description: + - This overrides the cloud level default and needs to match the se group value in which it will be used if the se group use_standard_alb value is + - set. + - This is only used when fip is used for vs on azure cloud. + - Field introduced in 18.2.3. + version_added: "2.9" + type: bool uuid: description: - Uuid of the vsvip object. @@ -82,6 +90,12 @@ options: - This is used to provide the isolation of the set of networks the application is attached to. - It is a reference to an object of type vrfcontext. - Field introduced in 17.1.1. + vsvip_cloud_config_cksum: + description: + - Checksum of cloud configuration for vsvip. + - Internally set by cloud connector. + - Field introduced in 17.2.9, 18.1.2. + version_added: "2.9" extends_documentation_fragment: - avi ''' @@ -106,7 +120,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -124,16 +138,18 @@ def main(): name=dict(type='str', required=True), tenant_ref=dict(type='str',), url=dict(type='str',), + use_standard_alb=dict(type='bool',), uuid=dict(type='str',), vip=dict(type='list',), vrf_context_ref=dict(type='str',), + vsvip_cloud_config_cksum=dict(type='str',), ) argument_specs.update(avi_common_argument_spec()) module = AnsibleModule( argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'vsvip', set([])) diff --git a/lib/ansible/modules/network/avi/avi_wafpolicy.py b/lib/ansible/modules/network/avi/avi_wafpolicy.py deleted file mode 100644 index dab69b106e2..00000000000 --- a/lib/ansible/modules/network/avi/avi_wafpolicy.py +++ /dev/null @@ -1,162 +0,0 @@ -#!/usr/bin/python -# -# @author: Gaurav Rastogi (grastogi@avinetworks.com) -# Eric Anderson (eanderson@avinetworks.com) -# module_check: supported -# -# Copyright: (c) 2017 Gaurav Rastogi, -# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) -# - -ANSIBLE_METADATA = {'metadata_version': '1.1', - 'status': ['preview'], - 'supported_by': 'community'} - -DOCUMENTATION = ''' ---- -module: avi_wafpolicy -author: Gaurav Rastogi (@grastogi23) - -short_description: Module for setup of WafPolicy Avi RESTful Object -description: - - This module is used to configure WafPolicy object - - more examples at U(https://github.com/avinetworks/devops) -requirements: [ avisdk ] -version_added: "2.5" -options: - state: - description: - - The state that should be applied on the entity. - default: present - choices: ["absent", "present"] - avi_api_update_method: - description: - - Default method for object update is HTTP PUT. - - Setting to patch will override that behavior to use HTTP PATCH. - version_added: "2.5" - default: put - choices: ["put", "patch"] - avi_api_patch_op: - description: - - Patch operation to use when using avi_api_update_method as patch. - version_added: "2.5" - choices: ["add", "replace", "delete"] - created_by: - description: - - Creator name. - - Field introduced in 17.2.4. - crs_groups: - description: - - Waf rules are categorized in to groups based on their characterization. - - These groups are system created with crs groups. - - Field introduced in 17.2.1. - description: - description: - - Field introduced in 17.2.1. - mode: - description: - - Waf policy mode. - - This can be detection or enforcement. - - Enum options - WAF_MODE_DETECTION_ONLY, WAF_MODE_ENFORCEMENT. - - Field introduced in 17.2.1. - - Default value when not specified in API or module is interpreted by Avi Controller as WAF_MODE_DETECTION_ONLY. - required: true - name: - description: - - Field introduced in 17.2.1. - required: true - paranoia_level: - description: - - Waf ruleset paranoia mode. - - This is used to select rules based on the paranoia-level tag. - - Enum options - WAF_PARANOIA_LEVEL_LOW, WAF_PARANOIA_LEVEL_MEDIUM, WAF_PARANOIA_LEVEL_HIGH, WAF_PARANOIA_LEVEL_EXTREME. - - Field introduced in 17.2.1. - - Default value when not specified in API or module is interpreted by Avi Controller as WAF_PARANOIA_LEVEL_LOW. - post_crs_groups: - description: - - Waf rules are categorized in to groups based on their characterization. - - These groups are created by the user and will be enforced after the crs groups. - - Field introduced in 17.2.1. - pre_crs_groups: - description: - - Waf rules are categorized in to groups based on their characterization. - - These groups are created by the user and will be enforced before the crs groups. - - Field introduced in 17.2.1. - tenant_ref: - description: - - It is a reference to an object of type tenant. - - Field introduced in 17.2.1. - url: - description: - - Avi controller URL of the object. - uuid: - description: - - Field introduced in 17.2.1. - waf_profile_ref: - description: - - Waf profile for waf policy. - - It is a reference to an object of type wafprofile. - - Field introduced in 17.2.1. - required: true -extends_documentation_fragment: - - avi -''' - -EXAMPLES = """ -- name: Example to create WafPolicy object - avi_wafpolicy: - controller: 10.10.25.42 - username: admin - password: something - state: present - name: sample_wafpolicy -""" - -RETURN = ''' -obj: - description: WafPolicy (api/wafpolicy) object - returned: success, changed - type: dict -''' - -from ansible.module_utils.basic import AnsibleModule -try: - from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) -except ImportError: - HAS_AVI = False - - -def main(): - argument_specs = dict( - state=dict(default='present', - choices=['absent', 'present']), - avi_api_update_method=dict(default='put', - choices=['put', 'patch']), - avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), - created_by=dict(type='str',), - crs_groups=dict(type='list',), - description=dict(type='str',), - mode=dict(type='str', required=True), - name=dict(type='str', required=True), - paranoia_level=dict(type='str',), - post_crs_groups=dict(type='list',), - pre_crs_groups=dict(type='list',), - tenant_ref=dict(type='str',), - url=dict(type='str',), - uuid=dict(type='str',), - waf_profile_ref=dict(type='str', required=True), - ) - argument_specs.update(avi_common_argument_spec()) - module = AnsibleModule( - argument_spec=argument_specs, supports_check_mode=True) - if not HAS_AVI: - return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' - 'For more details visit https://github.com/avinetworks/sdk.')) - return avi_ansible_api(module, 'wafpolicy', - set([])) - - -if __name__ == '__main__': - main() diff --git a/lib/ansible/modules/network/avi/avi_wafprofile.py b/lib/ansible/modules/network/avi/avi_wafprofile.py deleted file mode 100644 index 86f41f6e2bf..00000000000 --- a/lib/ansible/modules/network/avi/avi_wafprofile.py +++ /dev/null @@ -1,126 +0,0 @@ -#!/usr/bin/python -# -# @author: Gaurav Rastogi (grastogi@avinetworks.com) -# Eric Anderson (eanderson@avinetworks.com) -# module_check: supported -# -# Copyright: (c) 2017 Gaurav Rastogi, -# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) -# - -ANSIBLE_METADATA = {'metadata_version': '1.1', - 'status': ['preview'], - 'supported_by': 'community'} - -DOCUMENTATION = ''' ---- -module: avi_wafprofile -author: Gaurav Rastogi (@grastogi23) - -short_description: Module for setup of WafProfile Avi RESTful Object -description: - - This module is used to configure WafProfile object - - more examples at U(https://github.com/avinetworks/devops) -requirements: [ avisdk ] -version_added: "2.5" -options: - state: - description: - - The state that should be applied on the entity. - default: present - choices: ["absent", "present"] - avi_api_update_method: - description: - - Default method for object update is HTTP PUT. - - Setting to patch will override that behavior to use HTTP PATCH. - version_added: "2.5" - default: put - choices: ["put", "patch"] - avi_api_patch_op: - description: - - Patch operation to use when using avi_api_update_method as patch. - version_added: "2.5" - choices: ["add", "replace", "delete"] - config: - description: - - Config params for waf. - - Field introduced in 17.2.1. - required: true - description: - description: - - Field introduced in 17.2.1. - files: - description: - - List of data files used for waf rules. - - Field introduced in 17.2.1. - name: - description: - - Field introduced in 17.2.1. - required: true - tenant_ref: - description: - - It is a reference to an object of type tenant. - - Field introduced in 17.2.1. - url: - description: - - Avi controller URL of the object. - uuid: - description: - - Field introduced in 17.2.1. -extends_documentation_fragment: - - avi -''' - -EXAMPLES = """ -- name: Example to create WafProfile object - avi_wafprofile: - controller: 10.10.25.42 - username: admin - password: something - state: present - name: sample_wafprofile -""" - -RETURN = ''' -obj: - description: WafProfile (api/wafprofile) object - returned: success, changed - type: dict -''' - -from ansible.module_utils.basic import AnsibleModule -try: - from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) -except ImportError: - HAS_AVI = False - - -def main(): - argument_specs = dict( - state=dict(default='present', - choices=['absent', 'present']), - avi_api_update_method=dict(default='put', - choices=['put', 'patch']), - avi_api_patch_op=dict(choices=['add', 'replace', 'delete']), - config=dict(type='dict', required=True), - description=dict(type='str',), - files=dict(type='list',), - name=dict(type='str', required=True), - tenant_ref=dict(type='str',), - url=dict(type='str',), - uuid=dict(type='str',), - ) - argument_specs.update(avi_common_argument_spec()) - module = AnsibleModule( - argument_spec=argument_specs, supports_check_mode=True) - if not HAS_AVI: - return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' - 'For more details visit https://github.com/avinetworks/sdk.')) - return avi_ansible_api(module, 'wafprofile', - set([])) - - -if __name__ == '__main__': - main() diff --git a/lib/ansible/modules/network/avi/avi_webhook.py b/lib/ansible/modules/network/avi/avi_webhook.py index f787b60505e..4cd6960c006 100644 --- a/lib/ansible/modules/network/avi/avi_webhook.py +++ b/lib/ansible/modules/network/avi/avi_webhook.py @@ -92,7 +92,7 @@ obj: from ansible.module_utils.basic import AnsibleModule try: from ansible.module_utils.network.avi.avi import ( - avi_common_argument_spec, HAS_AVI, avi_ansible_api) + avi_common_argument_spec, avi_ansible_api, HAS_AVI) except ImportError: HAS_AVI = False @@ -117,7 +117,7 @@ def main(): argument_spec=argument_specs, supports_check_mode=True) if not HAS_AVI: return module.fail_json(msg=( - 'Avi python API SDK (avisdk>=17.1) is not installed. ' + 'Avi python API SDK (avisdk>=17.1) or requests is not installed. ' 'For more details visit https://github.com/avinetworks/sdk.')) return avi_ansible_api(module, 'webhook', set([])) diff --git a/lib/ansible/plugins/doc_fragments/avi.py b/lib/ansible/plugins/doc_fragments/avi.py index 5c4fac1e6e2..e8a284479fc 100644 --- a/lib/ansible/plugins/doc_fragments/avi.py +++ b/lib/ansible/plugins/doc_fragments/avi.py @@ -51,6 +51,11 @@ options: - This allows user to perform single login and re-use the session. type: dict version_added: "2.5" + avi_disable_session_cache_as_fact: + description: + - It disables avi session information to be cached as a fact. + type: bool + version_added: "2.6" notes: - For more information on using Ansible to manage Avi Network devices see U(https://www.ansible.com/ansible-avi-networks). '''