Refactored Finding DTO into ScoutSuiteFinding and MonkeyFinding DTO which inherit from more abstract Finding.

This commit is contained in:
VakarisZ 2021-02-08 17:38:45 +02:00
parent 9444067250
commit 80e7435572
16 changed files with 150 additions and 95 deletions

View File

@ -22,10 +22,6 @@ STATUS_FAILED = "Failed"
# Don't change order! The statuses are ordered by importance/severity.
ORDERED_TEST_STATUSES = [STATUS_FAILED, STATUS_VERIFY, STATUS_PASSED, STATUS_UNEXECUTED]
MONKEY_FINDING = "monkey_finding"
SCOUTSUITE_FINDING = "scoutsuite_finding"
FINDING_TYPES = [MONKEY_FINDING, SCOUTSUITE_FINDING]
TEST_DATA_ENDPOINT_ELASTIC = "unencrypted_data_endpoint_elastic"
TEST_DATA_ENDPOINT_HTTP = "unencrypted_data_endpoint_http"
TEST_MACHINE_EXPLOITED = "machine_exploited"

View File

@ -4,7 +4,8 @@ Define a Document Schema for Zero Trust findings.
"""
from __future__ import annotations
from typing import Union
import abc
from mongoengine import Document, GenericLazyReferenceField, StringField
@ -12,7 +13,6 @@ import common.common_consts.zero_trust_consts as zero_trust_consts
# Dummy import for mongoengine.
# noinspection PyUnresolvedReferences
from monkey_island.cc.models.zero_trust.monkey_finding_details import MonkeyFindingDetails
from monkey_island.cc.models.zero_trust.scoutsuite_finding_details import ScoutSuiteFindingDetails
class Finding(Document):
@ -33,39 +33,21 @@ class Finding(Document):
* The logic section defines complex questions we can ask about a single document which are asked multiple
times, or complex action we will perform - somewhat like an API.
"""
# SCHEMA
test = StringField(required=True, choices=zero_trust_consts.TESTS)
status = StringField(required=True, choices=zero_trust_consts.ORDERED_TEST_STATUSES)
finding_type = StringField(required=True, choices=zero_trust_consts.FINDING_TYPES)
# Details are in a separate document in order to discourage pulling them when not needed
# due to performance.
details = GenericLazyReferenceField(choices=[MonkeyFindingDetails, ScoutSuiteFindingDetails], required=True)
# http://docs.mongoengine.org/guide/defining-documents.html#document-inheritance
meta = {'allow_inheritance': True}
# LOGIC
def get_test_explanation(self):
return zero_trust_consts.TESTS_MAP[self.test][zero_trust_consts.TEST_EXPLANATION_KEY]
# SCHEMA
test = StringField(required=True, choices=zero_trust_consts.TESTS)
status = StringField(required=True, choices=zero_trust_consts.ORDERED_TEST_STATUSES)
def get_pillars(self):
return zero_trust_consts.TESTS_MAP[self.test][zero_trust_consts.PILLARS_KEY]
# Details are in a separate document in order to discourage pulling them when not needed
# due to performance.
details = GenericLazyReferenceField(required=True)
# Creation methods
@staticmethod
@abc.abstractmethod
def save_finding(test: str,
status: str,
detail_ref: Union[MonkeyFindingDetails, ScoutSuiteFindingDetails]) -> Finding:
finding = Finding(test=test,
status=status,
details=detail_ref,
finding_type=Finding._get_finding_type_by_details(detail_ref))
finding.save()
return finding
@staticmethod
def _get_finding_type_by_details(details: Union[MonkeyFindingDetails, ScoutSuiteFindingDetails]) -> str:
if type(details) == MonkeyFindingDetails:
return zero_trust_consts.MONKEY_FINDING
else:
return zero_trust_consts.SCOUTSUITE_FINDING
detail_ref) -> Finding:
pass

View File

