Skip to main content

A markdown renderer focusing on security first

Project description

safemd Twitter Follow Add Hultnér on LinkedIn Build Status PyPI - Status Codacy Badge Codacy Badge PyPI Code style: black

♜ safemd

A markdown renderer focusing on security first
Building upon the strong foundation of GitHub's fork of cmark while adding additional security precautions to be safe out of the box.

When auditing applications rendering markdown from user input I noticed that many popular markdown implementations are unsafe and vulnerable to XSS with standard configuration.

I am a strong believer in safe by default instead of opt-in security. Therefor I decided to build a library focusing on using the best tools for the job while configuring them to safely render unsanitized user input.

Installation & usage

Install through pip:
Any other tool using PyPI works fine as well, I always recommend using virtual environments.

$ pip install safemd

Render standard markdown:

import safemd

safemd.render(content)

Render GitHub Flavoured Markdown:

import safemd

safemd.render(content, flavour="github")

Precautions taken

The same library used for rendering markdown in the official PyPI Warehouse application is used by safemd. This is based on GitHub's battle-tested fork of CommonMark. We use this with the safety feature CMARK_OPT_SAFE enabled per default, so no one in your team accidentally let insecure code slip through. As an additional safety layer safemd also pass the output from cmark through a whitelist with Bleach, Mozilla's HTML sanitizing library.

Automatic safety testing through Travis is also utilized, running daily even if there are no new changes.

Opt-out from safety features

There's a way to opt-out of these safety precautions for those cases where you have a genuine need, this way it's obvious for you and your team that these places are to be considered with extra care.

import safemd

# Disable additional whitelist sanitizing through bleach
safemd.render(content, UNSAFE_NO_BLEACH=True)

# Disable cmark safety functions
safemd.render(content, UNSAFE_CMARK_XSS=True)

Is my application vulnerable?

It's not uncommon for various markdown-renderers in production environments to be open for XSS-exploits, some more widespread than others. A list of common exploits have been assembled for your convenience, so you can test your current and future code.

[Just a link](javascript:alert("hi"))

[Normal link](data:text/html;base64,PHNjcmlwdD5hbGVydCgiSGkiKTwvc2NyaXB0Pgo=) 

[Nothing fishy here](data:text/html;base64,PHNjcmlwdCBzcmM9Imh0dHBzOi8vZ2lzdGNkbi5naXRoYWNrLmNvbS9IdWx0bmVyL2JjMDIzOGJkOWIxZDI4M2JhMWM5NDczZjU0M2ZmZjc4L3Jhdy9kM2U5YWFkYTdlMGRlNzFkNmNlYTY1MDVmMTljZGE2NjE1MmE0MDFlL2hpLmpzIiBpbnRlZ3JpdHk9InNoYTM4NC0yaGZ6aFlkelB1SGd0S1E2Vk96UGlNbEN2Nzl3WDM1NzdxTDR3eWpmNWhMYkEvcW1BZHhCbXdxNGl6YXRwRy93IiBjcm9zc29yaWdpbj0iYW5vbnltb3VzIj48L3NjcmlwdD4=)

Markdown XSS exploits found in the wild

Of course, this document wouldn't be complete without a list of markdown-based XSS-exploits found in the wild. Most of these are from 2018 and 2017.

Found something

I am grateful for all suggestions, improvements and bugfixes. Feel free to send a PR or create a GitHub Issue for anything that isn't sensitive and urgent. Additional tests trying to break the security is especially appriciated.

I'm on keybase for encrypted communication. Send an email to security on my own domain hultner.se. Be aware, I discard any SPF, DMARC or DKIM-failing message, including SPF-Soft fail.


 .
..:

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

safemd-18.10.4.tar.gz (6.6 kB view details)

Uploaded Source

Built Distribution

safemd-18.10.4-py3-none-any.whl (8.9 kB view details)

Uploaded Python 3

File details

Details for the file safemd-18.10.4.tar.gz.

File metadata

  • Download URL: safemd-18.10.4.tar.gz
  • Upload date:
  • Size: 6.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/2.0.0 pkginfo/1.5.0.1 requests/2.22.0 setuptools/41.2.0 requests-toolbelt/0.9.1 tqdm/4.36.1 CPython/3.7.4

File hashes

Hashes for safemd-18.10.4.tar.gz
Algorithm Hash digest
SHA256 4aa8acaf9cbeeed5e909731d0c67609e97cc81236ec48f37d1e31377a8407c89
MD5 293acf3a2b37dff974a84a069a8c4425
BLAKE2b-256 234fe7598a28463e78820ebd9bc289debfee7f42f6d4eb21bd1bc69a94e9058b

See more details on using hashes here.

File details

Details for the file safemd-18.10.4-py3-none-any.whl.

File metadata

  • Download URL: safemd-18.10.4-py3-none-any.whl
  • Upload date:
  • Size: 8.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/2.0.0 pkginfo/1.5.0.1 requests/2.22.0 setuptools/41.2.0 requests-toolbelt/0.9.1 tqdm/4.36.1 CPython/3.7.4

File hashes

Hashes for safemd-18.10.4-py3-none-any.whl
Algorithm Hash digest
SHA256 ca78ef847bcb7fa4d0fdf753aaca8abc199e89446b3d8677a54a7f30eedde17b
MD5 a3a0861b8c96786ad5f40fc0277a1c08
BLAKE2b-256 abc734286eb28b67eb80840f1304dd0fa0bb1e638aa04f7958ca6f581f6f5513

See more details on using hashes here.

Supported by

AWS AWS Cloud computing and Security Sponsor Datadog Datadog Monitoring Fastly Fastly CDN Google Google Download Analytics Microsoft Microsoft PSF Sponsor Pingdom Pingdom Monitoring Sentry Sentry Error logging StatusPage StatusPage Status page