名前を変えてはいけない。

Rails+PostgreSQLで、Fooというモデルがありfoosってテーブルがあるとする。このモデルの名前をBarにしたいとき、テーブルはMigrationの定義を書けば変更できる。

class FooToBar < ActiveRecord::Migration
  def self.up
    rename_table :foos, :bars
  end

  def self.down
    rename_table :bars, :foos
  end
end

後はapp/models/foo.rbを書き換えてやれば名前は変わる、かに見える。
しっかーし、やらしい落とし穴が。foosテーブルのIDを管理するために、シーケンスfoos_id_seqが作成されてるんだけど、これの名前はMigrationで変更されない。だから、こんな風になる。

# \d
               List of relations
 Schema |       Name        |   Type   | Owner 
--------+-------------------+----------+-------
 public | bars               | table    | user
 public | foos_id_seq        | sequence | user

シーケンスfoos_id_seqは名前変更後のテーブルbarsに結びついたままなので、普通にSQLを叩いてやる分には問題ないのだけど、Railsから(というよりARから)扱おうとした瞬間にはまる。
findなんかは問題ないのだけど、新しいレコードを追加しようとしたら

ActiveRecord::StatementInvalid (PGError: ERROR:  currval of sequence "bars_id_seq" is not yet defined in this session
: SELECT currval('bars_id_seq')):

こう、PGErrorが出て落っこちる。ARはどうやらシーケンス名をテーブル名からはじき出し、"[TABLE NAME]_id_seq"だと思って呼び出そうとするらしい。
シーケンスの名前は変えられないようなので、IDをいったん消して作り直してもいいのだけど、それだとIDが失われるのでどっちかと言えばテーブル名はそのまま、モデル側でset_table_nameしてやるといいみたい。