@ -0,0 +1,18 @@
from mongoengine import LazyReferenceField
from monkey_island.cc.models.zero_trust.finding import Finding
from monkey_island.cc.models.zero_trust.monkey_finding_details import MonkeyFindingDetails
class MonkeyFinding(Finding):
details = LazyReferenceField(MonkeyFindingDetails, required=True)
@staticmethod
def save_finding(test: str,
status: str,
detail_ref: MonkeyFindingDetails) -> Finding:
monkey_finding = MonkeyFinding(test=test,
status=status,
details=detail_ref)
monkey_finding.save()
return monkey_finding

View File

@ -0,0 +1,18 @@
from mongoengine import LazyReferenceField
from monkey_island.cc.models.zero_trust.finding import Finding
from monkey_island.cc.models.zero_trust.scoutsuite_finding_details import ScoutSuiteFindingDetails
class ScoutSuiteFinding(Finding):
details = LazyReferenceField(ScoutSuiteFindingDetails, required=True)
@staticmethod
def save_finding(test: str,
status: str,
detail_ref: ScoutSuiteFindingDetails) -> Finding:
scoutsuite_finding = ScoutSuiteFinding(test=test,
status=status,
details=detail_ref)
scoutsuite_finding.save()
return scoutsuite_finding

View File

@ -4,30 +4,23 @@ from mongoengine import ValidationError
import common.common_consts.zero_trust_consts as zero_trust_consts
from monkey_island.cc.models.zero_trust.event import Event
from monkey_island.cc.models.zero_trust.finding import Finding
from monkey_island.cc.models.zero_trust.monkey_finding import MonkeyFinding
from monkey_island.cc.models.zero_trust.monkey_finding_details import MonkeyFindingDetails
from monkey_island.cc.models.zero_trust.scoutsuite_finding_details import ScoutSuiteFindingDetails
from monkey_island.cc.test_common.fixtures import FixtureEnum
MONKEY_FINDING_DETAIL_MOCK = MonkeyFindingDetails()
MONKEY_FINDING_DETAIL_MOCK.events = ['mock1', 'mock2']
SCOUTSUITE_FINDING_DETAIL_MOCK = ScoutSuiteFindingDetails()
SCOUTSUITE_FINDING_DETAIL_MOCK.scoutsuite_rules = []
class TestFinding:
class TestMonkeyFinding:
@pytest.mark.usefixtures(FixtureEnum.USES_DATABASE)
def test_save_finding_validation(self):
with pytest.raises(ValidationError):
_ = Finding.save_finding(test="bla bla",
_ = MonkeyFinding.save_finding(test="bla bla",
status=zero_trust_consts.STATUS_FAILED,
detail_ref=MONKEY_FINDING_DETAIL_MOCK)
with pytest.raises(ValidationError):
_ = Finding.save_finding(test=zero_trust_consts.TEST_SEGMENTATION,
status="bla bla",
detail_ref=SCOUTSUITE_FINDING_DETAIL_MOCK)
@pytest.mark.usefixtures(FixtureEnum.USES_DATABASE)
def test_save_finding_sanity(self):
assert len(Finding.objects(test=zero_trust_consts.TEST_SEGMENTATION)) == 0
@ -37,8 +30,10 @@ class TestFinding:
monkey_details_example = MonkeyFindingDetails()
monkey_details_example.events.append(event_example)
monkey_details_example.save()
Finding.save_finding(test=zero_trust_consts.TEST_SEGMENTATION,
status=zero_trust_consts.STATUS_FAILED, detail_ref=monkey_details_example)
MonkeyFinding.save_finding(test=zero_trust_consts.TEST_SEGMENTATION,
status=zero_trust_consts.STATUS_FAILED,
detail_ref=monkey_details_example)
assert len(Finding.objects(test=zero_trust_consts.TEST_SEGMENTATION)) == 1
assert len(MonkeyFinding.objects(test=zero_trust_consts.TEST_SEGMENTATION)) == 1
assert len(MonkeyFinding.objects(status=zero_trust_consts.STATUS_FAILED)) == 1
assert len(Finding.objects(status=zero_trust_consts.STATUS_FAILED)) == 1

View File

@ -0,0 +1,41 @@
import pytest
from mongoengine import ValidationError
import common.common_consts.zero_trust_consts as zero_trust_consts
from monkey_island.cc.models.zero_trust.finding import Finding
from monkey_island.cc.models.zero_trust.monkey_finding_details import MonkeyFindingDetails
from monkey_island.cc.models.zero_trust.scoutsuite_finding import ScoutSuiteFinding
from monkey_island.cc.models.zero_trust.scoutsuite_finding_details import ScoutSuiteFindingDetails
from monkey_island.cc.services.zero_trust.test_common.scoutsuite_finding_data import RULES
from monkey_island.cc.test_common.fixtures import FixtureEnum
MONKEY_FINDING_DETAIL_MOCK = MonkeyFindingDetails()
MONKEY_FINDING_DETAIL_MOCK.events = ['mock1', 'mock2']
SCOUTSUITE_FINDING_DETAIL_MOCK = ScoutSuiteFindingDetails()
SCOUTSUITE_FINDING_DETAIL_MOCK.scoutsuite_rules = []
class TestScoutSuiteFinding:
@pytest.mark.usefixtures(FixtureEnum.USES_DATABASE)
def test_save_finding_validation(self):
with pytest.raises(ValidationError):
_ = ScoutSuiteFinding.save_finding(test=zero_trust_consts.TEST_SEGMENTATION,
status="bla bla",
detail_ref=SCOUTSUITE_FINDING_DETAIL_MOCK)
@pytest.mark.usefixtures(FixtureEnum.USES_DATABASE)
def test_save_finding_sanity(self):
assert len(Finding.objects(test=zero_trust_consts.TEST_SEGMENTATION)) == 0
rule_example = RULES[0]
scoutsuite_details_example = ScoutSuiteFindingDetails()
scoutsuite_details_example.scoutsuite_rules.append(rule_example)
scoutsuite_details_example.save()
ScoutSuiteFinding.save_finding(test=zero_trust_consts.TEST_SEGMENTATION,
status=zero_trust_consts.STATUS_FAILED,
detail_ref=scoutsuite_details_example)
assert len(ScoutSuiteFinding.objects(test=zero_trust_consts.TEST_SEGMENTATION)) == 1
assert len(ScoutSuiteFinding.objects(status=zero_trust_consts.STATUS_FAILED)) == 1
assert len(Finding.objects(status=zero_trust_consts.STATUS_FAILED)) == 1

View File

@ -24,7 +24,7 @@ class ZeroTrustReport(flask_restful.Resource):
elif report_data == REPORT_DATA_PRINCIPLES_STATUS:
return jsonify(PrincipleService.get_principles_status())
elif report_data == REPORT_DATA_FINDINGS:
return jsonify(FindingService.get_all_findings())
return jsonify(FindingService.get_all_findings_for_ui())
elif report_data == REPORT_DATA_SCOUTSUITE:
# Raw ScoutSuite data is already solved as json, no need to jsonify
return Response(ScoutSuiteRawDataService.get_scoutsuite_data_json(),

View File

@ -4,14 +4,14 @@ from bson import ObjectId
from common.common_consts import zero_trust_consts
from monkey_island.cc.models.zero_trust.event import Event
from monkey_island.cc.models.zero_trust.finding import Finding
from monkey_island.cc.models.zero_trust.monkey_finding import MonkeyFinding
from monkey_island.cc.models.zero_trust.monkey_finding_details import MonkeyFindingDetails
class MonkeyZTFindingService:
@staticmethod
def create_or_add_to_existing(test: str, status: str, events: str):
def create_or_add_to_existing(test: str, status: str, events: List[Event]):
"""
Create a new finding or add the events to an existing one if it's the same (same meaning same status and same
test).
@ -19,7 +19,7 @@ class MonkeyZTFindingService:
:raises: Assertion error if this is used when there's more then one finding which fits the query - this is not
when this function should be used.
"""
existing_findings = Finding.objects(test=test, status=status)
existing_findings = MonkeyFinding.objects(test=test, status=status)
assert (len(existing_findings) < 2), "More than one finding exists for {}:{}".format(test, status)
if len(existing_findings) == 0:
@ -33,15 +33,15 @@ class MonkeyZTFindingService:
details = MonkeyFindingDetails()
details.events = events
details.save()
Finding.save_finding(test, status, details)
MonkeyFinding.save_finding(test, status, details)
@staticmethod
def add_events(finding: Finding, events: List[Event]):
def add_events(finding: MonkeyFinding, events: List[Event]):
finding.details.fetch().add_events(events).save()
@staticmethod
def get_events_by_finding(finding_id: str) -> List[object]:
finding = Finding.objects.get(id=finding_id)
finding = MonkeyFinding.objects.get(id=finding_id)
pipeline = [{'$match': {'_id': ObjectId(finding.details.id)}},
{'$unwind': '$events'},
{'$project': {'events': '$events'}},

View File

@ -5,6 +5,7 @@ import pytest
from common.common_consts import zero_trust_consts
from monkey_island.cc.models.zero_trust.event import Event
from monkey_island.cc.models.zero_trust.finding import Finding
from monkey_island.cc.models.zero_trust.monkey_finding import MonkeyFinding
from monkey_island.cc.services.zero_trust.monkey_findings.monkey_zt_finding_service import MonkeyZTFindingService
from monkey_island.cc.test_common.fixtures import FixtureEnum
@ -67,4 +68,4 @@ class TestMonkeyZTFindingService:
# Create new finding
MonkeyZTFindingService.create_or_add_to_existing(test=TESTS[1], status=STATUS[1], events=[EVENTS[1]])
# Assert there was a new finding created, because test and status is different
assert len(Finding.objects()) == 2
assert len(MonkeyFinding.objects()) == 2

View File

@ -1,18 +1,18 @@
from typing import List
from common.common_consts import zero_trust_consts
from monkey_island.cc.models.zero_trust.finding import Finding
from monkey_island.cc.models.zero_trust.scoutsuite_finding import ScoutSuiteFinding
from monkey_island.cc.models.zero_trust.scoutsuite_finding_details import ScoutSuiteFindingDetails
from monkey_island.cc.models.zero_trust.scoutsuite_rule import ScoutSuiteRule
from monkey_island.cc.services.zero_trust.scoutsuite.consts.scoutsuite_findings import ScoutSuiteFinding
from monkey_island.cc.services.zero_trust.scoutsuite.consts.scoutsuite_finding_maps import ScoutSuiteFindingMap
from monkey_island.cc.services.zero_trust.scoutsuite.scoutsuite_rule_service import ScoutSuiteRuleService
class ScoutSuiteZTFindingService:
@staticmethod
def process_rule(finding: ScoutSuiteFinding, rule: ScoutSuiteRule):
existing_findings = Finding.objects(test=finding.test, finding_type=zero_trust_consts.SCOUTSUITE_FINDING)
def process_rule(finding: ScoutSuiteFindingMap, rule: ScoutSuiteRule):
existing_findings = ScoutSuiteFinding.objects(test=finding.test)
assert (len(existing_findings) < 2), "More than one finding exists for {}".format(finding.test)
if len(existing_findings) == 0:
@ -21,12 +21,12 @@ class ScoutSuiteZTFindingService:
ScoutSuiteZTFindingService.add_rule(existing_findings[0], rule)
@staticmethod
def _create_new_finding_from_rule(finding: ScoutSuiteFinding, rule: ScoutSuiteRule):
def _create_new_finding_from_rule(finding: ScoutSuiteFindingMap, rule: ScoutSuiteRule):
details = ScoutSuiteFindingDetails()
details.scoutsuite_rules = [rule]
details.save()
status = ScoutSuiteZTFindingService.get_finding_status_from_rules(details.scoutsuite_rules)
Finding.save_finding(finding.test, status, details)
ScoutSuiteFinding.save_finding(finding.test, status, details)
@staticmethod
def get_finding_status_from_rules(rules: List[ScoutSuiteRule]) -> str:
@ -40,13 +40,13 @@ class ScoutSuiteZTFindingService:
return zero_trust_consts.STATUS_PASSED
@staticmethod
def add_rule(finding: Finding, rule: ScoutSuiteRule):
def add_rule(finding: ScoutSuiteFinding, rule: ScoutSuiteRule):
ScoutSuiteZTFindingService.change_finding_status_by_rule(finding, rule)
finding.save()
finding.details.fetch().add_rule(rule)
@staticmethod
def change_finding_status_by_rule(finding: Finding, rule: ScoutSuiteRule):
def change_finding_status_by_rule(finding: ScoutSuiteFinding, rule: ScoutSuiteRule):
rule_status = ScoutSuiteZTFindingService.get_finding_status_from_rules([rule])
finding_status = finding.status
new_finding_status = ScoutSuiteZTFindingService.get_finding_status_from_rule_status(finding_status, rule_status)

View File

@ -2,6 +2,7 @@ import pytest
from common.common_consts import zero_trust_consts
from monkey_island.cc.models.zero_trust.finding import Finding
from monkey_island.cc.models.zero_trust.scoutsuite_finding import ScoutSuiteFinding
from monkey_island.cc.services.zero_trust.scoutsuite.scoutsuite_zt_finding_service import ScoutSuiteZTFindingService
from monkey_island.cc.services.zero_trust.test_common.scoutsuite_finding_data import RULES, SCOUTSUITE_FINDINGS
from monkey_island.cc.test_common.fixtures import FixtureEnum
@ -15,7 +16,7 @@ class TestScoutSuiteZTFindingService:
ScoutSuiteZTFindingService.process_rule(SCOUTSUITE_FINDINGS[0], RULES[0])
findings = list(Finding.objects())
assert len(findings) == 1
assert findings[0].finding_type == zero_trust_consts.SCOUTSUITE_FINDING
assert type(findings[0]) == ScoutSuiteFinding
# Assert that details were created properly
details = findings[0].details.fetch()
assert len(details.scoutsuite_rules) == 1
@ -23,9 +24,9 @@ class TestScoutSuiteZTFindingService:
# Rule processing should add rule to an already existing finding
ScoutSuiteZTFindingService.process_rule(SCOUTSUITE_FINDINGS[0], RULES[1])
findings = list(Finding.objects())
findings = list(ScoutSuiteFinding.objects())
assert len(findings) == 1
assert findings[0].finding_type == zero_trust_consts.SCOUTSUITE_FINDING
assert type(findings[0]) == ScoutSuiteFinding
# Assert that details were created properly
details = findings[0].details.fetch()
assert len(details.scoutsuite_rules) == 2
@ -35,7 +36,7 @@ class TestScoutSuiteZTFindingService:
ScoutSuiteZTFindingService.process_rule(SCOUTSUITE_FINDINGS[1], RULES[1])
findings = list(Finding.objects())
assert len(findings) == 2
assert findings[1].finding_type == zero_trust_consts.SCOUTSUITE_FINDING
assert type(findings[0]) == ScoutSuiteFinding
# Assert that details were created properly
details = findings[1].details.fetch()
assert len(details.scoutsuite_rules) == 1

View File

@ -1,6 +1,8 @@
from common.common_consts.zero_trust_consts import TEST_SCOUTSUITE_SERVICE_SECURITY, STATUS_FAILED, SCOUTSUITE_FINDING, \
TEST_ENDPOINT_SECURITY_EXISTS, STATUS_PASSED, MONKEY_FINDING
from common.common_consts.zero_trust_consts import TEST_SCOUTSUITE_SERVICE_SECURITY, STATUS_FAILED, \
TEST_ENDPOINT_SECURITY_EXISTS, STATUS_PASSED
from monkey_island.cc.models.zero_trust.finding import Finding
from monkey_island.cc.models.zero_trust.monkey_finding import MonkeyFinding
from monkey_island.cc.models.zero_trust.scoutsuite_finding import ScoutSuiteFinding
from monkey_island.cc.services.zero_trust.test_common.monkey_finding_data import get_monkey_details_dto
from monkey_island.cc.services.zero_trust.test_common.scoutsuite_finding_data import get_scoutsuite_details_dto
@ -8,16 +10,14 @@ from monkey_island.cc.services.zero_trust.test_common.scoutsuite_finding_data im
def get_scoutsuite_finding_dto() -> Finding:
scoutsuite_details = get_scoutsuite_details_dto()
scoutsuite_details.save()
return Finding(test=TEST_SCOUTSUITE_SERVICE_SECURITY,
return ScoutSuiteFinding(test=TEST_SCOUTSUITE_SERVICE_SECURITY,
status=STATUS_FAILED,
finding_type=SCOUTSUITE_FINDING,
details=scoutsuite_details)
def get_monkey_finding_dto() -> Finding:
monkey_details = get_monkey_details_dto()
monkey_details.save()
return Finding(test=TEST_ENDPOINT_SECURITY_EXISTS,
return MonkeyFinding(test=TEST_ENDPOINT_SECURITY_EXISTS,
status=STATUS_PASSED,
finding_type=MONKEY_FINDING,
details=monkey_details)

View File

@ -6,6 +6,8 @@ from bson import SON
from common.common_consts import zero_trust_consts
from common.utils.exceptions import UnknownFindingError
from monkey_island.cc.models.zero_trust.finding import Finding
from monkey_island.cc.models.zero_trust.monkey_finding import MonkeyFinding
from monkey_island.cc.models.zero_trust.scoutsuite_finding import ScoutSuiteFinding
from monkey_island.cc.services.zero_trust.monkey_findings.monkey_zt_details_service import MonkeyZTDetailsService
@ -16,15 +18,18 @@ class EnrichedFinding:
test_key: str
pillars: List[str]
status: str
finding_type: str
details: Union[dict, None]
class FindingService:
@staticmethod
def get_all_findings() -> List[EnrichedFinding]:
findings = list(Finding.objects)
def get_all_findings_from_db() -> List[Finding]:
return list(Finding.objects)
@staticmethod
def get_all_findings_for_ui() -> List[EnrichedFinding]:
findings = FindingService.get_all_findings_from_db()
for i in range(len(findings)):
details = FindingService._get_finding_details(findings[i])
findings[i] = findings[i].to_mongo()
@ -41,16 +46,15 @@ class FindingService:
test_key=finding['test'],
pillars=test_info[zero_trust_consts.PILLARS_KEY],
status=finding['status'],
finding_type=finding['finding_type'],
details=None
)
return enriched_finding
@staticmethod
def _get_finding_details(finding: Finding) -> Union[dict, SON]:
if finding.finding_type == zero_trust_consts.MONKEY_FINDING:
if type(finding) == MonkeyFinding:
return MonkeyZTDetailsService.fetch_details_for_display(finding.details.id)
elif finding.finding_type == zero_trust_consts.SCOUTSUITE_FINDING:
elif type(finding) == ScoutSuiteFinding:
return finding.details.fetch().to_mongo()
else:
raise UnknownFindingError(f"Unknown finding type {finding.finding_type}")
raise UnknownFindingError(f"Unknown finding type {str(type(finding))}")

View File

@ -1,5 +1,5 @@
import common.common_consts.zero_trust_consts as zero_trust_consts
from monkey_island.cc.models.zero_trust.finding import Finding
from monkey_island.cc.services.zero_trust.zero_trust_report.finding_service import FindingService
class PillarService:
@ -13,7 +13,7 @@ class PillarService:
@staticmethod
def _get_pillars_grades():
pillars_grades = []
all_findings = Finding.objects()
all_findings = FindingService.get_all_findings_from_db()
for pillar in zero_trust_consts.PILLARS:
pillars_grades.append(PillarService.__get_pillar_grade(pillar, all_findings))
return pillars_grades
@ -67,7 +67,7 @@ class PillarService:
@staticmethod
def __get_status_of_single_pillar(pillar):
all_findings = Finding.objects()
all_findings = FindingService.get_all_findings_from_db()
grade = PillarService.__get_pillar_grade(pillar, all_findings)
for status in zero_trust_consts.ORDERED_TEST_STATUSES:
if grade[status] > 0:

View File

@ -3,9 +3,10 @@ from unittest.mock import MagicMock
import pytest
from common.common_consts.zero_trust_consts import TESTS_MAP, TEST_SCOUTSUITE_SERVICE_SECURITY, STATUS_FAILED, \
SCOUTSUITE_FINDING, DEVICES, NETWORKS, MONKEY_FINDING, STATUS_PASSED, TEST_ENDPOINT_SECURITY_EXISTS
DEVICES, NETWORKS, STATUS_PASSED, TEST_ENDPOINT_SECURITY_EXISTS
from monkey_island.cc.services.zero_trust.monkey_findings.monkey_zt_details_service import MonkeyZTDetailsService
from monkey_island.cc.services.zero_trust.test_common.finding_data import get_scoutsuite_finding_dto, get_monkey_finding_dto
from monkey_island.cc.services.zero_trust.test_common.finding_data import get_scoutsuite_finding_dto, \
get_monkey_finding_dto
from monkey_island.cc.services.zero_trust.zero_trust_report.finding_service import FindingService, EnrichedFinding
from monkey_island.cc.test_common.fixtures.fixture_enum import FixtureEnum
@ -18,11 +19,10 @@ def test_get_all_findings():
# This method fails due to mongomock not being able to simulate $unset, so don't test details
MonkeyZTDetailsService.fetch_details_for_display = MagicMock(return_value=None)
findings = FindingService.get_all_findings()
findings = FindingService.get_all_findings_for_ui()
description = TESTS_MAP[TEST_SCOUTSUITE_SERVICE_SECURITY]['finding_explanation'][STATUS_FAILED]
expected_finding0 = EnrichedFinding(finding_id=findings[0].finding_id,
finding_type=SCOUTSUITE_FINDING,
pillars=[DEVICES, NETWORKS],
status=STATUS_FAILED,
test=description,
@ -31,7 +31,6 @@ def test_get_all_findings():
description = TESTS_MAP[TEST_ENDPOINT_SECURITY_EXISTS]['finding_explanation'][STATUS_PASSED]
expected_finding1 = EnrichedFinding(finding_id=findings[1].finding_id,
finding_type=MONKEY_FINDING,
pillars=[DEVICES],
status=STATUS_PASSED,
test=description,

View File

@ -36,10 +36,10 @@ export class FindingsTable extends Component {
];
getFindingDetails(finding) {
if (finding.finding_type === 'scoutsuite_finding') {
if ('scoutsuite_rules' in finding.details) {
return <ScoutSuiteRuleButton scoutsuite_rules={finding.details.scoutsuite_rules}
scoutsuite_data={this.props.scoutsuite_data}/>;
} else if (finding.finding_type === 'monkey_finding') {
} else {
return <EventsButton finding_id={finding.finding_id}
latest_events={finding.details.latest_events}
oldest_events={finding.details.oldest_events}