CKEditor 5 в админке Django: короткое руководство
Как заменить простое textarea в админке Django на визуальный редактор текста с форматированием. Настройка занимает около 15 минут на пакете django-ckeditor-5.

По умолчанию поле TextField в админке Django выглядит как обычное серое текстовое поле без единой кнопки форматирования. Если в этом поле редактор должен набирать статьи с заголовками, списками и ссылками, работать в голом textarea мучительно. К концу этого руководства у вас в админке будет визуальный редактор с панелью форматирования, а в базе — HTML. Настройка занимает 10–15 минут.
Разбираем связку Django 5.x и пакета django-ckeditor-5 — это активно поддерживаемая обёртка вокруг CKEditor 5. Старый пакет django-ckeditor тянет CKEditor 4, у которого закончилась публичная поддержка, поэтому для нового проекта берите именно версию с пятёркой.
Что нужно иметь до начала
- работающий проект на Django 5.x (проверить:
python -m django --version); - активированное виртуальное окружение и права ставить пакеты через
pip; - модель с текстовым полем, которое хотите редактировать (в примере — модель статьи с полем
content); - настроенная раздача статики: переменная
STATIC_URLв настройках и для продакшена —STATIC_ROOT.
Если статику вы ещё ни разу не собирали, ничего страшного: для локальной разработки при включённом DEBUG = True Django раздаёт файлы приложений сам.
Шаг 1. Установить пакет
pip install django-ckeditor-5Проверка: команда завершилась без ошибок, а pip show django-ckeditor-5 показывает установленную версию. Зафиксируйте её в requirements.txt, чтобы через полгода не поймать несовместимость.
Шаг 2. Подключить приложение
Добавьте приложение в INSTALLED_APPS в файле настроек проекта:
# settings.py
INSTALLED_APPS = [
# ... стандартные приложения Django
"django.contrib.staticfiles",
"django_ckeditor_5",
# ... ваши приложения
]Имя приложения пишется через нижнее подчёркивание — django_ckeditor_5, хотя пакет ставится через дефис. Это частый источник ошибки на старте.
Шаг 3. Настроить панель редактора
Редактор берёт конфигурацию из словаря CKEDITOR_5_CONFIGS. Минимальный набор с одним профилем default выглядит так:
# settings.py
CKEDITOR_5_CONFIGS = {
"default": {
"toolbar": [
"heading", "|",
"bold", "italic", "link", "|",
"bulletedList", "numberedList", "|",
"blockQuote", "insertTable", "|",
"undo", "redo",
],
},
}Названия кнопок — это идентификаторы плагинов CKEditor 5, а не произвольные строки. Если вписать несуществующее имя, кнопка просто не появится, а в консоли браузера будет предупреждение. Полный список доступных кнопок сверяйте в документации CKEditor 5 по конкретной сборке — набор плагинов зависит от версии.
Шаг 4. Подключить поле в модели
Замените TextField на CKEditor5Field. Параметр config_name ссылается на профиль из CKEDITOR_5_CONFIGS:
# models.py
from django.db import models
from django_ckeditor_5.fields import CKEditor5Field
class Article(models.Model):
title = models.CharField("Заголовок", max_length=200)
content = CKEditor5Field("Текст", config_name="default")
def __str__(self):
return self.titleСоздайте и примените миграции — тип столбца в базе останется текстовым, но Django должен зафиксировать изменение поля:
python manage.py makemigrations
python manage.py migrateПроверка: команды прошли без ошибок и makemigrations сообщила об изменении поля content.
Шаг 5. Прописать маршруты для загрузки
Редактор умеет загружать картинки, и для этого пакету нужен свой URL. Добавьте его в корневой urls.py:
# urls.py
from django.contrib import admin
from django.urls import path, include
urlpatterns = [
path("admin/", admin.site.urls),
path("ckeditor5/", include("django_ckeditor_5.urls")),
]Без этого блока текст редактируется, но при попытке вставить изображение вы получите ошибку загрузки.
Шаг 6. Зарегистрировать модель и проверить
# admin.py
from django.contrib import admin
from .models import Article
admin.site.register(Article)Запустите сервер и откройте страницу добавления статьи в админке:
python manage.py runserverПроверка: на месте поля content вместо серого прямоугольника появилась панель с кнопками форматирования. Наберите текст, сделайте заголовок и список, сохраните запись. В базе в этом поле окажется HTML-разметка.
Как показать результат на сайте
В базе теперь лежит HTML, и в шаблоне его нужно вывести без экранирования. Django по умолчанию экранирует всё, поэтому применяйте фильтр safe:
{{ article.content|safe }}Фильтр safe выводит содержимое как есть. Это безопасно ровно до тех пор, пока текст пишут доверенные редакторы через админку. Если поле заполняют внешние пользователи, сырой HTML открывает дорогу XSS — тогда содержимое нужно чистить санитайзером перед сохранением.Если не получилось
- Поле осталось обычным textarea, панели нет. Чаще всего не подгрузилась статика редактора. При
DEBUG = Trueпроверьте, чтоdjango.contrib.staticfilesесть вINSTALLED_APPS. На продакшене выполнитеpython manage.py collectstatic. - ModuleNotFoundError: No module named 'django_ckeditor_5'. Приложение вписано с дефисом вместо подчёркивания либо пакет установлен в другое окружение. Сверьте активное окружение и имя в
INSTALLED_APPS. - При вставке картинки — ошибка загрузки или 404. Не подключён маршрут
ckeditor5/вurls.pyлибо не настроеныMEDIA_URLиMEDIA_ROOTдля хранения файлов. - В шаблоне видны теги вида <p> как текст. Забыли фильтр
safeпри выводе поля. - Кнопка из toolbar не появилась. Указано имя плагина, которого нет в вашей сборке CKEditor 5. Сверьте идентификатор с документацией.
Что настроить дальше
Базовый редактор работает. Следующие шаги — по мере необходимости: настройте MEDIA_ROOT и права на загружаемые файлы, если редакторы будут заливать изображения; заведите отдельный профиль в CKEDITOR_5_CONFIGS с урезанной панелью для комментариев или анонсов; на продакшене не забудьте про collectstatic в процессе деплоя. Санитайзинг HTML и разграничение прав редакторов — отдельная тема, здесь мы её не разворачиваем.
Редактор изображений: Убрать лишнее, заменить фон, добавить объект, расширить кадр — на вашем изображении.
Спросить за 20 ₽Источники: django-ckeditor-5 на PyPI, CKEditor 5 documentation — Toolbar
Частые вопросы
А если у меня Django 4.2, а не 5.x?
Чем django-ckeditor-5 отличается от старого django-ckeditor?
Панель не появилась даже после collectstatic — что дальше?
Безопасно ли хранить и выводить HTML из редактора?
Можно ли сделать разные редакторы для разных полей?
Нужно ли что-то делать с базой при замене TextField на CKEditor5Field?
Материал носит информационный характер и подготовлен редакцией «Агентуры». Он не является офертой, рекламой или индивидуальной консультацией. Упомянутые продукты, компании и торговые знаки принадлежат их правообладателям. Перед принятием решений, влекущих юридические или финансовые последствия, обратитесь к профильному специалисту.