From e313b5972ece394c6b74fef3aacdbbbee0ef350a Mon Sep 17 00:00:00 2001 From: alexander Date: Wed, 19 Feb 2025 01:04:34 +0300 Subject: [PATCH] Support raw cvss data --- CveXplore/core/database_indexer/db_indexer.py | 1 + .../database_maintenance/sources_process.py | 117 ++++++++++++++++++ CveXplore/database/helpers/generic_db.py | 1 + CveXplore/database/helpers/specific_db.pyi | 1 + CveXplore/database_models/models.py | 1 + 5 files changed, 121 insertions(+) diff --git a/CveXplore/core/database_indexer/db_indexer.py b/CveXplore/core/database_indexer/db_indexer.py index 54a86afae..7387cb98b 100644 --- a/CveXplore/core/database_indexer/db_indexer.py +++ b/CveXplore/core/database_indexer/db_indexer.py @@ -53,6 +53,7 @@ def __init__(self, datasource: DatabaseConnectionBase): MongoAddIndex(index=[("cvss", ASCENDING)], name="cvss"), MongoAddIndex(index=[("cvss3", ASCENDING)], name="cvss3"), MongoAddIndex(index=[("cvss4", ASCENDING)], name="cvss4"), + MongoAddIndex(index=[("cvss_data", ASCENDING)], name="cvss_data"), MongoAddIndex(index=[("summary", TEXT)], name="summary"), MongoAddIndex(index=[("vendors", ASCENDING)], name="vendors"), MongoAddIndex(index=[("products", ASCENDING)], name="products"), diff --git a/CveXplore/core/database_maintenance/sources_process.py b/CveXplore/core/database_maintenance/sources_process.py index e209e045f..8481ceddb 100644 --- a/CveXplore/core/database_maintenance/sources_process.py +++ b/CveXplore/core/database_maintenance/sources_process.py @@ -593,6 +593,123 @@ def process_the_item(self, item: dict = None): else: cve["cvss"] = None + cve["cvss_data"] = {"cvss2": {}, "cvss3": {}, "cvss4": {}} + + for version in [ + "cvssMetricV40", + "cvssMetricV31", + "cvssMetricV30", + "cvssMetricV2", + ]: + if version in item["cve"]["metrics"]: + for metric in item["cve"]["metrics"][version]: + cvss_key = ( + "cvss4" + if version == "cvssMetricV40" + else ( + "cvss3" + if version in ["cvssMetricV31", "cvssMetricV30"] + else "cvss2" + ) + ) + source = metric["source"] + + entry = { + "type": metric["type"], + "vectorString": metric["cvssData"]["vectorString"], + "baseScore": metric["cvssData"]["baseScore"], + } + + if cvss_key == "cvss4": + entry.update( + { + "vulnerable_system_confidentiality": metric[ + "cvssData" + ].get("vulnerableSystemConfidentiality"), + "vulnerable_system_integrity": metric["cvssData"].get( + "vulnerableSystemIntegrity" + ), + "vulnerable_system_availability": metric[ + "cvssData" + ].get("vulnerableSystemAvailability"), + "subsequent_system_confidentiality": metric[ + "cvssData" + ].get("subsequentSystemConfidentiality"), + "subsequent_system_integrity": metric["cvssData"].get( + "subsequentSystemIntegrity" + ), + "subsequent_system_availability": metric[ + "cvssData" + ].get("subsequentSystemAvailability"), + "attackVector": metric["cvssData"].get("attackVector"), + "attackComplexity": metric["cvssData"].get( + "attackComplexity" + ), + "attackRequirements": metric["cvssData"].get( + "attackRequirements" + ), + "privilegesRequired": metric["cvssData"].get( + "privilegesRequired" + ), + "userInteraction": metric["cvssData"].get( + "userInteraction" + ), + "exploitMaturity": metric["cvssData"].get( + "exploitMaturity" + ), + } + ) + elif cvss_key == "cvss3": + entry.update( + { + "confidentialityImpact": metric["cvssData"].get( + "confidentialityImpact" + ), + "integrityImpact": metric["cvssData"].get( + "integrityImpact" + ), + "availabilityImpact": metric["cvssData"].get( + "availabilityImpact" + ), + "attackVector": metric["cvssData"].get("attackVector"), + "attackComplexity": metric["cvssData"].get( + "attackComplexity" + ), + "privilegesRequired": metric["cvssData"].get( + "privilegesRequired" + ), + "userInteraction": metric["cvssData"].get( + "userInteraction" + ), + "scope": metric["cvssData"].get("scope"), + } + ) + elif cvss_key == "cvss2": + entry.update( + { + "authentication": metric["cvssData"].get( + "authentication" + ), + "accessComplexity": metric["cvssData"].get( + "accessComplexity" + ), + "accessVector": metric["cvssData"].get("accessVector"), + "confidentialityImpact": metric["cvssData"].get( + "confidentialityImpact" + ), + "integrityImpact": metric["cvssData"].get( + "integrityImpact" + ), + "availabilityImpact": metric["cvssData"].get( + "availabilityImpact" + ), + } + ) + + if source not in cve["cvss_data"][cvss_key]: + cve["cvss_data"][cvss_key][source] = [] + cve["cvss_data"][cvss_key][source].append(entry) + if "references" in item["cve"]: cve["references"] = [] for ref in item["cve"]["references"]: diff --git a/CveXplore/database/helpers/generic_db.py b/CveXplore/database/helpers/generic_db.py index 00b2df8de..060de3f40 100644 --- a/CveXplore/database/helpers/generic_db.py +++ b/CveXplore/database/helpers/generic_db.py @@ -39,6 +39,7 @@ def __init__(self, collection: str): "cvss", "cvss3", "cvss4", + "cvss_data", "summary", "vendors", "products", diff --git a/CveXplore/database/helpers/specific_db.pyi b/CveXplore/database/helpers/specific_db.pyi index 137a08879..75f485493 100644 --- a/CveXplore/database/helpers/specific_db.pyi +++ b/CveXplore/database/helpers/specific_db.pyi @@ -5,6 +5,7 @@ class CvesDatabaseFunctions: cvss: GenericDatabaseFieldsFunctions cvss3: GenericDatabaseFieldsFunctions cvss4: GenericDatabaseFieldsFunctions + cvss_data: GenericDatabaseFieldsFunctions summary: GenericDatabaseFieldsFunctions vendors: GenericDatabaseFieldsFunctions products: GenericDatabaseFieldsFunctions diff --git a/CveXplore/database_models/models.py b/CveXplore/database_models/models.py index fc76a34d5..e223d758e 100644 --- a/CveXplore/database_models/models.py +++ b/CveXplore/database_models/models.py @@ -126,6 +126,7 @@ class Cves(CveXploreBase): cvssTime = Column(DateTime, doc="Time of the CVSS of the CVE") cvssVector = Column(String(100), doc="Vector of the CVSS of the CVE") configurations = Column(JSON, doc="Vulnerable configurations of the CVE") + cvss_data = Column(JSON, doc="Raw cvss data") cwe = Column(JSON, default=[], doc="Related CWEs to the CVE") epss = Column(Float, index=True, doc="Epss of the CVE") epssMetric = Column(JSON, doc="Epss metric of the CVE")