Ich habe eine Messages
Tabelle mit user_id
Feld (Zeichenfolge). Eine Abfrage für insgesamt eindeutige Benutzer ist extrem langsam mit mehr als einer Million Datensätze.Langsame activerecord/postgres Abfrage nicht mit Index
Message.where(created_at: start_date..end_date).select(:user_id).distinct(:user_id).count
=> (120145.6ms) SELECT DISTINCT COUNT(DISTINCT "messages"."user_id") FROM "messages" WHERE ("messages"."created_at" BETWEEN '2016-05-14 04:00:00.000000' AND '2016-06-13 03:59:59.999000')
Ich habe Indizes auf user_id
& created_at
, aber Postgres scheint nicht, sie zu benutzen:
Schema
add_index "messages", ["user_id"], name: "index_messages_on_user_id", using: :btree
add_index "messages", ["created_at"], name: "index_messages_on_created_at", using: :btree
PG Erklären
QUERY PLAN
-----------------------------------------------------------------------------------------------------------------------------------------------------------------
HashAggregate (cost=56111.04..56291.89 rows=18085 width=29)
Group Key: user_id
-> Seq Scan on messages (cost=0.00..52215.65 rows=1558153 width=29)
Filter: ((created_at >= '2016-05-14 04:00:00'::timestamp without time zone) AND (created_at <= '2016-06-13 03:59:59.999'::timestamp without time zone))
(4 rows)
Warum werden die Indizes nicht verwendet? Irgendwelche Tipps zur Beschleunigung der Abfrage?
Ich versuchte 'Nachrichten (created_at, user_id)' und es scheint auch diesen Index zu ignorieren :( – mnort9
@ mnort9.. Versuchen Sie die 'Select distinct' zu entfernen. Es macht keinen Sinn für diese Abfrage und es könnte verwirrend sein der Optimierer –
Ohne 'select' kann ich die AR-Abfrage mit' Message.distinct.count (: user_id) 'erstellen, aber es erzeugt die selbe 'SELECT DISTINCT' sql – mnort9