Фильтр счета аннотации Django - PullRequest
2 голосов
/ 16 февраля 2012

Я пытаюсь подсчитывать ежедневные записи для некоторой модели, но мне хотелось бы, чтобы подсчет производился только для записей с некоторым полем fk = xy, поэтому я получаю список дней, когда была создана новая запись, но некоторые могут вернуть 0.

class SomeModel(models.Model):
    place = models.ForeignKey(Place)
    note = models.TextField()
    time_added = models.DateTimeField()

Скажите, что есть место с именем = "NewYork"

data = SomeModel.objects.extra({'created': "date(time_added)"}).values('created').annotate(placed_in_ny_count=Count('id'))

Это работает, но показывает все записи ... все места.

Пробовал с фильтрацией,но он не возвращает дни, когда не было записи с place.name="NewYork".Это не то, что мне нужно.

1 Ответ

1 голос
/ 17 февраля 2012

Похоже, что вы хотите знать, для каждого дня, в который был добавлен любой объект, сколько объектов, созданных в этот день, имеют место, имя которого - Нью-Йорк.(Дайте мне знать, если я неправильно понял.) В SQL требуется внешнее объединение :

SELECT m.id, date(m.time_added) AS created, count(p.id) AS count
  FROM myapp_somemodel AS m
  LEFT OUTER JOIN myapp_place AS p
       ON m.place_id = p.id
       AND p.name = 'New York'
  GROUP BY created

Так что вы всегда можете выразить это в Django, используя необработанный SQL-запрос:

for o in SomeModel.objects.raw('SELECT ...'):   # query as above
    print 'On {0}, {1} objects were added in New York'.format(o.created, o.count)

Примечания:

  1. Я не пытался выяснить, можно ли это выразить на языке запросов Джанго;это может быть, но , как утверждают разработчики , API базы данных - это «ярлык, но не обязательно конечный результат»)

  2. m.id является избыточным в запросе SQL, но Django требует , что «первичный ключ ... всегда должен быть включен в необработанный запрос».

  3. Youвероятно, вы не хотите записывать в запросе литерал 'New York', поэтому вместо этого передайте параметр : raw('SELECT ... AND p.name = %s ...', [placename]).

...