From 10983c1a059879a52559a2bbf3b90e7c5be3b251 Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 12:46:22 +0000 Subject: [PATCH 01/13] Add search alert command --- Packs/Code42/Integrations/Code42/Code42.py | 28 +++++++- Packs/Code42/Integrations/Code42/Code42.yml | 41 ++++++++++- .../Code42/integration-Code42.yml | 69 ++++++++++++++++++- .../Code42GetDepartingEmployees/CHANGELOG.md | 2 + .../Code42GetDepartingEmployees.py | 16 +++++ .../Code42GetDepartingEmployees.yml | 17 +++++ .../Code42GetDepartingEmployees/README.md | 0 .../widget-Departing_Employees_Alerts.json | 35 ++++++++++ 8 files changed, 204 insertions(+), 4 deletions(-) create mode 100644 Packs/Code42/Scripts/Code42GetDepartingEmployees/CHANGELOG.md create mode 100644 Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py create mode 100644 Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.yml create mode 100644 Packs/Code42/Scripts/Code42GetDepartingEmployees/README.md create mode 100644 Packs/Code42/Widgets/widget-Departing_Employees_Alerts.json diff --git a/Packs/Code42/Integrations/Code42/Code42.py b/Packs/Code42/Integrations/Code42/Code42.py index 8d83633fe331..de3f2f00e056 100644 --- a/Packs/Code42/Integrations/Code42/Code42.py +++ b/Packs/Code42/Integrations/Code42/Code42.py @@ -20,7 +20,7 @@ FileCategory, ) from py42.sdk.queries.alerts.alert_query import AlertQuery -from py42.sdk.queries.alerts.filters import DateObserved, Severity, AlertState +from py42.sdk.queries.alerts.filters import DateObserved, Severity, AlertState, Actor as AlertActor # Disable insecure warnings requests.packages.urllib3.disable_warnings() @@ -216,6 +216,10 @@ def fetch_alerts(self, start_time, event_severity_filter): res = self._sdk.alerts.search(query) return res["alerts"] + def search_alerts(self, username): + query = AlertQuery(AlertActor.eq(username)) + return self._sdk.alerts.search(query)["alerts"] + def get_alert_details(self, alert_id): res = self._sdk.alerts.get_details(alert_id)["alerts"] if not res: @@ -509,6 +513,27 @@ def alert_resolve_command(client, args): return_error(create_command_error_message(demisto.command(), e)) +def alert_search_command(client, args): + username = args["username"] + try: + alerts = client.search_alerts(username) + alert_context = [] + for alert in alerts: + alert_context.append(map_to_code42_alert_context(alert)) + readable_outputs = tableToMarkdown( + "Code42 Security Alert Search", + alert_context, + headers=SECURITY_ALERT_HEADERS, + ) + return ( + readable_outputs, + {"Code42.SecurityAlert": alert_context}, + alerts + ) + + except Exception as e: + return_error(create_command_error_message(demisto.command(), e)) + @logger def departingemployee_add_command(client, args): departing_date = args.get("departuredate") @@ -815,6 +840,7 @@ def main(): commands = { "code42-alert-get": alert_get_command, "code42-alert-resolve": alert_resolve_command, + "code42-alert-search": alert_search_command, "code42-securitydata-search": securitydata_search_command, "code42-departingemployee-add": departingemployee_add_command, "code42-departingemployee-remove": departingemployee_remove_command, diff --git a/Packs/Code42/Integrations/Code42/Code42.yml b/Packs/Code42/Integrations/Code42/Code42.yml index e914c2b7feaa..822032a33c8e 100644 --- a/Packs/Code42/Integrations/Code42/Code42.yml +++ b/Packs/Code42/Integrations/Code42/Code42.yml @@ -240,7 +240,7 @@ script: - contextPath: Code42.SecurityAlert.Severity description: The severity of the alert. type: string - description: Retrieve alert details by alert ID + description: Retrieve alert details by alert ID. - name: code42-alert-resolve arguments: - name: id @@ -252,6 +252,43 @@ script: description: The alert ID of the resolved alert. type: string description: Resolves a Code42 Security alert. + - name: code42-alert-search + arguments: + - name: username + required: true + description: The username for the user to search alerts for. + outputs: + - contextPath: Code42.SecurityAlert.Username + description: The username associated with the alert. + type: string + - contextPath: Code42.SecurityAlert.Occurred + description: The timestamp when the alert occurred. + type: date + - contextPath: Code42.SecurityAlert.Description + description: The description of the alert. + type: string + - contextPath: Code42.SecurityAlert.ID + description: The alert ID. + type: string + - contextPath: Code42.SecurityAlert.Name + description: The alert rule name that generated the alert. + type: string + - contextPath: Code42.SecurityAlert.State + description: The alert state. + type: string + - contextPath: Code42.SecurityAlert.Type + description: The alert type. + type: string + - contextPath: Code42.SecurityAlert.Severity + description: The severity of the alert. + type: string + description: Search alerts by username. + + + + + + - name: code42-departingemployee-add arguments: - name: username @@ -362,6 +399,7 @@ script: type: string - contextPath: Code42.HighRiskEmployee.RiskTags description: Risk tags to associate with the High Risk Employee. + description: Add the given risk tags to the user with the given username. - name: code42-highriskemployee-remove-risk-tags arguments: - name: username @@ -379,6 +417,7 @@ script: type: string - contextPath: Code42.HighRiskEmployee.RiskTags description: Risk tags to disassociate from the High Risk Employee. + description: Remove the given risk tags from the user with the given username. dockerimage: demisto/py42:1.0.0.9242 isfetch: true runonce: false diff --git a/Packs/Code42/Integrations/Code42/integration-Code42.yml b/Packs/Code42/Integrations/Code42/integration-Code42.yml index 1bf98b61977e..b3e16f927b89 100644 --- a/Packs/Code42/Integrations/Code42/integration-Code42.yml +++ b/Packs/Code42/Integrations/Code42/integration-Code42.yml @@ -81,7 +81,7 @@ script: from py42.sdk.queries.alerts.alert_query import AlertQuery - from py42.sdk.queries.alerts.filters import DateObserved, Severity, AlertState + from py42.sdk.queries.alerts.filters import DateObserved, Severity, AlertState, Actor as AlertActor # Disable insecure warnings @@ -287,6 +287,10 @@ script: res = self._sdk.alerts.search(query) return res["alerts"] + def search_alerts(self, username): + query = AlertQuery(AlertActor.eq(username)) + return self._sdk.alerts.search(query)["alerts"] + def get_alert_details(self, alert_id): res = self._sdk.alerts.get_details(alert_id)["alerts"] if not res: @@ -588,6 +592,27 @@ script: return_error(create_command_error_message(demisto.command(), e)) + def alert_search_command(client, args): + username = args["username"] + try: + alerts = client.search_alerts(username) + alert_context = [] + for alert in alerts: + alert_context.append(map_to_code42_alert_context(alert)) + readable_outputs = tableToMarkdown( + "Code42 Security Alert Search", + alert_context, + headers=SECURITY_ALERT_HEADERS, + ) + return ( + readable_outputs, + {"Code42.SecurityAlert": alert_context}, + alerts + ) + + except Exception as e: + return_error(create_command_error_message(demisto.command(), e)) + @logger def departingemployee_add_command(client, args): @@ -903,6 +928,7 @@ script: commands = { "code42-alert-get": alert_get_command, "code42-alert-resolve": alert_resolve_command, + "code42-alert-search": alert_search_command, "code42-securitydata-search": securitydata_search_command, "code42-departingemployee-add": departingemployee_add_command, "code42-departingemployee-remove": departingemployee_remove_command, @@ -1128,7 +1154,7 @@ script: - contextPath: Code42.SecurityAlert.Severity description: The severity of the alert. type: string - description: Retrieve alert details by alert ID + description: Retrieve alert details by alert ID. - name: code42-alert-resolve arguments: - name: id @@ -1139,6 +1165,43 @@ script: description: The alert ID of the resolved alert. type: string description: Resolves a Code42 Security alert. + - name: code42-alert-search + arguments: + - name: username + required: true + description: The username for the user to search alerts for. + outputs: + - contextPath: Code42.SecurityAlert.Username + description: The username associated with the alert. + type: string + - contextPath: Code42.SecurityAlert.Occurred + description: The timestamp when the alert occurred. + type: date + - contextPath: Code42.SecurityAlert.Description + description: The description of the alert. + type: string + - contextPath: Code42.SecurityAlert.ID + description: The alert ID. + type: string + - contextPath: Code42.SecurityAlert.Name + description: The alert rule name that generated the alert. + type: string + - contextPath: Code42.SecurityAlert.State + description: The alert state. + type: string + - contextPath: Code42.SecurityAlert.Type + description: The alert type. + type: string + - contextPath: Code42.SecurityAlert.Severity + description: The severity of the alert. + type: string + description: Search alerts by username. + + + + + + - name: code42-departingemployee-add arguments: - name: username @@ -1249,6 +1312,7 @@ script: type: string - contextPath: Code42.HighRiskEmployee.RiskTags description: Risk tags to associate with the High Risk Employee. + description: Add the given risk tags to the user with the given username. - name: code42-highriskemployee-remove-risk-tags arguments: - name: username @@ -1266,6 +1330,7 @@ script: type: string - contextPath: Code42.HighRiskEmployee.RiskTags description: Risk tags to disassociate from the High Risk Employee. + description: Remove the given risk tags from the user with the given username. dockerimage: demisto/py42:1.0.0.9242 isfetch: true runonce: false diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployees/CHANGELOG.md b/Packs/Code42/Scripts/Code42GetDepartingEmployees/CHANGELOG.md new file mode 100644 index 000000000000..63439c17f377 --- /dev/null +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployees/CHANGELOG.md @@ -0,0 +1,2 @@ +## [Unreleased] +- diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py b/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py new file mode 100644 index 000000000000..5e031b0c412b --- /dev/null +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py @@ -0,0 +1,16 @@ +import demistomock as demisto +from CommonServerPython import * + +res = {"total": 0, "data": []} +employees = demisto.executeCommand("code42-departingemployee-get-all", {})[0]["Contents"] +res["total"] = len(employees) + +for employee in employees: + user_id = employee["userId"] + + + + employee_res = {"Username": employee["userName"]} + res["data"].append(employee_res) + +demisto.results(res) diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.yml b/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.yml new file mode 100644 index 000000000000..4fd66c3c8437 --- /dev/null +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.yml @@ -0,0 +1,17 @@ +comment: Gets all departing employees and alerts for each. +commonfields: + id: 468c8e6f-6f50-486f-8cde-7dabe4cbeb2b + version: -1 +dependson: + must: + - Code42|||code42-departingemployee-get-all +dockerimage: demisto/py42:1.0.0.9242 +enabled: true +name: Code42GetDepartingEmployees +pswd: "" +runas: DBotWeakRole +runonce: false +script: '' +scripttarget: 0 +subtype: python3 +type: python diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployees/README.md b/Packs/Code42/Scripts/Code42GetDepartingEmployees/README.md new file mode 100644 index 000000000000..e69de29bb2d1 diff --git a/Packs/Code42/Widgets/widget-Departing_Employees_Alerts.json b/Packs/Code42/Widgets/widget-Departing_Employees_Alerts.json new file mode 100644 index 000000000000..75fbc8f1c16d --- /dev/null +++ b/Packs/Code42/Widgets/widget-Departing_Employees_Alerts.json @@ -0,0 +1,35 @@ +{ + "category": "", + "dataType": "scripts", + "dateRange": { + "fromDate": "0001-01-01T00:00:00Z", + "fromDateLicense": "0001-01-01T00:00:00Z", + "period": { + "by": "", + "byFrom": "days", + "byTo": "", + "field": "", + "fromValue": null, + "toValue": null + }, + "toDate": "0001-01-01T00:00:00Z" + }, + "id": "570ec235-7ee4-43ea-8fc7-eba94a0cca71", + "isPredefined": false, + "name": "Departing Employees Alerts", + "params": { + "tableColumns": [ + { + "displayed": true, + "isDefault": true, + "key": "Username" + } + ] + }, + "query": "Code42GetDepartingEmployees", + "size": 0, + "sort": null, + "sortValues": null, + "version": -1, + "widgetType": "table" +} \ No newline at end of file From 7000efb570fc73193d304dca818d8d121537be25 Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 13:09:53 +0000 Subject: [PATCH 02/13] Save progress --- Packs/Code42/Integrations/Code42/CHANGELOG.md | 2 ++ .../Code42GetDepartingEmployees.py | 22 +++++++++++-------- .../Code42GetDepartingEmployees.yml | 1 + .../widget-Departing_Employees_Alerts.json | 5 +++++ 4 files changed, 21 insertions(+), 9 deletions(-) diff --git a/Packs/Code42/Integrations/Code42/CHANGELOG.md b/Packs/Code42/Integrations/Code42/CHANGELOG.md index 244b5e76f237..d04b1c3823ab 100644 --- a/Packs/Code42/Integrations/Code42/CHANGELOG.md +++ b/Packs/Code42/Integrations/Code42/CHANGELOG.md @@ -1,5 +1,7 @@ ## [Unreleased] Added new commands: + - **Code42GetDepartingEmployees** which gets departing employees and alerts for each employee. + - **code42-alert-search** that searches alerts by username. - **code42-departingemployee-get-all** that gets all the employees on the Departing Employee List. - **code42-highriskemployee-add** that takes a username and adds the employee to the High Risk Employee List. - **code42-highriskemployee-remove** that takes a username and remove the employee from the High Risk Employee List. diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py b/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py index 5e031b0c412b..d518a75efe66 100644 --- a/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py @@ -2,15 +2,19 @@ from CommonServerPython import * res = {"total": 0, "data": []} -employees = demisto.executeCommand("code42-departingemployee-get-all", {})[0]["Contents"] -res["total"] = len(employees) -for employee in employees: - user_id = employee["userId"] +try: + employees = demisto.executeCommand("code42-departingemployee-get-all", {})[0]["Contents"] + res["total"] = len(employees) + for employee in employees: + username = employee["userName"] + alerts = demisto.executeCommand("code42-alert-search", {"username": username})[0]["Contents"] + alerts_count = len(alerts) + if alerts_count: + employee_res = {"Username": username, "Alerts Count": alerts_count} + res["data"].append(employee_res) - - employee_res = {"Username": employee["userName"]} - res["data"].append(employee_res) - -demisto.results(res) + demisto.results(res) +except Exception as e: + demisto.results(e) diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.yml b/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.yml index 4fd66c3c8437..41bfc6673381 100644 --- a/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.yml +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.yml @@ -5,6 +5,7 @@ commonfields: dependson: must: - Code42|||code42-departingemployee-get-all + - Code42|||code42-alerts-search dockerimage: demisto/py42:1.0.0.9242 enabled: true name: Code42GetDepartingEmployees diff --git a/Packs/Code42/Widgets/widget-Departing_Employees_Alerts.json b/Packs/Code42/Widgets/widget-Departing_Employees_Alerts.json index 75fbc8f1c16d..2f256486b03b 100644 --- a/Packs/Code42/Widgets/widget-Departing_Employees_Alerts.json +++ b/Packs/Code42/Widgets/widget-Departing_Employees_Alerts.json @@ -23,6 +23,11 @@ "displayed": true, "isDefault": true, "key": "Username" + }, + { + "displayed": true, + "isDefault": true, + "key": "Alerts Count" } ] }, From 4affd1b0fac5b11c2e057f9a1778b0e872c468f9 Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 17:21:05 +0000 Subject: [PATCH 03/13] Rename --- .../CHANGELOG.md | 0 .../Code42GetDepartingEmployeeAlerts.py | 30 +++++++++++++++++++ .../Code42GetDepartingEmployeeAlerts.yml} | 0 .../README.md | 0 .../Code42GetDepartingEmployees.py | 20 ------------- ... => widget-Departing_Employee_Alerts.json} | 0 6 files changed, 30 insertions(+), 20 deletions(-) rename Packs/Code42/Scripts/{Code42GetDepartingEmployees => Code42GetDepartingEmployeeAlerts}/CHANGELOG.md (100%) create mode 100644 Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py rename Packs/Code42/Scripts/{Code42GetDepartingEmployees/Code42GetDepartingEmployees.yml => Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml} (100%) rename Packs/Code42/Scripts/{Code42GetDepartingEmployees => Code42GetDepartingEmployeeAlerts}/README.md (100%) delete mode 100644 Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py rename Packs/Code42/Widgets/{widget-Departing_Employees_Alerts.json => widget-Departing_Employee_Alerts.json} (100%) diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployees/CHANGELOG.md b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/CHANGELOG.md similarity index 100% rename from Packs/Code42/Scripts/Code42GetDepartingEmployees/CHANGELOG.md rename to Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/CHANGELOG.md diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py new file mode 100644 index 000000000000..a06cd3c05458 --- /dev/null +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py @@ -0,0 +1,30 @@ +import demistomock as demisto +from CommonServerPython import * + +res = {"total": 0} +res_data = [] + +try: + employees = demisto.executeCommand("code42-departingemployee-get-all", {})[0]["Contents"] + res["total"] = len(employees) + + # Get each employee on the Departing Employee List and their total alerts. + for employee in employees: + username = employee["userName"] + alerts = demisto.executeCommand("code42-alert-search", {"username": username})[0]["Contents"] + alerts_count = len(alerts) + employee_res = {"Username": username, "Alerts Count": alerts_count} + res_data.append(employee_res) + + # Sort such that highest alert counts are first. + res["data"] = sorted(res_data, key=lambda x: x["Alerts Count"], reverse=True) + demisto.results(res) +except Exception as e: + res = { + "Type": entryTypes["error"], + "ContentsFormat": formats["text"], + "Contents": "Exception info:\n{0}".format(str(ex)) + } + +# Submit final results to Cortex XSOAR +demisto.results(res) diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.yml b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml similarity index 100% rename from Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.yml rename to Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployees/README.md b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/README.md similarity index 100% rename from Packs/Code42/Scripts/Code42GetDepartingEmployees/README.md rename to Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/README.md diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py b/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py deleted file mode 100644 index d518a75efe66..000000000000 --- a/Packs/Code42/Scripts/Code42GetDepartingEmployees/Code42GetDepartingEmployees.py +++ /dev/null @@ -1,20 +0,0 @@ -import demistomock as demisto -from CommonServerPython import * - -res = {"total": 0, "data": []} - -try: - employees = demisto.executeCommand("code42-departingemployee-get-all", {})[0]["Contents"] - res["total"] = len(employees) - - for employee in employees: - username = employee["userName"] - alerts = demisto.executeCommand("code42-alert-search", {"username": username})[0]["Contents"] - alerts_count = len(alerts) - if alerts_count: - employee_res = {"Username": username, "Alerts Count": alerts_count} - res["data"].append(employee_res) - - demisto.results(res) -except Exception as e: - demisto.results(e) diff --git a/Packs/Code42/Widgets/widget-Departing_Employees_Alerts.json b/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json similarity index 100% rename from Packs/Code42/Widgets/widget-Departing_Employees_Alerts.json rename to Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json From f54c3b6db214e9b5f2a9f6e3297c41b375ef5d03 Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 17:21:13 +0000 Subject: [PATCH 04/13] Rename --- .../Code42GetDepartingEmployeeAlerts.yml | 2 +- Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml index 41bfc6673381..e6e5d6e60798 100644 --- a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml @@ -8,7 +8,7 @@ dependson: - Code42|||code42-alerts-search dockerimage: demisto/py42:1.0.0.9242 enabled: true -name: Code42GetDepartingEmployees +name: Code42GetDepartingEmployeeAlerts pswd: "" runas: DBotWeakRole runonce: false diff --git a/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json b/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json index 2f256486b03b..1b097e32e9af 100644 --- a/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json +++ b/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json @@ -16,7 +16,7 @@ }, "id": "570ec235-7ee4-43ea-8fc7-eba94a0cca71", "isPredefined": false, - "name": "Departing Employees Alerts", + "name": "Departing Employee Alerts", "params": { "tableColumns": [ { @@ -31,7 +31,7 @@ } ] }, - "query": "Code42GetDepartingEmployees", + "query": "Code42GetDepartingEmployeeAlerts", "size": 0, "sort": null, "sortValues": null, From 4aa37910558051fbbbe450ef6f86fc103585cf26 Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 17:26:44 +0000 Subject: [PATCH 05/13] Test alert search command --- Packs/Code42/Integrations/Code42/Code42_test.py | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/Packs/Code42/Integrations/Code42/Code42_test.py b/Packs/Code42/Integrations/Code42/Code42_test.py index e2d7dba7ce58..328a11c3f257 100644 --- a/Packs/Code42/Integrations/Code42/Code42_test.py +++ b/Packs/Code42/Integrations/Code42/Code42_test.py @@ -12,6 +12,7 @@ map_to_file_context, alert_get_command, alert_resolve_command, + alert_search_command, departingemployee_add_command, departingemployee_remove_command, departingemployee_get_all_command, @@ -994,6 +995,12 @@ def test_alert_resolve_command(code42_alerts_mock): assert res["id"] == "36fb8ca5-0533-4d25-9763-e09d35d60610" +def test_alert_search_command(code42_alerts_mock): + client = create_client(code42_alerts_mock) + _, _, res = alert_search_command(client, {"username": "user1@example.com"}) + assert res == json.loads(MOCK_ALERTS_RESPONSE)["alerts"] + + def test_departingemployee_add_command(code42_sdk_mock): client = create_client(code42_sdk_mock) _, _, res = departingemployee_add_command( From 3d50bd0727a2935871586836c7144268d243805b Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 18:02:55 +0000 Subject: [PATCH 06/13] Handle getting only top x number --- .../Code42GetDepartingEmployeeAlerts.py | 13 ++++++------- .../Code42GetDepartingEmployeeAlerts.yml | 6 ++++++ 2 files changed, 12 insertions(+), 7 deletions(-) diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py index a06cd3c05458..b1eb3c4feace 100644 --- a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py @@ -1,8 +1,10 @@ import demistomock as demisto from CommonServerPython import * + res = {"total": 0} res_data = [] +top = demisto.args().get("top") or 10 try: employees = demisto.executeCommand("code42-departingemployee-get-all", {})[0]["Contents"] @@ -16,15 +18,12 @@ employee_res = {"Username": username, "Alerts Count": alerts_count} res_data.append(employee_res) - # Sort such that highest alert counts are first. - res["data"] = sorted(res_data, key=lambda x: x["Alerts Count"], reverse=True) + # Sort such that highest alert counts are first and get top. + res["data"] = sorted(res_data, key=lambda x: x["Alerts Count"], reverse=True)[:top] demisto.results(res) except Exception as e: - res = { - "Type": entryTypes["error"], - "ContentsFormat": formats["text"], - "Contents": "Exception info:\n{0}".format(str(ex)) - } + res["total"] = -1 + res["data"] = str(e) # Submit final results to Cortex XSOAR demisto.results(res) diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml index e6e5d6e60798..6b6f9f495d2a 100644 --- a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml @@ -1,3 +1,8 @@ +args: +- defaultValue: 10 + description: To limit results to x number of employees with the highest alert count. + name: top + type: number comment: Gets all departing employees and alerts for each. commonfields: id: 468c8e6f-6f50-486f-8cde-7dabe4cbeb2b @@ -15,4 +20,5 @@ runonce: false script: '' scripttarget: 0 subtype: python3 +tags: [] type: python From 515e438395d40fd51d27c2fe55c36480e13d602b Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 18:16:02 +0000 Subject: [PATCH 07/13] ignore 0 --- .../Code42GetDepartingEmployeeAlerts.py | 7 +++++-- Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json | 7 ++++++- 2 files changed, 11 insertions(+), 3 deletions(-) diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py index b1eb3c4feace..83e457d30c59 100644 --- a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py @@ -15,8 +15,11 @@ username = employee["userName"] alerts = demisto.executeCommand("code42-alert-search", {"username": username})[0]["Contents"] alerts_count = len(alerts) - employee_res = {"Username": username, "Alerts Count": alerts_count} - res_data.append(employee_res) + + # Ignores employees without alerts + if alerts_count: + employee_res = {"Username": username, "Alerts Count": alerts_count} + res_data.append(employee_res) # Sort such that highest alert counts are first and get top. res["data"] = sorted(res_data, key=lambda x: x["Alerts Count"], reverse=True)[:top] diff --git a/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json b/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json index 1b097e32e9af..14f85e30ebde 100644 --- a/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json +++ b/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json @@ -24,12 +24,17 @@ "isDefault": true, "key": "Username" }, + { + "displayed": true, + "isDefault": true, + "key": "Alerts Count" + }, { "displayed": true, "isDefault": true, "key": "Alerts Count" } - ] + ] }, "query": "Code42GetDepartingEmployeeAlerts", "size": 0, From c7dca90467bd6c214ad88e28f1a5adc90faf1fc7 Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 18:17:03 +0000 Subject: [PATCH 08/13] Fix cl --- Packs/Code42/Integrations/Code42/CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Packs/Code42/Integrations/Code42/CHANGELOG.md b/Packs/Code42/Integrations/Code42/CHANGELOG.md index d04b1c3823ab..3226c1a1b14f 100644 --- a/Packs/Code42/Integrations/Code42/CHANGELOG.md +++ b/Packs/Code42/Integrations/Code42/CHANGELOG.md @@ -1,6 +1,6 @@ ## [Unreleased] Added new commands: - - **Code42GetDepartingEmployees** which gets departing employees and alerts for each employee. + - **Code42GetDepartingEmployees** automation script which gets departing employees with alerts. - **code42-alert-search** that searches alerts by username. - **code42-departingemployee-get-all** that gets all the employees on the Departing Employee List. - **code42-highriskemployee-add** that takes a username and adds the employee to the High Risk Employee List. From d38b5e90f2de3fa70a857aba988a77c8d4be79aa Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 18:17:16 +0000 Subject: [PATCH 09/13] Fix cl --- Packs/Code42/Integrations/Code42/CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Packs/Code42/Integrations/Code42/CHANGELOG.md b/Packs/Code42/Integrations/Code42/CHANGELOG.md index 3226c1a1b14f..dd10bb0a433f 100644 --- a/Packs/Code42/Integrations/Code42/CHANGELOG.md +++ b/Packs/Code42/Integrations/Code42/CHANGELOG.md @@ -1,6 +1,6 @@ ## [Unreleased] Added new commands: - - **Code42GetDepartingEmployees** automation script which gets departing employees with alerts. + - **Code42GetDepartingEmployeeAlerts** automation script which gets departing employees with alerts. - **code42-alert-search** that searches alerts by username. - **code42-departingemployee-get-all** that gets all the employees on the Departing Employee List. - **code42-highriskemployee-add** that takes a username and adds the employee to the High Risk Employee List. From b84049f9d581fd6ed48917dbeb2842aa1ee94b81 Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 18:18:02 +0000 Subject: [PATCH 10/13] Remove whitespace in yml --- Packs/Code42/Integrations/Code42/Code42.yml | 6 ------ 1 file changed, 6 deletions(-) diff --git a/Packs/Code42/Integrations/Code42/Code42.yml b/Packs/Code42/Integrations/Code42/Code42.yml index 822032a33c8e..a5b742574476 100644 --- a/Packs/Code42/Integrations/Code42/Code42.yml +++ b/Packs/Code42/Integrations/Code42/Code42.yml @@ -283,12 +283,6 @@ script: description: The severity of the alert. type: string description: Search alerts by username. - - - - - - - name: code42-departingemployee-add arguments: - name: username From 6f7ebc526d1d95e91d3e756cfbf9c071adf75c45 Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 18:19:01 +0000 Subject: [PATCH 11/13] Gen yml --- Packs/Code42/Integrations/Code42/integration-Code42.yml | 6 ------ 1 file changed, 6 deletions(-) diff --git a/Packs/Code42/Integrations/Code42/integration-Code42.yml b/Packs/Code42/Integrations/Code42/integration-Code42.yml index b3e16f927b89..a04731a12049 100644 --- a/Packs/Code42/Integrations/Code42/integration-Code42.yml +++ b/Packs/Code42/Integrations/Code42/integration-Code42.yml @@ -1196,12 +1196,6 @@ script: description: The severity of the alert. type: string description: Search alerts by username. - - - - - - - name: code42-departingemployee-add arguments: - name: username From 752883895d04676e9db15c8e1ed5c62904c74748 Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Tue, 23 Jun 2020 18:21:34 +0000 Subject: [PATCH 12/13] Main --- .../Code42GetDepartingEmployeeAlerts.py | 56 ++++++++++--------- 1 file changed, 30 insertions(+), 26 deletions(-) diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py index 83e457d30c59..8f428d0bfa92 100644 --- a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.py @@ -2,31 +2,35 @@ from CommonServerPython import * -res = {"total": 0} -res_data = [] -top = demisto.args().get("top") or 10 - -try: - employees = demisto.executeCommand("code42-departingemployee-get-all", {})[0]["Contents"] - res["total"] = len(employees) - - # Get each employee on the Departing Employee List and their total alerts. - for employee in employees: - username = employee["userName"] - alerts = demisto.executeCommand("code42-alert-search", {"username": username})[0]["Contents"] - alerts_count = len(alerts) - - # Ignores employees without alerts - if alerts_count: - employee_res = {"Username": username, "Alerts Count": alerts_count} - res_data.append(employee_res) - - # Sort such that highest alert counts are first and get top. - res["data"] = sorted(res_data, key=lambda x: x["Alerts Count"], reverse=True)[:top] +def main(): + res = {"total": 0} + res_data = [] + top = demisto.args().get("top") or 10 + + try: + employees = demisto.executeCommand("code42-departingemployee-get-all", {})[0]["Contents"] + res["total"] = len(employees) + + # Get each employee on the Departing Employee List and their total alerts. + for employee in employees: + username = employee["userName"] + alerts = demisto.executeCommand("code42-alert-search", {"username": username})[0]["Contents"] + alerts_count = len(alerts) + + # Ignores employees without alerts + if alerts_count: + employee_res = {"Username": username, "Alerts Count": alerts_count} + res_data.append(employee_res) + + # Sort such that highest alert counts are first and get top. + res["data"] = sorted(res_data, key=lambda x: x["Alerts Count"], reverse=True)[:top] + demisto.results(res) + except Exception as e: + res["total"] = -1 + res["data"] = str(e) + + # Submit final results to Cortex XSOAR demisto.results(res) -except Exception as e: - res["total"] = -1 - res["data"] = str(e) -# Submit final results to Cortex XSOAR -demisto.results(res) +if __name__ in ("__main__", "__builtin__", "builtins"): + main() From 4af651b362849010691f62595c02a0c139e840fd Mon Sep 17 00:00:00 2001 From: Juliya Smith Date: Wed, 24 Jun 2020 13:13:46 +0000 Subject: [PATCH 13/13] Tags --- .../Code42GetDepartingEmployeeAlerts.yml | 2 +- Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json | 5 ----- 2 files changed, 1 insertion(+), 6 deletions(-) diff --git a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml index 6b6f9f495d2a..67d299bd84c3 100644 --- a/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml +++ b/Packs/Code42/Scripts/Code42GetDepartingEmployeeAlerts/Code42GetDepartingEmployeeAlerts.yml @@ -20,5 +20,5 @@ runonce: false script: '' scripttarget: 0 subtype: python3 -tags: [] +tags: ['dynamic-section', 'widget'] type: python diff --git a/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json b/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json index 14f85e30ebde..426a1ba23c79 100644 --- a/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json +++ b/Packs/Code42/Widgets/widget-Departing_Employee_Alerts.json @@ -24,11 +24,6 @@ "isDefault": true, "key": "Username" }, - { - "displayed": true, - "isDefault": true, - "key": "Alerts Count" - }, { "displayed": true, "isDefault": true,