From bead48ce58256d01b43c20f48cdef992f4de0ba7 Mon Sep 17 00:00:00 2001 From: Dmitrii Mariushkin Date: Fri, 22 Nov 2024 08:29:31 +0300 Subject: [PATCH] Mobsfscan report files parsing fix (#11278) * Fix multi files parsing * Fix multi files parsing * Fix multi files parsing --------- Co-authored-by: Dmitry Maryushkin --- dojo/settings/.settings.dist.py.sha256sum | 2 +- dojo/settings/settings.dist.py | 2 +- dojo/tools/mobsfscan/parser.py | 52 +++++++++++++------- unittests/scans/mobsfscan/many_findings.json | 12 +++++ unittests/tools/test_mobsfscan_parser.py | 29 +++++++---- 5 files changed, 67 insertions(+), 30 deletions(-) diff --git a/dojo/settings/.settings.dist.py.sha256sum b/dojo/settings/.settings.dist.py.sha256sum index 6e1a934f57d..3f596c0890b 100644 --- a/dojo/settings/.settings.dist.py.sha256sum +++ b/dojo/settings/.settings.dist.py.sha256sum @@ -1 +1 @@ -f85484f23e59aabe591b30db10e0de05aaeeb9d8979d236d565dc8279e03e116 +ea62fff7e384d73568e1293c739ce1a116e090cd4550a403ac272821a7785e0b diff --git a/dojo/settings/settings.dist.py b/dojo/settings/settings.dist.py index c5453c018de..57cfafee1ef 100644 --- a/dojo/settings/settings.dist.py +++ b/dojo/settings/settings.dist.py @@ -1213,7 +1213,7 @@ def saml2_attrib_map_format(dict): "Dependency Check Scan": ["title", "cwe", "file_path"], "Dockle Scan": ["title", "description", "vuln_id_from_tool"], "Dependency Track Finding Packaging Format (FPF) Export": ["component_name", "component_version", "vulnerability_ids"], - "Mobsfscan Scan": ["title", "severity", "cwe"], + "Mobsfscan Scan": ["title", "severity", "cwe", "file_path", "description"], "Tenable Scan": ["title", "severity", "vulnerability_ids", "cwe", "description"], "Nexpose Scan": ["title", "severity", "vulnerability_ids", "cwe"], # possible improvement: in the scanner put the library name into file_path, then dedup on cwe + file_path + severity diff --git a/dojo/tools/mobsfscan/parser.py b/dojo/tools/mobsfscan/parser.py index 83c69a58947..0473b7c6491 100644 --- a/dojo/tools/mobsfscan/parser.py +++ b/dojo/tools/mobsfscan/parser.py @@ -51,29 +51,43 @@ def get_findings(self, filename, test): else: severity = "Info" - finding = Finding( - title=f"{key}", - test=test, - severity=severity, - nb_occurences=1, - cwe=cwe, - description=description, - references=references, - ) + files = [] + if item.get("files"): for file in item.get("files"): - file_path = file.get("file_path") - line = file.get("match_lines")[0] + file_path = file.get("file_path", "") + line = file.get("match_lines", [0])[0] + snippet = file.get("match_string", "") + + files.append((file_path, line, snippet)) + else: + files.append(("", 0, "")) + + for file_path, line, snippet in files: + + finding = Finding( + title=f"{key}", + test=test, + severity=severity, + nb_occurences=1, + cwe=cwe, + description=description, + references=references, + ) + + if file_path: finding.file_path = file_path finding.line = line + finding.description = f"{description}\n**Snippet:** `{snippet}`" - dupe_key = hashlib.sha256( - (key + str(cwe) + masvs + owasp_mobile).encode("utf-8"), - ).hexdigest() + dupe_key = hashlib.sha256( + (key + str(cwe) + masvs + owasp_mobile + file_path).encode("utf-8"), + ).hexdigest() + + if dupe_key in dupes: + finding = dupes[dupe_key] + finding.nb_occurences += 1 + else: + dupes[dupe_key] = finding - if dupe_key in dupes: - finding = dupes[dupe_key] - finding.nb_occurences += 1 - else: - dupes[dupe_key] = finding return list(dupes.values()) diff --git a/unittests/scans/mobsfscan/many_findings.json b/unittests/scans/mobsfscan/many_findings.json index 5e38baf88de..30701b88501 100644 --- a/unittests/scans/mobsfscan/many_findings.json +++ b/unittests/scans/mobsfscan/many_findings.json @@ -25,6 +25,18 @@ 271 ], "match_string": "key = \"hmi_busroutes_health\"" + }, + { + "file_path": "app/src/main/java/com/routes/domain/analytics/event/Signatures2.kt", + "match_lines": [ + 20, + 20 + ], + "match_position": [ + 243, + 271 + ], + "match_string": "key2 = \"hmi_busroutes_health2\"" } ], "metadata": { diff --git a/unittests/tools/test_mobsfscan_parser.py b/unittests/tools/test_mobsfscan_parser.py index 9a41cb02035..a4051bd3a5a 100644 --- a/unittests/tools/test_mobsfscan_parser.py +++ b/unittests/tools/test_mobsfscan_parser.py @@ -15,7 +15,7 @@ def test_parse_many_findings(self): with open("unittests/scans/mobsfscan/many_findings.json", encoding="utf-8") as testfile: parser = MobsfscanParser() findings = parser.get_findings(testfile, Test()) - self.assertEqual(7, len(findings)) + self.assertEqual(8, len(findings)) with self.subTest(i=0): finding = findings[0] @@ -39,6 +39,17 @@ def test_parse_many_findings(self): with self.subTest(i=2): finding = findings[2] + self.assertEqual("android_kotlin_hardcoded", finding.title) + self.assertEqual("Medium", finding.severity) + self.assertEqual(1, finding.nb_occurences) + self.assertIsNotNone(finding.description) + self.assertEqual(798, finding.cwe) + self.assertIsNotNone(finding.references) + self.assertEqual("app/src/main/java/com/routes/domain/analytics/event/Signatures2.kt", finding.file_path) + self.assertEqual(20, finding.line) + + with self.subTest(i=3): + finding = findings[3] self.assertEqual("android_prevent_screenshot", finding.title) self.assertEqual("Low", finding.severity) self.assertEqual(1, finding.nb_occurences) @@ -46,8 +57,8 @@ def test_parse_many_findings(self): self.assertEqual(200, finding.cwe) self.assertIsNotNone(finding.references) - with self.subTest(i=3): - finding = findings[3] + with self.subTest(i=4): + finding = findings[4] self.assertEqual("android_root_detection", finding.title) self.assertEqual("Low", finding.severity) self.assertEqual(1, finding.nb_occurences) @@ -55,8 +66,8 @@ def test_parse_many_findings(self): self.assertEqual(919, finding.cwe) self.assertIsNotNone(finding.references) - with self.subTest(i=4): - finding = findings[4] + with self.subTest(i=5): + finding = findings[5] self.assertEqual("android_safetynet", finding.title) self.assertEqual("Low", finding.severity) self.assertEqual(1, finding.nb_occurences) @@ -64,8 +75,8 @@ def test_parse_many_findings(self): self.assertEqual(353, finding.cwe) self.assertIsNotNone(finding.references) - with self.subTest(i=5): - finding = findings[5] + with self.subTest(i=6): + finding = findings[6] self.assertEqual("android_ssl_pinning", finding.title) self.assertEqual("Low", finding.severity) self.assertEqual(1, finding.nb_occurences) @@ -73,8 +84,8 @@ def test_parse_many_findings(self): self.assertEqual(295, finding.cwe) self.assertIsNotNone(finding.references) - with self.subTest(i=6): - finding = findings[6] + with self.subTest(i=7): + finding = findings[7] self.assertEqual("android_tapjacking", finding.title) self.assertEqual("Low", finding.severity) self.assertEqual(1, finding.nb_occurences)