def _validate_domain(self, param): if len(param) > 255: return False if phantom.is_ip(param): return False if param[-1] == '.': param = param[:-1] allowed = re.compile(r"(?!-)[A-Z\\d\-_]{1,63}(?<!-')$", re.IGNORECASE) parts = param.split('.') # Wildcard search '*' is allowed in the first and # last subdomain only for idx, x in enumerate(parts): if idx == 0 or idx == (len(parts) - 1): if not (x == '*' or allowed.match(x)): return False elif not allowed.match(x): return False return True
def _modify_device(self, action_result, ip_hostname, action="cmd_isolate_agent"): endpoint = APEX_ONE_PRODUCT_AGENTS_ENDPOINT payload = {"act": action, "allow_multiple_match": False} if phantom.is_ip(ip_hostname): payload["ip_address"] = ip_hostname else: payload["host_name"] = ip_hostname req_payload = json.dumps(payload) ret_val, response = self._make_rest_call(endpoint, action_result, "post", data=req_payload) return ret_val, response
def _test_connectivity(self, param): """ Called when the user depresses the test connectivity button on the Phantom UI. Use a basic query to determine if the device IP/hostname, username and password is correct """ action_result = ActionResult() self.save_progress(FORTIGATE_TEST_CONNECTIVITY_MSG) self.save_progress("Configured URL: {}".format(self._device)) ret_val = self._login(action_result) if phantom.is_fail(ret_val): # self.save_progress("Test Connectivity Failed") self.save_progress(action_result.get_message()) # return action_result.get_status() # If SSL is enabled and URL configuration has IP address if self._verify_server_cert and (phantom.is_ip(self._device) or self._is_ipv6(self._device)): # The failure could be due to IP provided in URL instead of hostname self.save_progress(FORTIGATE_TEST_WARN_MSG) self.set_status(phantom.APP_ERROR, FORTIGATE_TEST_CONN_FAIL) return action_result.get_status() self.save_progress(FORTIGATE_TEST_ENDPOINT_MSG) # Querying endpoint to check connection to device status, _ = self._make_rest_call(FORTIGATE_BLOCKED_IPS, action_result) if phantom.is_fail(status): self.save_progress(action_result.get_message()) self.set_status(phantom.APP_ERROR, FORTIGATE_TEST_CONN_FAIL) return action_result.get_status() self.set_status_save_progress(phantom.APP_SUCCESS, FORTIGATE_TEST_CONN_SUCC) return action_result.get_status()
def _is_ip(self, ip_addr): try: ip_addr = self._handle_py_ver_compat_for_input_str( self._python_version, ip_addr) ip, net_size, net_mask = self._break_ip_addr(ip_addr.strip()) except Exception as e: error_code, error_msg = self._get_error_message_from_exception(e) self.debug_print( "Validation for ip_addr failed. Error Code:{0}. Error Message:{1}. For valid IP formats, please refer to the action's documentation." .format(error_code, error_msg)) return False # Validate ip address if not phantom.is_ip(ip): return False # Regex to validate the subnet reg_exp = re.compile( '^((128|192|224|240|248|252|254).0.0.0)|(255.(((0|128|192|224|240|248|252|254).0.0)' '|(255.(((0|128|192|224|240|248|252|254).0)|255.(0|128|192|224|240|248|252|254|255)))))$' ) # Validate subnet if net_mask: if not reg_exp.match(net_mask): return False if net_size: try: net_size = int(net_size) except: self.debug_print("net_size: {0} invalid int".format(net_size)) return False if (not (0 < net_size <= 32)): return False return True
def _handle_get_system_info(self, param): self.save_progress("In action handler for: {0}".format( self.get_action_identifier())) action_result = self.add_action_result(ActionResult(dict(param))) ip_hostname = param["ip_hostname"] endpoint = APEX_ONE_PRODUCT_AGENTS_ENDPOINT if phantom.is_ip(ip_hostname): qs = f"?ip_address={ip_hostname}" else: qs = f"?host_name={ip_hostname}" ret_val, response = self._make_rest_call("{0}{1}".format(endpoint, qs), action_result, params=None) if phantom.is_fail(ret_val): return action_result.get_status() if response and (not response.get("result_content") or response.get("result_code") != 1): return action_result.set_status(phantom.APP_ERROR, APEX_ONE_RESPONSE_EMPTY_MSG) try: action_result.add_data(response["result_content"][0]) summary = action_result.update_summary({}) summary["msg"] = response.get("result_description", "") summary["total_objects"] = len(response["result_content"]) except: return action_result.set_status(phantom.APP_ERROR, APEX_ONE_ERR_SERVER_RES) return action_result.set_status(phantom.APP_SUCCESS)
def _lookup_rdata_ip(self, param): action_result = self.add_action_result(ActionResult(dict(param))) # Getting mandatory input parameter ip = param[DNSDB_JSON_IP] # Getting optional input parameter network_prefix = param.get(DNSDB_JSON_NETWORK_PREFIX) ret_val, network_prefix = self._validate_integer(action_result, network_prefix, DNSDB_NETWORK_PREFIX_KEY) if phantom.is_fail(ret_val): return action_result.get_status() limit = param.get(DNSDB_JSON_LIMIT, 200) ret_val, limit = self._validate_integer(action_result, limit, DNSDB_LIMIT_KEY) if phantom.is_fail(ret_val): return action_result.get_status() summary_data = action_result.update_summary({}) if network_prefix is not None: # Validate network prefix # network prefix valid if between 0 and 32 for ipv4 if phantom.is_ip(ip): net_prefix_valid = 0 <= network_prefix <= 32 else: # network prefix valid if between 0 and 128 for ipv6 net_prefix_valid = 0 <= network_prefix <= 128 if not net_prefix_valid: self.debug_print(DNSDB_ERR_INVALID_NETWORK_PREFIX.format(prefix=network_prefix)) return action_result.set_status( phantom.APP_ERROR, DNSDB_ERR_INVALID_NETWORK_PREFIX.format(prefix=network_prefix)) # Endpoint as per parameter given if network_prefix is not None: ip = "%s,%s" % (ip, network_prefix) # Constructing request parameters based on input # Validating the input parameters provided # Would be used during REST call ret_val, timestamps = self._validate_params(param, action_result) # Something went wrong while validing input parameters if phantom.is_fail(ret_val): return action_result.get_status() try: responses = list(self._client.lookup_rdata_ip(ip, limit=limit, time_first_before=timestamps[0], time_first_after=timestamps[1], time_last_before=timestamps[2], time_last_after=timestamps[3], ignore_limited=True)) except dnsdb2.exceptions.AccessDenied: return action_result.set_status( phantom.APP_ERROR, DNSDB_REST_RESP_ACCESS_DENIED_MSG) except dnsdb2.exceptions.QuotaExceeded: return action_result.set_status( phantom.APP_ERROR, DNSDB_REST_RESP_LIC_EXCEED_MSG) except Exception as e: err = self._get_error_message_from_exception(e) return action_result.set_status(phantom.APP_ERROR, err) # Something went wrong with the request if phantom.is_fail(ret_val): return action_result.get_status() # No data is considered as app success if len(responses) == 0: return action_result.set_status(phantom.APP_SUCCESS, DNSDB_DATA_NOT_AVAILABLE_MSG) # To display count of domains in summary data count_domain = set() for resp in responses: if 'rrname' in resp: resp['rrname'] = resp['rrname'].rstrip('.') count_domain.add(resp['rrname']) # Response from the API is list of rdata. # Adding Each data of list to action_result action_result.add_data(resp) summary_data['total_domains'] = len(count_domain) return action_result.set_status(phantom.APP_SUCCESS)
def _lookup_ip(self, param): action_result = self.add_action_result(ActionResult(dict(param))) # Getting mandatory input parameter ip = param[DNSDB_JSON_IP] # Getting optional input parameter network_prefix = param.get(DNSDB_JSON_NETWORK_PREFIX) summary_data = action_result.update_summary({}) if network_prefix: # Validate network prefix # network prefix valid if between 0 and 32 for ipv4 if phantom.is_ip(ip): net_prefix_valid = 0 <= int(network_prefix) <= 32 else: # network prefix valid if between 0 and 128 for ipv6 net_prefix_valid = 0 <= int(network_prefix) <= 128 if not net_prefix_valid: self.debug_print( DNSDB_ERR_INVALID_NETWORK_PREFIX.format( prefix=network_prefix)) return action_result.set_status( phantom.APP_ERROR, DNSDB_ERR_INVALID_NETWORK_PREFIX.format( prefix=network_prefix)) # Endpoint as per parameter given if network_prefix: endpoint = (DNSDB_ENDPOINT_IP_PREFIX).format(ip=ip, prefix=network_prefix) else: endpoint = (DNSDB_ENDPOINT_IP).format(ip=ip) # Constructing request parameters based on input # Validating the input parameters provided # Would be used during REST call ret_val, url_params = self._get_url_params(param, action_result) # Something went wrong while validing input parameters if phantom.is_fail(ret_val): return action_result.get_status() ret_val, response = self._make_rest_call(endpoint, action_result, params=url_params) # Something went wrong with the request if phantom.is_fail(ret_val): return action_result.get_status() # No data is considered as app success if (response.get(DNSDB_REST_RESP_RESOURCE_NOT_FOUND_MSG)): return action_result.set_status(phantom.APP_SUCCESS, DNSDB_DATA_NOT_AVAILABLE_MSG) json_resp = response.get(DNSDB_JSON_RESPONSE) # To display count of domains in summary data count_domain = set() for resp in json_resp: if ('rrname' in resp): resp['rrname'] = resp['rrname'].rstrip('.') count_domain.add(resp['rrname']) # Response from the API is list of rdata. # Adding Each data of list to action_result action_result.add_data(resp) summary_data['total_domains'] = len(count_domain) return action_result.set_status(phantom.APP_SUCCESS)