[Rails] ActiveRecordでの検索時にインデックスの使用を強制する(MySQL用)
query-reviewerを使っていると、インデックスを作っているはずなのに、Full index tree scanをしている、とか警告される事がある(この警告がどういう意味はまだよく分かってない)。これは、データ量が少ないとかそういう理由でMySQLがインデックスを使わない方が早いと判断しているらしいんだけど、query-reviewerにはそこまではわからない。これはインデックスは使わない方が早いよ、とMySQLが判断した結果なのであって、基本的には問題ではない。
しかし、そうはいっても、インデックスが使えるのかどうか、確認したい事もあるだろう。MySQLの場合、そういう時には、発行するSQLに force index(インデックス名) と付け加えてやれば良い。しかし、RailsだとActiveRecordがそこら辺をラップしているので、そのやり方はよく分からない。マニュアルを見てもそんなオプションはないし。
Technoblogによると、findのオプションに:from => "tablename force index (index_name)"とつけると、インデックスを使ってくれると書いてある。全部書くとこんな感じ?
tbls = Tbl.find(:all, :from => "tbls force index(index_name)")
このオプション、リンク先の記事には"un-documented :from option"と書いてあるが、これは2006年の記事なので、2008年の現在ではドキュメントにもfromオプションは記載されている。SQLの文法的にも、これで動かなくなるということは考えられないように思う。(あんまり詳しくないので断定できないけど。)
インデックス名はdb/schema.rbを見ればわかる。もしくはquery-reviewerでも、使えるインデックス候補が表示される。また、インデックスを使わせたくない場合、forceの代わりにignore index(index_name1, index_name2, ...)とすると、インデックスを使わずに検索してくれる。