diff --git a/dojo/jira/views.py b/dojo/jira/views.py index b325fab696d..e63f20d2b27 100644 --- a/dojo/jira/views.py +++ b/dojo/jira/views.py @@ -11,7 +11,7 @@ from django.core.exceptions import PermissionDenied from django.db import DEFAULT_DB_ALIAS from django.db.models import Q -from django.http import Http404, HttpResponse, HttpResponseRedirect +from django.http import HttpResponse, HttpResponseRedirect from django.shortcuts import get_object_or_404, render from django.urls import reverse from django.utils import timezone @@ -106,10 +106,9 @@ def webhook(request, secret=None): if parsed.get("webhookEvent") == "jira:issue_updated": # xml examples at the end of file jid = parsed["issue"]["id"] - # This may raise a 404, but it will be handled in the exception response try: jissue = JIRA_Issue.objects.get(jira_id=jid) - except JIRA_Instance.DoesNotExist: + except JIRA_Issue.DoesNotExist: return webhook_responser_handler("info", f"JIRA issue {jid} is not linked to a DefectDojo Finding") # Add jira_key to context now that we have it pghistory.context(jira_key=jissue.jira_key) @@ -182,22 +181,9 @@ def webhook(request, secret=None): if (error_response := check_for_and_create_comment(parsed)) is not None: return error_response - except Exception as e: - # Check if the issue is originally a 404 - if isinstance(e, Http404): - return webhook_responser_handler("debug", str(e)) - # Try to get a little more information on the exact exception - try: - message = ( - f"Original Exception: {e}\n" - f"jira webhook body parsed:\n{json.dumps(parsed, indent=4)}" - ) - except Exception: - message = ( - f"Original Exception: {e}\n" - f"jira webhook body :\n{request.body.decode('utf-8')}" - ) - return webhook_responser_handler("debug", message) + except Exception: + logger.exception("Failed to process incoming JIRA webhook") + return webhook_responser_handler("debug", "Could not process the incoming JIRA webhook") return webhook_responser_handler("No logging here", "Success!") @@ -262,7 +248,7 @@ def check_for_and_create_comment(parsed_json): jid = comment.get("self", "").split("/")[-3] try: jissue = JIRA_Issue.objects.get(jira_id=jid) - except JIRA_Instance.DoesNotExist: + except JIRA_Issue.DoesNotExist: return webhook_responser_handler("info", f"JIRA issue {jid} is not linked to a DefectDojo Finding") logger.debug(f"Received issue comment for {jissue.jira_key}") logger.debug("jissue: %s", vars(jissue)) diff --git a/unittests/test_jira_webhook.py b/unittests/test_jira_webhook.py index a63e35f07aa..8038e8b5bf7 100644 --- a/unittests/test_jira_webhook.py +++ b/unittests/test_jira_webhook.py @@ -640,6 +640,36 @@ def test_webhook_update_no_jira_issue_at_all(self): self.assertEqual(200, response.status_code, response.content[:1000]) + def test_webhook_unlinked_issue_returns_the_not_linked_message(self): + self.system_settings(enable_jira=True, enable_jira_web_hook=True, disable_jira_webhook_secret=False, jira_webhook_secret=self.correct_secret) + + # no JIRA_Issue row carries this id at all + body = json.loads(self.jira_issue_update_template_string) + body["issue"]["id"] = 999999 + + response = self.client.post(reverse("jira_web_hook_secret", args=(self.correct_secret, )), + body, + content_type="application/json") + + self.assertEqual(200, response.status_code, response.content[:1000]) + self.assertEqual(b"JIRA issue 999999 is not linked to a DefectDojo Finding", response.content) + + def test_webhook_failure_does_not_echo_the_request_body(self): + self.system_settings(enable_jira=True, enable_jira_web_hook=True, disable_jira_webhook_secret=False, jira_webhook_secret=self.correct_secret) + + # "updated" is required by the handler, so dropping it forces the fall-through handler + body = json.loads(self.jira_issue_update_template_string) + body["issue"]["fields"].pop("updated") + body["canary"] = "DO-NOT-ECHO-THIS" + + response = self.client.post(reverse("jira_web_hook_secret", args=(self.correct_secret, )), + body, + content_type="application/json") + + self.assertEqual(200, response.status_code, response.content[:1000]) + self.assertNotIn(b"DO-NOT-ECHO-THIS", response.content) + self.assertNotIn(b"Original Exception", response.content) + def test_webhook_issue_updated_extracts_comment(self): self.system_settings(enable_jira=True, enable_jira_web_hook=True, disable_jira_webhook_secret=False, jira_webhook_secret=self.correct_secret)