Browse Source

Escape markdown in MS Teams notifications. cc: #426

pull/437/head
Pēteris Caune 4 years ago
parent
commit
05c81e0a41
No known key found for this signature in database GPG Key ID: E28D7679E9A9EDE2
4 changed files with 32 additions and 4 deletions
  1. +1
    -0
      CHANGELOG.md
  2. +20
    -0
      hc/api/tests/test_notify.py
  3. +11
    -3
      hc/api/transports.py
  4. +0
    -1
      templates/integrations/msteams_message.json

+ 1
- 0
CHANGELOG.md View File

@ -20,6 +20,7 @@ All notable changes to this project will be documented in this file.
- When copying a check, copy all fields from the "Filtering Rules" dialog (#417)
- Fix missing Resume button (#421)
- When decoding inbound emails, decode encoded headers (#420)
- Escape markdown in MS Teams notifications (#426)
## v1.16.0 - 2020-08-04


+ 20
- 0
hc/api/tests/test_notify.py View File

@ -866,6 +866,26 @@ class NotifyTestCase(BaseTestCase):
payload = kwargs["json"]
self.assertEqual(payload["@type"], "MessageCard")
@patch("hc.api.transports.requests.request")
def test_msteams_escapes_markdown(self, mock_post):
self._setup_data("msteams", "http://example.com/webhook")
mock_post.return_value.status_code = 200
self.check.name = """
TEST _underscore_ `backticks` <u>underline</u> \\backslash\\ "quoted"
"""
self.channel.notify(self.check)
args, kwargs = mock_post.call_args
text = kwargs["json"]["text"]
self.assertIn(r"\_underscore\_", text)
self.assertIn(r"\`backticks\`", text)
self.assertIn("&lt;u&gt;underline&lt;/u&gt;", text)
self.assertIn(r"\\backslash\\ ", text)
self.assertIn("&quot;quoted&quot;", text)
@patch("hc.api.transports.os.system")
@override_settings(SHELL_ENABLED=True)
def test_shell(self, mock_system):


+ 11
- 3
hc/api/transports.py View File

@ -3,6 +3,7 @@ import os
from django.conf import settings
from django.template.loader import render_to_string
from django.utils import timezone
from django.utils.html import escape
import json
import requests
from urllib.parse import quote, urlencode
@ -582,6 +583,15 @@ class MsTeams(HttpTransport):
def notify(self, check):
text = tmpl("msteams_message.json", check=check)
payload = json.loads(text)
# Escape special HTML characters in check's name
safe_name = escape(check.name_then_code())
# Escape characters that have special meaning in Markdown
for c in r"\`*_{}[]()#+-.!|":
safe_name = safe_name.replace(c, "\\" + c)
payload["text"] = f"“{safe_name}” is {check.status.upper()}."
return self.post(self.channel.value, json=payload)
@ -629,7 +639,5 @@ class LineNotify(HttpTransport):
"Content-Type": "application/x-www-form-urlencoded",
"Authorization": "Bearer %s" % self.channel.linenotify_token,
}
payload = {
"message": tmpl("linenotify_message.html", check=check)
}
payload = {"message": tmpl("linenotify_message.html", check=check)}
return self.post(self.URL, headers=headers, params=payload)

+ 0
- 1
templates/integrations/msteams_message.json View File

@ -3,7 +3,6 @@
"@type": "MessageCard",
"@context": "https://schema.org/extensions",
"themeColor": "{% if check.status == "up" %}5cb85c{% endif %}{% if check.status == "down" %}d9534f{% endif %}",
"text": "“{{ check.name_then_code|escapejs }}” is {{ check.status|upper }}.",
"sections": [
{
"facts": [


Loading…
Cancel
Save