123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184 |
- from functools import cached_property
- from urllib.parse import parse_qs
- import pytest
- import responses
- from sentry.integrations.slack.message_builder import LEVEL_TO_COLOR
- from sentry.models import Rule
- from sentry.plugins.base import Notification
- from sentry.shared_integrations.exceptions import ApiError
- from sentry.testutils import PluginTestCase
- from sentry.utils import json
- from sentry_plugins.slack.plugin import SlackPlugin
- class SlackPluginTest(PluginTestCase):
- @cached_property
- def plugin(self):
- return SlackPlugin()
- def test_conf_key(self):
- assert self.plugin.conf_key == "slack"
- def test_entry_point(self):
- self.assertPluginInstalled("slack", self.plugin)
- @responses.activate
- def test_simple_notification(self):
- responses.add("POST", "http://example.com/slack")
- self.plugin.set_option("webhook", "http://example.com/slack", self.project)
- event = self.store_event(
- data={"message": "Hello world", "level": "warning", "culprit": "foo.bar"},
- project_id=self.project.id,
- )
- group = event.group
- assert group is not None
- rule = Rule.objects.create(project=self.project, label="my rule")
- notification = Notification(event=event, rule=rule)
- with self.options({"system.url-prefix": "http://example.com"}):
- self.plugin.notify(notification)
- request = responses.calls[0].request
- payload = json.loads(parse_qs(request.body)["payload"][0])
- assert payload == {
- "username": "Sentry",
- "attachments": [
- {
- "color": LEVEL_TO_COLOR["warning"],
- "fields": [
- {"short": False, "value": "foo.bar", "title": "Culprit"},
- {"short": True, "value": "bar", "title": "Project"},
- ],
- "fallback": "[bar] Hello world",
- "title": "Hello world",
- "title_link": "http://example.com/organizations/baz/issues/%s/?referrer=slack"
- % group.id,
- }
- ],
- }
- @responses.activate
- def test_notification_without_culprit(self):
- responses.add("POST", "http://example.com/slack")
- self.plugin.set_option("webhook", "http://example.com/slack", self.project)
- self.plugin.set_option("exclude_culprit", True, self.project)
- event = self.store_event(
- data={"message": "Hello world", "level": "warning"}, project_id=self.project.id
- )
- group = event.group
- assert group is not None
- rule = Rule.objects.create(project=self.project, label="my rule")
- notification = Notification(event=event, rule=rule)
- with self.options({"system.url-prefix": "http://example.com"}):
- self.plugin.notify(notification)
- request = responses.calls[0].request
- payload = json.loads(parse_qs(request.body)["payload"][0])
- assert payload == {
- "username": "Sentry",
- "attachments": [
- {
- "color": LEVEL_TO_COLOR["warning"],
- "fields": [{"short": True, "value": "bar", "title": "Project"}],
- "fallback": "[bar] Hello world",
- "title": "Hello world",
- "title_link": "http://example.com/organizations/baz/issues/%s/?referrer=slack"
- % group.id,
- }
- ],
- }
- @responses.activate
- def test_notification_without_project(self):
- responses.add("POST", "http://example.com/slack")
- self.plugin.set_option("webhook", "http://example.com/slack", self.project)
- self.plugin.set_option("exclude_project", True, self.project)
- event = self.store_event(
- data={"message": "Hello world", "level": "warning", "culprit": "foo.bar"},
- project_id=self.project.id,
- )
- group = event.group
- assert group is not None
- rule = Rule.objects.create(project=self.project, label="my rule")
- notification = Notification(event=event, rule=rule)
- with self.options({"system.url-prefix": "http://example.com"}):
- self.plugin.notify(notification)
- request = responses.calls[0].request
- payload = json.loads(parse_qs(request.body)["payload"][0])
- assert payload == {
- "username": "Sentry",
- "attachments": [
- {
- "color": LEVEL_TO_COLOR["warning"],
- "fields": [{"short": False, "value": "foo.bar", "title": "Culprit"}],
- "fallback": "[bar] Hello world",
- "title": "Hello world",
- "title_link": "http://example.com/organizations/baz/issues/%s/?referrer=slack"
- % group.id,
- }
- ],
- }
- @responses.activate
- def test_no_error_on_404(self):
- responses.add("POST", "http://example.com/slack", status=404)
- self.plugin.set_option("webhook", "http://example.com/slack", self.project)
- event = self.store_event(
- data={"message": "Hello world", "level": "warning", "culprit": "foo.bar"},
- project_id=self.project.id,
- )
- rule = Rule.objects.create(project=self.project, label="my rule")
- notification = Notification(event=event, rule=rule)
- # No exception since 404s are supposed to be ignored
- with self.options({"system.url-prefix": "http://example.com"}):
- self.plugin.notify(notification)
- responses.replace("POST", "http://example.com/slack", status=400)
- # Other exceptions should not be ignored
- with self.options({"system.url-prefix": "http://example.com"}):
- with pytest.raises(ApiError):
- self.plugin.notify(notification)
- @responses.activate
- def test_no_error_on_ignorable_slack_errors(self):
- responses.add("POST", "http://example.com/slack", status=403, body="action_prohibited")
- self.plugin.set_option("webhook", "http://example.com/slack", self.project)
- event = self.store_event(
- data={"message": "Hello world", "level": "warning", "culprit": "foo.bar"},
- project_id=self.project.id,
- )
- rule = Rule.objects.create(project=self.project, label="my rule")
- notification = Notification(event=event, rule=rule)
- # No exception since certain errors are supposed to be ignored
- with self.options({"system.url-prefix": "http://example.com"}):
- self.plugin.notify(notification)
- responses.replace("POST", "http://example.com/slack", status=403, body="some_other_error")
- # Other exceptions should not be ignored
- with self.options({"system.url-prefix": "http://example.com"}):
- with pytest.raises(ApiError):
- self.plugin.notify(notification)
|