diff --git a/components/package.json b/components/package.json index 634edd2d8b..c569e2e364 100644 --- a/components/package.json +++ b/components/package.json @@ -1,6 +1,6 @@ { "name": "defectdojo", - "version": "2.27.3", + "version": "2.27.4", "license" : "BSD-3-Clause", "private": true, "dependencies": { diff --git a/dojo/__init__.py b/dojo/__init__.py index ec797f99a3..fa0ddf6c0a 100644 --- a/dojo/__init__.py +++ b/dojo/__init__.py @@ -4,6 +4,6 @@ # Django starts so that shared_task will use this app. from .celery import app as celery_app # noqa -__version__ = '2.27.3' +__version__ = '2.27.4' __url__ = 'https://github.com/DefectDojo/django-DefectDojo' __docs__ = 'https://documentation.defectdojo.com' diff --git a/dojo/models.py b/dojo/models.py index ee75eca665..b5d86e5671 100755 --- a/dojo/models.py +++ b/dojo/models.py @@ -4268,6 +4268,7 @@ def enable_disable_auditlog(enable=True): auditlog.register(Endpoint) auditlog.register(Engagement) auditlog.register(Finding) + auditlog.register(Product_Type) auditlog.register(Product) auditlog.register(Test) auditlog.register(Risk_Acceptance) @@ -4279,6 +4280,7 @@ def enable_disable_auditlog(enable=True): auditlog.unregister(Endpoint) auditlog.unregister(Engagement) auditlog.unregister(Finding) + auditlog.unregister(Product_Type) auditlog.unregister(Product) auditlog.unregister(Test) auditlog.unregister(Risk_Acceptance) diff --git a/dojo/settings/settings.dist.py b/dojo/settings/settings.dist.py index 82d4303a94..059b366085 100644 --- a/dojo/settings/settings.dist.py +++ b/dojo/settings/settings.dist.py @@ -1257,6 +1257,8 @@ def saml2_attrib_map_format(dict): 'Popeye Scan': ['title', 'description'], 'Wazuh Scan': ['title'], 'Nuclei Scan': ['title', 'cwe', 'severity'], + 'KubeHunter Scan': ['title', 'description'], + 'kube-bench Scan': ['title', 'vuln_id_from_tool', 'description'], } # Override the hardcoded settings here via the env var @@ -1450,6 +1452,8 @@ def saml2_attrib_map_format(dict): 'Wpscan': DEDUPE_ALGO_HASH_CODE, 'Popeye Scan': DEDUPE_ALGO_HASH_CODE, 'Nuclei Scan': DEDUPE_ALGO_HASH_CODE, + 'KubeHunter Scan': DEDUPE_ALGO_HASH_CODE, + 'kube-bench Scan': DEDUPE_ALGO_HASH_CODE, } # Override the hardcoded settings here via the env var diff --git a/dojo/templates/dojo/filter_snippet.html b/dojo/templates/dojo/filter_snippet.html index 58c08ee79b..577e43d4d4 100644 --- a/dojo/templates/dojo/filter_snippet.html +++ b/dojo/templates/dojo/filter_snippet.html @@ -54,3 +54,32 @@ + \ No newline at end of file diff --git a/dojo/tools/whispers/parser.py b/dojo/tools/whispers/parser.py index 7ca075377a..42b79ee7c7 100644 --- a/dojo/tools/whispers/parser.py +++ b/dojo/tools/whispers/parser.py @@ -9,11 +9,18 @@ class WhispersParser(object): """ SEVERITY_MAP = { + # Whispers 2.1 "BLOCKER": "Critical", "CRITICAL": "High", "MAJOR": "Medium", "MINOR": "Low", "INFO": "Info", + # Whispers 2.2 + "Critical": "Critical", + "High": "High", + "Medium": "Medium", + "Low": "Low", + "Info": "Info", } @staticmethod diff --git a/dojo/user/validators.py b/dojo/user/validators.py index 407a9324e0..36869d2df1 100644 --- a/dojo/user/validators.py +++ b/dojo/user/validators.py @@ -36,7 +36,7 @@ def get_help_text(self): class NumberValidator(object): def validate(self, password, user=None): - if not re.findall('\d', password) and get_system_setting('number_character_required'): # noqa W605 + if not re.findall(r'\d', password) and get_system_setting('number_character_required'): raise ValidationError( self.get_help_text(), code='password_no_number') @@ -75,7 +75,7 @@ def get_help_text(self): class SymbolValidator(object): def validate(self, password, user=None): - contains_special_character = re.findall('[()[\]{}|\\`~!@#$%^&*_\-+=;:\'\",<>./?]', password) # noqa W605 + contains_special_character = re.findall(r'[(){}\[\]|~!@#$%^&*_\-+=;:\'",\`<>\./?]', password) if not contains_special_character and get_system_setting('special_character_required'): raise ValidationError( self.get_help_text(), @@ -85,7 +85,7 @@ def validate(self, password, user=None): def get_help_text(self): return gettext('The password must contain at least 1 special character, ' + - '()[]{}|\`~!@#$%^&*_-+=;:\'\",<>./?.') # noqa W605 + '''()[]{}|`~!@#$%^&*_-+=;:'",<>./?.''') class DojoCommonPasswordValidator(CommonPasswordValidator): diff --git a/helm/defectdojo/Chart.yaml b/helm/defectdojo/Chart.yaml index 42f802dba8..9abe3401d7 100644 --- a/helm/defectdojo/Chart.yaml +++ b/helm/defectdojo/Chart.yaml @@ -1,8 +1,8 @@ apiVersion: v2 -appVersion: "2.27.3" +appVersion: "2.27.4" description: A Helm chart for Kubernetes to install DefectDojo name: defectdojo -version: 1.6.92 +version: 1.6.93 icon: https://www.defectdojo.org/img/favicon.ico maintainers: - name: madchap diff --git a/unittests/scans/whispers/whispers_one_vul_v2.2.json b/unittests/scans/whispers/whispers_one_vul_v2.2.json new file mode 100644 index 0000000000..86563c4659 --- /dev/null +++ b/unittests/scans/whispers/whispers_one_vul_v2.2.json @@ -0,0 +1 @@ +[{"key": "pip password", "value": "hardcoded", "file": "src/pip.conf", "line": 2, "rule_id": "pip", "message": "pip.conf Password", "severity": "High"}] diff --git a/unittests/test_user_validators.py b/unittests/test_user_validators.py index 59e1e4061e..06bdf953b5 100644 --- a/unittests/test_user_validators.py +++ b/unittests/test_user_validators.py @@ -101,7 +101,7 @@ def test_validator_special_character_required(self): self.assertFalse(form.is_valid()) self.assertEqual( form.errors['new_password'][0], - 'The password must contain at least 1 special character, ()[]{}|\\`~!@#$%^&*_-+=;:\'",<>./?.') + '''The password must contain at least 1 special character, ()[]{}|`~!@#$%^&*_-+=;:'",<>./?.''') def test_validator_lowercase_character_required(self): with self.subTest(policy='lowercase_character_required=False'): diff --git a/unittests/tools/test_whispers_parser.py b/unittests/tools/test_whispers_parser.py index d0df6b7294..9a2da18dde 100644 --- a/unittests/tools/test_whispers_parser.py +++ b/unittests/tools/test_whispers_parser.py @@ -5,6 +5,20 @@ class TestWhispersParser(TestCase): + def test_whispers_parser_severity_map(self): + fixtures = [ + "unittests/scans/whispers/whispers_one_vul.json", # v2.1 format + "unittests/scans/whispers/whispers_one_vul_v2.2.json", # v2.2 format + ] + expected_severity = "High" + + for fixture in fixtures: + testfile = open(fixture) + parser = WhispersParser() + findings = parser.get_findings(testfile, Test()) + testfile.close() + self.assertEqual(expected_severity, findings[0].severity) + def test_whispers_parser_with_no_vuln_has_no_findings(self): testfile = open("unittests/scans/whispers/whispers_zero_vul.json") parser = WhispersParser()