Railsからbigintを使用する時の注意点

idとかの AUTO_INCREMENTのカラムをbigintで使用している時、特に32bitを超える数値の時(自分のPCは32bitマシン)は明らかに挙動がおかしい。
例えば

id bigint
title text
body text

というテーブルがあり

alter table posts auto_increment = 100000000000000;

と設定し

post = Post.new
post.title = "aaa"
post.body = "bbb"
post.save!

とした場合、MySQL C API の関数 mysql_insert_id()を実行します。
この関数は、直近の INSERT クエリにより AUTO_INCREMENT カラム用に生成さ
れたIDを取得します。が、mysql_insert_id() の返り値の型を long 型に変換します。
AUTO_INCREMENT カラムが BIGINT 型である場合、返される型は不正確になります。

なので、

redirect_to :action=>:show,id=>post

saveのあとに詳細ページへリダイレクトすると、modelのidの数値が不正なのでRecodeNotFoundとなります。

解決方法は

module ActiveRecord
  module ConnectionAdapters
    class MysqlAdapter < AbstractAdapter
      def insert(sql, name = nil, pk = nil, id_value = nil, sequence_name = nil) #:nodoc:
        execute(sql, name = nil)
        id_value || @connection.query("SELECT LAST_INSERT_ID();").fetch_row()[0].to_i
        #id_value || @connection.insert_id
      end
    end
  end
end

をenviroment.rbとかに書けばOK!
いや〜これで軽く半日はハマった^^;

でも、これは他の言語でも同じ現象起こしそうだ・・・