Ответ 1
Я бы ожидал .latest(), чтобы всегда возвращать самый последний экземпляр, основанный на поле (дата) (время).
В документации говорится, что
Если ваша модель
Meta
указываетget_latest_by
, вы можете оставить аргументfield_name
доlatest()
. По умолчанию Django будет использовать поле, указанное вget_latest_by
.
Все это означает, что когда вы стреляете MyModel.objects.latest()
, вы получите последний экземпляр, основанный на поле даты/времени. И когда я проверил ваш код с использованием данных примера, он действительно сделал.
И потом мне понадобилось instance.latest(), но это не дало бы мне правильный экземпляр, на самом деле это дало мне первый экземпляр.
Вы неправильно поняли, как работает latest()
. Когда вызывается в MyModel.objects, он возвращает
последний экземпляр в таблице. При вызове запроса, latest
вернет первый объект в наборе запросов. Ваш запрос состоял из всех экземпляров MyModel
, упорядоченных по creation_date
в порядке возрастания. Естественно тогда, что latest
в этом запросе должен возвращать первую строку набора запросов. Это, кстати, самая старая строка в таблице.
Одним из способов лучшего понимания является просмотр запроса, запущенного для latest
.
Случай 1:
from django.db import connection
MyModel.objects.latest()
print connection.queries[-1]['sql']
Отпечатки:
SELECT "app_mymodel"."id", "app_mymodel"."creation_date" FROM
"app_mymodel" ORDER BY "app_mymodel"."creation_date" DESC LIMIT 1
Обратите внимание на упорядочение с помощью creation_date DESC
и предложения LIMIT
. Первое имеет значение get_latest_by
, а последнее - вклад latest
.
Теперь, случай 2:
MyModel.objects.order_by('creation_date').latest()
print connection.queries[-1]['sql']
печатает
SELECT "app_mymodel"."id", "app_mymodel"."creation_date" FROM
"app_mymodel" ORDER BY "app_mymodel"."creation_date" ASC LIMIT 1
Обратите внимание, что порядок изменился на creation_date ASC
. Это результат явного order_by
. LIMIT
приклеивается к эру, позже любезно latest
.
Давайте также рассмотрим случай 3: где вы явно указываете field_name
для objects.latest()
.
MyModel.objects.latest('id')
print connection.queries[-1]['sql']
показывает
SELECT "app_mymodel"."id", "app_mymodel"."creation_date" FROM "app_mymodel"
ORDER BY "app_mymodel"."id" DESC LIMIT 1