Как я могу выводить HTML в сообщении в новой структуре сообщений Django?
Я пытаюсь отобразить немного html в сообщении, которое отображается через новую структуру сообщений Django. В частности, я делаю это с помощью метода ModelAdmin.message_user, который представляет собой лишь тонкую оболочку сообщений():
def message_user(self, request, message):
"""
Send a message to the user. The default implementation
posts a message using the django.contrib.messages backend.
"""
messages.info(request, message)
Все, что я пробовал до сих пор, похоже, отображает экранированный HTML.
self.message_user(request, "<a href=\"http://www.google.com\">Here google!</a>")
Не работает и не работает:
from django.utils.safestring import mark_safe
...
self.message_user(request, mark_safe("<a href=\"http://www.google.com\">Here google!</a>"))
Отображение кода шаблона в шаблоне admin base.html довольно просто:
{% if messages %}
<ul class="messagelist">{% for message in messages %}<li>{{ message }}</li>{% endfor %}</ul>
{% endif %}
Поэтому я не совсем уверен, что я делаю неправильно.
Мысли или руководство получили высокую оценку, спасибо!
Ответы
Ответ 1
Другой вариант - использовать extra_tags
keyword arg, чтобы указать, что сообщение безопасно. Например,
messages.error(request, 'Here is a <a href="/">link</a>', extra_tags='safe')
затем используйте шаблонную логику для использования безопасного фильтра
{% for message in messages %}
<li class="{{ message.tags }}">
{% if 'safe' in message.tags %}{{ message|safe }}{% else %}{{ message }}{% endif %}
</li>
{% endfor %}
Ответ 2
Как указано в следующем билете Django, он должен работать, если вы используете mark_safe() в сочетании с бэкэнд SessionStorage: https://code.djangoproject.com/ticket/14976#comment:9
Ответ 3
Вы пробовали {{ message | safe }}
?
В шаблоне шаблона шаблона Django всегда сбрасываются, если вы не указали их как безопасные с фильтром safe
. Это значение по умолчанию делает даже невредимым защиту от инъекции.
Я не уверен, как это взаимодействует с mark_safe, но, возможно, что-то произошло между ними, что снова стало небезопасным.
Ответ 4
Это сработало для меня (Джанго 1.11):
from django.contrib import messages
from django.utils.safestring import mark_safe
messages.info(request, mark_safe('This is link to <a href="http://google.com">http://google.com</a>'))
Ответ 5
Я искал способ использовать unescaped HTML в списке admin. Не уверен, что это относится к структуре сообщений, но использование allow_tags, как описано здесь, помогло мне.
http://urlencode.blogspot.com/2009/10/neat-django-admin-tricks-part-1.html
Ответ 6
Весь смысл системы шаблонов состоит в том, чтобы иметь дело со строками и данными, подобными этим.
В то время как каждый другой ответ указывает на то, что вы должны пометить вашу созданную строку как безопасную, я бы пошел еще дальше и сказал бы вам никогда не использовать HTML в вашем коде - всегда используйте шаблон.
Система шаблонов гарантирует, что вещи должным образом экранированы, так что вам не нужно об этом беспокоиться, и программисту гораздо сложнее попасть в ситуацию, когда они создают строку HTML из набора if
и пользовательские данные.
app/templates/app/fragments/google_link.html
:
<a href="https://www.google.com">Here Google!</a>
views.py
:
from django.template import loader
...
def view(request):
messages.info(
request,
loader.render_to_string(
'app/fragments/google_link.html',
{},
request=request,
),
)
Ответ 7
Вы можете использовать format_html. Это относится к экранированию всех аргументов.
Например, если мы можем связать детали mymodel с помощью атрибута, называемого name:
from django.contrib import messages
from django.utils.html import format_html
message = format_html("{} <a href='{}'>{}</a>",
"This is the mymodel",
reverse('myapp:mymodel-detail', args=(mymodel.id,)),
mymodel.name)
messages.info(request, message)
Этот ответ основан на fooobar.com/info/430515/...