GreyNoise Indicator Feed
GreyNoise is a cybersecurity platform that collects and analyzes Internet-wide scan and attack traffic. With this integration, users can contextualize existing alerts, filter false-positives, identify compromised devices, and track emerging threats. This Integration provides a feed of IPv4 Internet Scanners from GreyNoise.
Data Enrichment & Threat Intelligence · GreyNoise Indicator Feed · Feed
Details
| ID | GreyNoise Indicator Feed |
|---|---|
| Provider | GreyNoise |
| Category | Data Enrichment & Threat Intelligence |
| From Version | 6.10.0 |
| Docker Image | demisto/greynoise:1.0.0.10133006 |
| Supported Modules | Agentix XSIAM |
README
GreyNoise is a cybersecurity platform that collects and analyzes Internet-wide scan and attack traffic. With this integration, users can contextualize existing alerts, filter false-positives, identify compromised devices, and track emerging threats. This Integration provides a feed of IPv4 Internet Scanners from GreyNoise.
This integration was integrated and tested with version 2.0.1 of GreyNoise SDK.
Configure GreyNoise Indicator Feed in Cortex
| Parameter | Description | Required |
|---|---|---|
| Fetch indicators | False | |
| Username | False | |
| Password | False | |
| Indicator Reputation | Leave this selection blank. Not used for this integration. | False |
| Source Reliability | Reliability of the source providing the intelligence data | True |
| GreyNoise Feed Type | Select which GreyNoise Feed to ingest | True |
| Tags | Supports CSV values. | False |
| Traffic Light Protocol Color | The Traffic Light Protocol (TLP) designation to apply to indicators fetched from the feed | False |
| feedExpirationPolicy | False | |
| feedExpirationInterval | False | |
| Feed Fetch Interval | False | |
| Bypass exclusion list | When selected, the exclusion list is ignored for indicators from this feed. This means that if an indicator from this feed is on the exclusion list, the indicator might still be added to the system. | False |
| Use system proxy settings | False | |
| Trust any certificate (not secure) | False |
Commands
You can execute these commands from the CLI, as part of an automation, or in a playbook.
After you successfully execute a command, a DBot message appears in the War Room with the command details.
greynoise-get-indicators
Gets the feed indicators.
Base Command
greynoise-get-indicators
Input
There are no input arguments for this command.
Context Output
| Path | Type | Description |
|---|---|---|
| GreyNoiseFeed.Indicators.Value | String | The value of the indicator. |
| GreyNoiseFeed.Indicators.Type | String | The type of the indicator. |
| GreyNoiseFeed.Indicators.Tags | String | The GreyNoise tags associated with the indicator. |
Configuration parameters
feed— Fetch indicatorscredentials— UsernamefeedReputation— Indicator ReputationfeedReliability— Source Reliability (required)greynoiseFeedType— GreyNoise Feed Type (required)feedTags— Tagstlp_color— Traffic Light Protocol ColorfeedExpirationPolicy—feedExpirationInterval—feedFetchInterval— Feed Fetch IntervalfeedBypassExclusionList— Bypass exclusion listproxy— Use system proxy settingsinsecure— Trust any certificate (not secure)
Commands (1)
-
greynoise-get-indicatorsGets the feed indicators.
import json import GreyNoiseIndicator import pytest TEST_MODULE_DATA = [ ("true_key", {"message": "pong", "expiration": "2025-12-31", "offering": "enterprise"}, 200, "ok"), ("dummy_key", "forbidden", 401, "Unauthenticated. Check the configured API Key."), ("dummy_key", "", 429, "API Rate limit hit. Try after sometime."), ( "dummy_key", "Dummy message", 405, "Failed to execute command.\n Error: Dummy message", ), ( "dummy_key", "Dummy message", 505, "The server encountered an internal error for GreyNoise and was unable to complete your request.", ), ] GET_IP_REPUTATION_SCORE_DATA = [ ("unknown", 0), ("suspicious", 2), ("benign", 1), ("malicious", 3), ("dummy", 0), ] GET_IP_TAG_NAMES_DATA = [([], []), ([{"name": "Mirai"}], ["Mirai"])] FORMAT_TIMESTAMP_DATA = [("2023-11-23", "2023-11-23T00:00:00Z")] FORMAT_INDICATOR_DATA = [ ( { "ip": "1.2.3.4", "internet_scanner_intelligence": { "last_seen": "2000-01-01", "first_seen": "1911-12-12", "tags": [], "classification": "benign", "metadata": {"source_country": "US"}, }, }, "GREEN", { "Type": "IP", "Value": "1.2.3.4", "fields": { "firstseenbysource": "1911-12-12T00:00:00Z", "geocountry": "US", "geolocation": "", "lastseenbysource": "2000-01-01T00:00:00Z", "tags": "INTERNET SCANNER", "trafficlightprotocol": "GREEN", }, "rawJSON": { "ip": "1.2.3.4", "internet_scanner_intelligence": { "classification": "benign", "first_seen": "1911-12-12", "last_seen": "2000-01-01", "metadata": {"source_country": "US"}, "tags": [], }, }, "score": 1, }, ), ( { "ip": "1.2.3.4", "internet_scanner_intelligence": { "last_seen": "2000-01-01", "first_seen": "1911-12-12", "tags": [{"name": "Mirai"}], "classification": "benign", "metadata": {"source_country": "US"}, }, }, "GREEN", { "Type": "IP", "Value": "1.2.3.4", "fields": { "firstseenbysource": "1911-12-12T00:00:00Z", "geocountry": "US", "geolocation": "", "lastseenbysource": "2000-01-01T00:00:00Z", "tags": "INTERNET SCANNER,Mirai", "trafficlightprotocol": "GREEN", }, "rawJSON": { "ip": "1.2.3.4", "internet_scanner_intelligence": { "classification": "benign", "first_seen": "1911-12-12", "last_seen": "2000-01-01", "metadata": {"source_country": "US"}, "tags": [{"name": "Mirai"}], }, }, "score": 1, }, ), ] BUILD_FEED_QUERY_DATA = [ ("Malicious", "last_seen:1d classification:malicious"), ("Benign", "last_seen:1d classification:benign"), ("Benign + Malicious", "last_seen:1d (classification:benign OR classification:malicious)"), ("All", "last_seen:1d"), ("", ""), ] VALID_QUERY = { "complete": True, "count": 1, "data": [ { "ip": "1.1.1.1", "internet_scanner_intelligence": { "bot": False, "vpn": False, "vpn_service": "N/A", "spoofable": False, "raw_data": {}, "first_seen": "2024-01-28", "last_seen": "2024-01-30", "seen": True, "tags": [], "actor": "unknown", "classification": "unknown", "cve": [], "metadata": { "source_country": "US", "latitude": "37.774929", "longitude": "-122.419416", }, }, } ], "request_metadata": { "complete": True, "count": 1, "scroll": "scroll_token", }, } COMMAND_OUTPUT = [ { "Type": "IP", "Value": "1.1.1.1", "fields": { "firstseenbysource": "2024-01-28T00:00:00Z", "geocountry": "US", "geolocation": "37.774929,-122.419416", "lastseenbysource": "2024-01-30T00:00:00Z", "tags": "INTERNET SCANNER", "trafficlightprotocol": None, }, "rawJSON": { "ip": "1.1.1.1", "internet_scanner_intelligence": { "bot": False, "vpn": False, "vpn_service": "N/A", "spoofable": False, "raw_data": {}, "first_seen": "2024-01-28", "last_seen": "2024-01-30", "seen": True, "tags": [], "actor": "unknown", "classification": "unknown", "cve": [], "metadata": { "source_country": "US", "latitude": "37.774929", "longitude": "-122.419416", }, }, }, "score": 0, } ] GET_INDICATORS_COMMAND_DATA = [({}, VALID_QUERY, 200, COMMAND_OUTPUT)] FETCH_INDICATORS_DATA = [("success", VALID_QUERY, 200, COMMAND_OUTPUT), ("failure", {}, 400, "(400, {})")] FETCH_INDICATORS_COMMAND_DATA = [({}, VALID_QUERY, 200, COMMAND_OUTPUT)] class DummyResponse: """ Dummy Response object of requests.response for unit testing. """ def __init__(self, headers, text, status_code): self.headers = headers self.text = text self.status_code = status_code def json(self): """ Dummy json method. """ return json.loads(self.text) @pytest.mark.parametrize("api_key, api_response, status_code, expected_output", TEST_MODULE_DATA) def test_test_module(api_key, api_response, status_code, expected_output, mocker): """ Tests test_module for GreyNoise integration. """ api_config = GreyNoiseIndicator.APIConfig(api_key, "dummy_server", 10, "proxy", False, "dummy_integration") client = GreyNoiseIndicator.Client(api_config) if isinstance(api_key, str) and api_key == "true_key": mocker.patch("greynoise.GreyNoise._request", return_value=api_response) response = GreyNoiseIndicator.test_module(client) assert response == expected_output else: dummy_response = DummyResponse({}, api_response, status_code) mocker.patch("requests.Session.get", return_value=dummy_response) with pytest.raises(Exception) as err: _ = GreyNoiseIndicator.test_module(client) assert str(err.value) == expected_output @pytest.mark.parametrize("input_data, expected_output", GET_IP_REPUTATION_SCORE_DATA) def test_get_ip_reputation_score(input_data, expected_output): """ Tests various combinations of GreyNoise classification data. """ response = GreyNoiseIndicator.get_ip_reputation_score(input_data) assert response == expected_output @pytest.mark.parametrize("input_data, expected_output", GET_IP_TAG_NAMES_DATA) def test_get_ip_tag_names(input_data, expected_output): """ Tests various combinations of GreyNoise classification data. """ response = GreyNoiseIndicator.get_ip_tag_names(input_data) assert response == expected_output @pytest.mark.parametrize("input_data, expected_output", FORMAT_TIMESTAMP_DATA) def test_format_timestamp(input_data, expected_output): """ Tests various combinations of GreyNoise classification data. """ response = GreyNoiseIndicator.format_timestamp(input_data) assert response == expected_output @pytest.mark.parametrize("input_data, tlp_color, expected_output", FORMAT_INDICATOR_DATA) def test_format_indicator(input_data, tlp_color, expected_output): """ Tests various combinations of GreyNoise classification data. """ response = GreyNoiseIndicator.format_indicator(input_data, tlp_color) assert response == expected_output @pytest.mark.parametrize("input_data, expected_output", BUILD_FEED_QUERY_DATA) def test_build_feed_query(input_data, expected_output): """ Tests various combinations of GreyNoise classification data. """ response = GreyNoiseIndicator.build_feed_query(input_data) assert response == expected_output @pytest.mark.parametrize("args, api_response, status_code, expected_output", GET_INDICATORS_COMMAND_DATA) def test_get_indicators_command(args, api_response, status_code, expected_output, mocker): """ Tests various combinations of valid and invalid responses for query command. """ api_config = GreyNoiseIndicator.APIConfig("true_api_key", "dummy_server", 10, "proxy", False, "dummy_integration") client = GreyNoiseIndicator.Client(api_config) dummy_response = DummyResponse({"Content-Type": "application/json"}, json.dumps(api_response), status_code) mocker.patch("requests.Session.get", return_value=dummy_response) response = GreyNoiseIndicator.get_indicators_command(client, args) assert response.raw_response == expected_output @pytest.mark.parametrize("args, api_response, status_code, expected_output", FETCH_INDICATORS_COMMAND_DATA) def test_fetch_indicators_command(args, api_response, status_code, expected_output, mocker): """ Tests various combinations of valid and invalid responses for query command. """ api_config = GreyNoiseIndicator.APIConfig("true_api_key", "dummy_server", 10, "proxy", False, "dummy_integration") client = GreyNoiseIndicator.Client(api_config) dummy_response = DummyResponse({"Content-Type": "application/json"}, json.dumps(api_response), status_code) mocker.patch("requests.Session.get", return_value=dummy_response) response = GreyNoiseIndicator.fetch_indicators_command(client, args) assert response == expected_output @pytest.mark.parametrize("test_case, api_response, status_code, expected_output", FETCH_INDICATORS_DATA) def test_fetch_indicators(test_case, api_response, status_code, expected_output, mocker): """ Tests various combinations of valid and invalid responses for query command. """ api_config = GreyNoiseIndicator.APIConfig("true_api_key", "dummy_server", 10, "proxy", False, "dummy_integration") client = GreyNoiseIndicator.Client(api_config) dummy_response = DummyResponse({"Content-Type": "application/json"}, json.dumps(api_response), status_code) mocker.patch("requests.Session.get", return_value=dummy_response) params = {} if test_case == "success": response = GreyNoiseIndicator.fetch_indicators(client, params) assert response == expected_output else: with pytest.raises(Exception) as err: GreyNoiseIndicator.fetch_indicators(client, params) assert str(err.value) == expected_output