在 django 模板中使用标签对消息进行排序
sorting messages with tag in django template
我收到了一个消息列表,每条消息都有一个标签。它可能是“信息”、“警告”、“危险”和“电子表格”。我需要先显示前三个,然后再显示电子表格,但如果超过 3 个,则可以折叠。
所以对于所有消息,但电子表格的模板是:
<div class="row banner">
<ul class="banner-message">
{% for message in messages %}
<li{% if message.tags %} class="banner-message--{{ message.tags }}" {% else %} class="banner-message--info" {% endif %}>
<div class="message-content">
<p>{{ message|safe }}</p>
<span class="close">×</span></div>
</li>
{% endfor %}
</ul>
</div>
对于带有“电子表格”标签的标签,模板是:
<div class="row banner">
<ul class="banner-message">
{% for message in messages %}
<li class="{% if forloop.counter >= 3 %}collapsible_content{% endif %} banner-message--info">
<div class='message-content'>
<p>{{ message|safe }}</p>
<span class="close">×</span>
</div>
</li>
{% endfor %}
{% if messages|length > 3 %}
<button id="show_more" class="btn btn-secondary collapsible_button">Show all</button>
{% endif %}
</ul>
</div>
如果电子表格消息超过 3 个并在点击时显示所有按钮,则为电子表格消息显示按钮。
问题是我在一个数组中收到这些消息,我不能保证它们不会以不同的顺序全部混淆。
我需要用 message.tags
以某种方式将它们排序到两个单独的数组中?或者使用一些聪明的 if 但我不知道如何在模板中实现它。你能帮忙吗?
编辑:
在下面发表评论后,我正在尝试对 view.py
中的消息进行排序
m = messages.get_messages(request)
if len(m) > 0:
context['msgs'] = m.filter(tags__in=['info', 'warning', 'danger']).order_by('tags')
context['spreadsheet'] = m.filter(tags='spreadsheet')
m 是 FallbackStorage
对象,它没有 filter
方法。 m.objects
和 FallbackStorage.objects
也不起作用(同理:没有属性 'objects')。我已经尝试用 messages
直接完成上述所有操作(没有 get_messages
方法),但结果是一样的。如何正确过滤?
您可以将消息分成两个不同的查询集。在你的 views.py:
context['messages'] = messages.filter(tags__in = ['info','warning','danger']).order_by('tags')
context['spreadsheet'] = messages.filter(tags = 'spreadsheet')
在您的模板上:
<div class="row banner">
<ul class="banner-message">
{% for message in messages %}
<li{% if message.tags %} class="banner-message--{{ message.tags }}" {% else %} class="banner-message--info" {% endif %}>
<div class="message-content">
<p>{{ message|safe }}</p>
<span class="close">×</span></div>
</li>
{% endfor %}
</ul>
</div>
<div class="row banner">
<ul class="banner-message">
{% for message in spreadsheet %}
<li class="{% if forloop.counter >= 3 %}collapsible_content{% endif %} banner-message--info">
<div class='message-content'>
<p>{{ message|safe }}</p>
<span class="close">×</span>
</div>
</li>
{% endfor %}
{% if messages|length > 3 %}
<button id="show_more" class="btn btn-secondary collapsible_button">Show all</button>
{% endif %}
</ul>
</div>
编辑:
根据您的评论。我建议尝试这样的事情:
msgs = []
spreadsheet = []
m = messages.get_messages(request)
if len(m) > 0:
for mensaje in m:
#TRY THE THREE OPTIONS BECAUSE I DON'T KNOW THE MESSAGES' STRUCTURE#
if 'spreadsheet' in message['tags']:
#if 'spreadsheet' in message.tags:
#if 'spreadshhet' in message.tags():
spreadsheet.append(mensaje)
else:
msgs.append(mensaje)
context['msgs'] = msgs
context['spreadsheet'] = spreadsheet
get_messages
是效用函数而不是 class 方法。您可以在文档 here.
中阅读有关如何使用它的更多信息
在您看来您可以这样做:
from django.contrib.messages import get_messages
...
message_list = get_messages(request)
messages = []
spreadsheet_messages = []
for message in message_list:
tags = message.tags
if ("info" in tags) or ("warning" in tags) or ("danger" in tags):
messages.append(message)
if "spreadsheet" in tags:
spreadsheet_messages.append(message)
context["messages"] = messages
context["spreadsheet"] = spreadsheet_messages
...
我收到了一个消息列表,每条消息都有一个标签。它可能是“信息”、“警告”、“危险”和“电子表格”。我需要先显示前三个,然后再显示电子表格,但如果超过 3 个,则可以折叠。
所以对于所有消息,但电子表格的模板是:
<div class="row banner">
<ul class="banner-message">
{% for message in messages %}
<li{% if message.tags %} class="banner-message--{{ message.tags }}" {% else %} class="banner-message--info" {% endif %}>
<div class="message-content">
<p>{{ message|safe }}</p>
<span class="close">×</span></div>
</li>
{% endfor %}
</ul>
</div>
对于带有“电子表格”标签的标签,模板是:
<div class="row banner">
<ul class="banner-message">
{% for message in messages %}
<li class="{% if forloop.counter >= 3 %}collapsible_content{% endif %} banner-message--info">
<div class='message-content'>
<p>{{ message|safe }}</p>
<span class="close">×</span>
</div>
</li>
{% endfor %}
{% if messages|length > 3 %}
<button id="show_more" class="btn btn-secondary collapsible_button">Show all</button>
{% endif %}
</ul>
</div>
如果电子表格消息超过 3 个并在点击时显示所有按钮,则为电子表格消息显示按钮。
问题是我在一个数组中收到这些消息,我不能保证它们不会以不同的顺序全部混淆。
我需要用 message.tags
以某种方式将它们排序到两个单独的数组中?或者使用一些聪明的 if 但我不知道如何在模板中实现它。你能帮忙吗?
编辑: 在下面发表评论后,我正在尝试对 view.py
中的消息进行排序m = messages.get_messages(request)
if len(m) > 0:
context['msgs'] = m.filter(tags__in=['info', 'warning', 'danger']).order_by('tags')
context['spreadsheet'] = m.filter(tags='spreadsheet')
m 是 FallbackStorage
对象,它没有 filter
方法。 m.objects
和 FallbackStorage.objects
也不起作用(同理:没有属性 'objects')。我已经尝试用 messages
直接完成上述所有操作(没有 get_messages
方法),但结果是一样的。如何正确过滤?
您可以将消息分成两个不同的查询集。在你的 views.py:
context['messages'] = messages.filter(tags__in = ['info','warning','danger']).order_by('tags')
context['spreadsheet'] = messages.filter(tags = 'spreadsheet')
在您的模板上:
<div class="row banner">
<ul class="banner-message">
{% for message in messages %}
<li{% if message.tags %} class="banner-message--{{ message.tags }}" {% else %} class="banner-message--info" {% endif %}>
<div class="message-content">
<p>{{ message|safe }}</p>
<span class="close">×</span></div>
</li>
{% endfor %}
</ul>
</div>
<div class="row banner">
<ul class="banner-message">
{% for message in spreadsheet %}
<li class="{% if forloop.counter >= 3 %}collapsible_content{% endif %} banner-message--info">
<div class='message-content'>
<p>{{ message|safe }}</p>
<span class="close">×</span>
</div>
</li>
{% endfor %}
{% if messages|length > 3 %}
<button id="show_more" class="btn btn-secondary collapsible_button">Show all</button>
{% endif %}
</ul>
</div>
编辑:
根据您的评论。我建议尝试这样的事情:
msgs = []
spreadsheet = []
m = messages.get_messages(request)
if len(m) > 0:
for mensaje in m:
#TRY THE THREE OPTIONS BECAUSE I DON'T KNOW THE MESSAGES' STRUCTURE#
if 'spreadsheet' in message['tags']:
#if 'spreadsheet' in message.tags:
#if 'spreadshhet' in message.tags():
spreadsheet.append(mensaje)
else:
msgs.append(mensaje)
context['msgs'] = msgs
context['spreadsheet'] = spreadsheet
get_messages
是效用函数而不是 class 方法。您可以在文档 here.
在您看来您可以这样做:
from django.contrib.messages import get_messages
...
message_list = get_messages(request)
messages = []
spreadsheet_messages = []
for message in message_list:
tags = message.tags
if ("info" in tags) or ("warning" in tags) or ("danger" in tags):
messages.append(message)
if "spreadsheet" in tags:
spreadsheet_messages.append(message)
context["messages"] = messages
context["spreadsheet"] = spreadsheet_messages
...