なんか開いてから表示されるまでクソおそくてどうしたもんかなぁ、と思っていたけど、slow_log を有効にして観察したら 10 秒とか 40 秒とかかかるクエリがあったのでインデックスはってみた。劇的にはやくなった。更めて、自分で DB のことわかってないなぁ……と気付かされた (超ごく最近まで slow_log をとれることすら知らなかった)。
実際に実行したやつ (phpmyadmin からもごもごやってた)
ALTER TABLE `items` ADD INDEX `feed_id_stored_on_created_on` ( `feed_id` , `stored_on` , `created_on` , `id` )
ためしてないけど、Migration:
class AddItemsIndex < ActiveRecord::Migration
def self.up
add_index :items, [:feed_id, :stored_on, :created_on, :id], :name => :items_search_index
end
def self.down
remove_index :items_search_index
end
end
問題のログ
# Time: 080310 9:59:22
# User@Host: root[root] @ localhost []
# Query_time: 47 Lock_time: 0 Rows_sent: 10 Rows_examined: 3511
SELECT * FROM `items` WHERE (items.feed_id = 36 AND (stored_on >= '2008-03-10 01:31:30')) ORDER BY created_on DESC, id DESC LIMIT 10;
はったあとの EXPLAIN
$ mysql -u root fastladder
mysql> EXPLAIN SELECT * FROM `items` WHERE (items.feed_id = 36 AND (stored_on >= '2008-03-10 01:31:30')) ORDER BY created_on DESC, id DESC LIMIT 10;
+----+-------------+-------+-------+--------------------------------------------------------------+------------------------------+---------+------+------+-----------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-------+-------+--------------------------------------------------------------+------------------------------+---------+------+------+-----------------------------+
| 1 | SIMPLE | items | range | index_items_on_feed_id_and_link,feed_id_stored_on_created_on | feed_id_stored_on_created_on | 13 | NULL | 115 | Using where; Using filesort |
+----+-------------+-------+-------+--------------------------------------------------------------+------------------------------+---------+------+------+-----------------------------+
1 row in set (0.06 sec)