django-bleach
django-bleach is a Django package that provides easy integration of the bleach HTML sanitization library with Django models and templates. It offers model fields and template filters to clean user-supplied HTML, preventing XSS vulnerabilities. The current version is 3.1.0, with a release cadence that generally follows Django and `bleach` updates, releasing new major versions for significant dependency bumps or framework compatibility changes.
Common errors
-
ImportError: cannot import name 'BleachField' from 'django_bleach.fields'
cause Attempting to import the `BleachField` model field from an incorrect or outdated module path. The model field `BleachField` and `BleachHTMLField` are located in `django_bleach.models`, while the form field `BleachField` is in `django_bleach.forms`.fixFor model fields, use `from django_bleach.models import BleachField` or `from django_bleach.models import BleachHTMLField`. For form fields, use `from django_bleach.forms import BleachField`. -
HTML content is unexpectedly stripped, or certain tags/attributes are removed.
cause The `BLEACH_ALLOWED_TAGS` or `BLEACH_ALLOWED_ATTRIBUTES` settings (either global in `settings.py` or field-specific) do not include the tags or attributes you expect to be retained. By default, `bleach` strips anything not explicitly allowed.fixVerify that all desired HTML tags are listed in `BLEACH_ALLOWED_TAGS`. For attributes, ensure they are explicitly listed for their respective tags in `BLEACH_ALLOWED_ATTRIBUTES` (e.g., `{'a': ['href', 'title']}`). If using a `BleachHTMLField`, check the `tags` and `attributes` arguments passed to its constructor.
Warnings
- breaking `django-bleach` version 3.0.0 updated its core `bleach` dependency to require `bleach>=5.0.0`. If you are upgrading from an older `django-bleach` version, ensure your existing `bleach` configurations (e.g., `BLEACH_ALLOWED_TAGS`, `BLEACH_ALLOWED_ATTRIBUTES`, or custom callbacks) are compatible with `bleach` 5.x, as `bleach` itself may have breaking changes or behavioral differences.
- breaking `django-bleach` version 2.0.0 dropped support for older Python and Django versions. Specifically, it now requires Python `>=3.8` and Django `>=3.2`. Attempting to install or run `django-bleach` 2.x or later on incompatible environments will result in errors.
- gotcha Improper configuration of allowed HTML tags and attributes can lead to either over-stripping of desired HTML content or insufficient sanitization, potentially introducing security vulnerabilities (e.g., XSS). The default global settings might not be appropriate for all use cases, and field-specific overrides are critical.
Install
-
pip install django-bleach
Imports
- BleachHTMLField
from django_bleach.models import BleachHTMLField
- BleachField (Model)
from django_bleach.fields import BleachField
from django_bleach.models import BleachField
- BleachField (Form)
from django_bleach.models import BleachField
from django_bleach.forms import BleachField
Quickstart
import os
from django.db import models
from django_bleach.models import BleachHTMLField
# Configure settings (e.g., in settings.py or test setup)
# You can also pass these directly to the field constructor
# os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'your_project.settings')
# os.environ['BLEACH_ALLOWED_TAGS'] = "['p', 'a', 'strong', 'em']"
# os.environ['BLEACH_ALLOWED_ATTRIBUTES'] = "{'a': ['href', 'title']}"
class Article(models.Model):
title = models.CharField(max_length=200)
# Use BleachHTMLField for content that might contain HTML
content = BleachHTMLField(
blank=True,
null=True,
# Field-specific allowed tags and attributes override global settings
tags=['p', 'a', 'h1', 'h2', 'strong', 'em', 'img'],
attributes={'a': ['href', 'title'], 'img': ['alt', 'src']},
strip_tags=False, # Do not strip tags not explicitly allowed (default is False)
strip_comments=True # Strip HTML comments (default is True)
)
def __str__(self):
return self.title
# Example usage (after creating and migrating the model):
# article = Article.objects.create(title='My Article', content='<h1>Hello</h1><p>This is <strong>safe</strong> content.</p><script>alert("XSS!")</script>')
# print(article.content) # Script tag should be removed.