def delete_cname(cname: str, session: object, url: str): """ Delete a CNAME from a host. :param str cname: The CNAME to add. :param str host: The host FQDN. :param object session: The requests session object. :param str url: The full URL of the DDI server. :return: The response as JSON :rtype: list """ logger.debug('Delete cname: %s called.', cname) host_data = get_cname_info(cname, session, url) if jsend.is_success(host_data): entry = host_data['data']['results'][0] payload = {'ip_id': entry['ip_id'], 'ip_name': cname} r = session.delete(url + 'rest/ip_alias_delete', json=payload) result = get_exceptions(r) logger.debug('Delete cname result code: %s, JSON: %s', r.status_code, result) return result else: return host_data
def get_free_ipv4(subnet: str, session: object, url: str): """ Get a free IP address in a given subnet ID. :param str subnet: The subnet ID to get the free IP for (e.g. 172.23.23.0). :param object session: the requests session object :param url: The full URL of the DDI server. :return: The JSON response in JSEND format. :rtype: dict """ logger.debug('Getting free IP for subnet: %s', subnet) r = get_subnet_info(subnet, session, url) if jsend.is_success(r): subnet_id = r['data']['results'][0]['subnet_id'] payload = {'subnet_id': subnet_id} r = session.get(url + '/rpc/ip_find_free_address', params=payload) result = get_exceptions(r) return result else: logger.debug('Failed: Getting free IP for subnet: %s', subnet) return r
def add_cname(cname: str, host: str, session: object, url: str): """ Add a cname to a given host. :param str cname: The CNAME to add. :param str host: The host FQDN. :param object session: The requests session object. :param str url: The full URL of the DDI server. :return: The response as JSON :rtype: list """ logger.debug('Add CNAME: %s called on host: %s', cname, host) host_data = get_host(host, session, url) if jsend.is_success(host_data): entry = host_data['data']['results'][0] payload = {'ip_id': entry['ip_id'], 'ip_name': cname} r = session.put(url + 'rest/ip_alias_add', json=payload) result = get_exceptions(r) logger.debug('Add cname result code: %s, JSON: %s', r.status_code, result) return result else: return host_data
def delete_host(fqdn: str, session: object, url: str): """ Delete a given host by ip_id. :param str fqdn: The FQDN of the host object to delete. :param object session: The requests session object. :param str url: The URL of the DDI server. :return: The JSON result of the operation. :rtype: str """ h = get_host(fqdn, session, url) if jsend.is_success(h): ip_id = h['data']['results'][0]['ip_id'] logger.debug('Deleting host: %s with ip_id: %s', fqdn, ip_id) payload = {'ip_id': ip_id} r = session.delete(url + 'rest/ip_delete', params=payload) result = get_exceptions(r) return result else: return h
def get_host(fqdn: str, session: object, url: str): """ Get the host information from DDI. :param str fqdn: The fully qualified domain name of the host to locate in DDI. :param object session: The requests session object. :param str url: The full URL of the DDI server. :return: The JSON result of the operation. :rtype: str """ logger.debug('Getting host info for: %s', fqdn) payload = {'WHERE': f"name='{fqdn}'"} r = session.get(url + 'rest/ip_address_list', params=payload) result = get_exceptions(r) return result
def get_cname_info(cname: str, session: object, url: str): """ Get host information associated with a given CNAME. :param str cname: The CNAME to search for. :param object session: The requests session object. :param str url: The full URL of the DDI server. :return: The response as JSON. :rtype: list """ logger.debug('Get CNAME called for: %s', cname) payload = {'WHERE': f"ip_alias like '%{cname}%'"} r = session.get(url + 'rest/ip_address_list', params=payload) result = get_exceptions(r) return result
def get_ipv4_info(ip: str, session: object, url: str): """ Get the host information from DDI. :param str ip: The IPv4 address as a dotted quad. :param object session: The requests session object. :param str url: The full URL of the DDI server. :return: The JSON response in JSEND format. :rtype: dict """ logger.debug('Getting IP info for: %s', ip) ip = hexlify_address(ip).decode() payload = {'WHERE': f"ip_addr='{ip}'"} r = session.get(url + 'rest/ip_address_list', params=payload) result = get_exceptions(r) return result
def get_subnet_info(subnet: str, session: object, url: str): """ Get information about a given subnet. :param str subnet: The subnet to get the free IP for (e.g. 192.168.127.0) :param object session: the requests session object :param url: The full URL of the DDI server. :return: The JSON response in JSEND format. :rtype: dict """ logger.debug('Getting subnet info for: %s', subnet) subnet = hexlify_address(subnet).decode() payload = {'WHERE': f"start_ip_addr='{subnet}'"} r = session.get(url + '/rest/ip_block_subnet_list', params=payload) result = get_exceptions(r) return result
def add_host(building: str, department: str, contact: str, phone: str, name: str, session: object, url: str, comment: str = None, ip: str = None, site_name: str = "UCB", subnet: str = None): """ Add a host to DDI. :param str building: The UCB building the host is located in. :param str contact: The UCB contact person for the host. :param str department: The UCB department the host is affiliated with. :param str phone: The phone number associated with the host. :param str name: The FQDN for the host, must be unique. :param object session: The requests session object. :param str url: The URL of the DDI server. :param str comment: An optional comment. :param str ip: The optional IP address to give to the host, either ip or subnet must be defined. :param str site_name: The site name to use, defaults to UCB. :param str subnet: The optional subnet to use (e.g. 172.23.23.0) either ip or subnet must be defined. :return: The JSON result of the operation. :rtype: str """ ip_class_parameters = { 'hostname': name.split('.')[0], 'ucb_buildings': building, 'ucb_dept_aff': department, 'ucb_ph_no': phone, 'ucb_resp_per': contact } # Add the comment if it was passed in if comment: ip_class_parameters['ucb_comment'] = comment ip_class_parameters = urllib.parse.urlencode(ip_class_parameters) # If an IP is specified that is more specific than a subnet, if neither # we fail. if ip: logger.debug('IP address: %s specified for host addition.', ip) ip = ip elif subnet: logger.debug('Subnet: %s specified, automatic IP discover started.', subnet) r = get_free_ipv4(subnet, session, url) if jsend.success(r): # Get the first free IP address offered. ip = r['data']['results'][0]['hostaddr'] logger.debug('IP: %s, automatically obtained.', ip) else: return r else: return jsend.fail({}) payload = { 'hostaddr': ip, 'name': name, 'site_name': site_name, 'ip_class_parameters': ip_class_parameters } logger.debug( 'Add operation invoked on Host: %s with IP: %s, Building: %s, ' 'Department: %s, Contact: %s Phone: %s, and Payload: %s', name, ip, building, department, contact, phone, payload) r = session.post(url + 'rest/ip_add', json=payload) result = get_exceptions(r) return result