Как вернуть Postgres записей, сгруппированных по неделям в Rails - PullRequest
0 голосов
/ 24 марта 2020

Rails-запрос ниндзя, мне трудно получить записи из моей Postgres БД, сгруппированные по неделям их создания.

(перед тем, как заблокировать этот вопрос за дубликат, посмотрите, что я Я попробовал то, что нашел в других местах на SO, но мои результаты бесполезны. Я все еще что-то упускаю.)

Учитывая объект ActiveRecord User с отметкой времени created_at, я бы хотел быстро выясните, сколько пользователей было создано за каждую неделю года.

Я пробовал:

> User.select("DATE_TRUNC('week', created_at) as week").group("week")
  User Load (0.4ms)  SELECT DATE_TRUNC('week', created_at) as week FROM "users" GROUP BY week
[#<User:0x00007fb73892e978 id: nil>,
 #<User:0x00007fb73892e7e8 id: nil>,
 #<User:0x00007fb73892e5e0 id: nil>,
 #<User:0x00007fb73892e400 id: nil>,
 #<User:0x00007fb73892e270 id: nil>]

Кажется, это работает, поскольку в данных этого теста 7 записей и 2 поделиться на той же неделе, но я хочу получить числовой ответ для общего числа рядом с номером недели:

Week     Count
   1         2
   2         1
   3         1
   4         5

Или га sh или что-либо пригодное для использования.

Или просто ruby User.group(:created_at).count но я не уверен, как включить номер недели в этот запрос.

Спасибо за любую помощь!

1 Ответ

3 голосов
/ 24 марта 2020
User.group("DATE_TRUNC('week', created_at)").count

Это даст вам га sh с датами в качестве ключей и подсчетом в качестве значений:

=> #<User id: 2, email: "test2@example.com", created_at: "2020-03-09 22:47:51", updated_at: "2020-03-23 22:47:51", display_name: "Test2">
irb(main):020:0> User.group("DATE_TRUNC('week', created_at)").count
   (0.4ms)  SELECT COUNT(*) AS count_all, DATE_TRUNC('week', created_at) AS date_trunc_week_created_at FROM "users" GROUP BY DATE_TRUNC('week', created_at)
=> {2020-03-23 00:00:00 UTC=>1, 2020-03-09 00:00:00 UTC=>1}

Вы можете получить номера недель по:

 User.group("DATE_TRUNC('week', created_at)")
     .count
     .transform_keys {|d| d.strftime('%V') }
...