Stack Overflow на русском Asked by Aquinary on December 2, 2021
Имеется таблица сообщений следующего вида:
Вопрос заключается в том, каким образом на основе этой таблицы вывести список диалогов.
Список диалогов имеет следующие требования:
Первый пункт криво-косо я реализовал, а вот на втором очень сильно застрял.
# model
# Получаем список всех диалогов пользователя (фильтруем по двум полям сразу)
dialogs = DialogModel.objects.filter(Q(u_from=u_id) | Q(u_to=u_id))
for dialog in dialogs:
# Не допускает, чтобы пользователь видел самого себя в диалогах
dialog.user = dialog.u_from
if dialog.u_from_id == self.u_id:
dialog.user = dialog.u_to
# template
# Просто вывод сообщений, на всякий случай
{% for dialog in dialogs %}
{{ dialog.user }} {{ dialog.time }} <br>
{% endfor %}
На текущий момент результат выглядит так:
Однако нужно, чтобы никнейм повторялся только единожды для отдельного собеседника.
Каким образом и на каком этапе можно это реализовать?
Заранее благодарю за помощь.
Решение было найдено:
# Получаем таблицу сообщений пользователя
dialogs = DialogModel.objects.filter(Q(u_from=u_id) | Q(u_to=u_id))
# Превращаем QuerySet в список словарей
dialogs = dialogs.values('u_from__id', 'u_from__username', 'u_to__id', 'u_to__username', 'time')
# Делаем так, чтобы не видеть самого себя в списках диалогах
# Так же это можно реализовать через сравнение в шаблоне (это будет даже короче по коду),
# но я решил оставить эту логику во вьюхе и не раскидывать логику по всему проекту
for dialog in dialogs:
dialog['username'] = dialog.pop('u_from__username')
dialog['id'] = dialog.pop('u_from__id')
if dialog['id'] == self.u_id:
dialog['username'] = dialog.pop('u_to__username')
dialog['id'] = dialog.pop('u_to__id')
# На выходе получаем список словарей с содержимым, вроде
# {'time': datetime.datetime(2020, 7, 23, 16, 47, 37, 600365), 'username': 'Гость13', 'id': 13}
# Так как в списке могут попадаться словари с одинаковым username, то удаляем дубликаты
dialogs = list({item['username']: item for item in dialogs}.values())
# В результате получаем список словарей без повторяющихся username, готовых к выводу
Answered by Aquinary on December 2, 2021
Можно проверить, если следующее сообщение от того же самого адресата, то не указывать dialog.user.
Ваш пример в который я добавил непроверенный псевдо-код:
# model
# Получаем список всех диалогов пользователя (фильтруем по двум полям сразу)
dialogs = DialogModel.objects.filter(Q(u_from=u_id) | Q(u_to=u_id))
i = 0
for dialog in dialogs:
# Не допускает, чтобы пользователь видел самого себя в диалогах
dialog.user = dialog.u_from
if dialog.u_from_id == self.u_id:
dialog.user = dialog.u_to
nextItemIndex = i + 1
if dialogs.length >= nextItemIndex and dialogs[nextItemIndex].u_from_id != self.u_id:
dialog.user = ''
i = nextItemIndex
# template
# Просто вывод сообщений, на всякий случай
{% for dialog in dialogs %}
{{ dialog.user }} {{ dialog.time }} <br>
{% endfor %}
Answered by hwak on December 2, 2021
Get help from others!
Recent Questions
Recent Answers
© 2024 TransWikia.com. All rights reserved. Sites we Love: PCI Database, UKBizDB, Menu Kuliner, Sharing RPP