Как упорядочить набор queryset, сохраняя объекты, сгруппированные по другому полю?
У меня есть модель с двумя полями дата и тип class Obj(Model): date = DateTimeField type = ChoiceField Я хочу упорядочить их по дате создания, но хочу, чтобы объекты одного типа держались вместе ОБЪЕКТ:
-
<<<1><1>>01.01.2022 СИНИЙ
- 02.01.2022 ЧЕРНЫЙ
- 03.01.2022 СИНИЙ
- 04.01.2022 ЗЕЛЕНЫЙ
- 05.01.2022 СИНИЙ
- 06.01.2022 BLACK
- 07.01.2022 GREEN
- 07.01.2022 ЗЕЛЕНЫЙ
- 04.01.2022 ЗЕЛЕНЫЙ
- 06.01.2022 ЧЕРНЫЙ
- 02.01.2022 ЧЕРНЫЙ
- 05.01.2022 СИНИЙ
- 03.01.2022 BLUE
- 01.01.2022 BLUE
Когда я делаю заказ, я хочу, чтобы он сначала посмотрел на дату, получил последнюю дату, затем взял все объекты с типом этого объекта и расположил их в порядке, сохраняя порядок дат среди них, а затем взял следующую дату второго типа и расположил их в порядке после предыдущего:
УПОРЯДОЧЕН:
По сути, я хочу сначала упорядочить_по_заголовку, а затем упорядочить группы по дате. Могу ли я сделать это тривиально или мне придется использовать Case When или, возможно, даже необработанный SQL. Было бы лучше, если бы я мог избежать необработанного SQL, потому что это постранично
Правильно, я думаю, что у меня есть ответ для вас, который работает - вам нужно использовать Subquery и OuterRef. Первый набор запросов упорядочивает все модели Obj по нужной вам дате, но фильтруется с помощью OuterRef - OuterRef получает поле type из второй строки.
Вторая строка затем выполняет аннотацию с подзапросом первой строки, .values('date')[:1]
получает последнее значение даты (которое вы можете захотеть изменить). Аннотация означает, что каждый объект помечен датой, когда был создан самый новый объект этого типа.
from django.db.models import OuterRef, Subquery
dates = Obj.objects.filter(type=OuterRef('type')).order_by('-date')
Obj.objects.annotate(
newest_creation=Subquery(dates.values('date')[:1])
).order_by('date', 'newest_creation')
Возможно, вам придется изменить порядок следования даты и newest_creation, чтобы получить желаемый порядок.