PostgreSQL9.1のベータを試用しているんだけど、beta2からCATALOG_VERSION_NOが変わっていてバイナリ差し替えが出来なかったので、pg_upgradeを試してみた。今回はbeta1からbeta3への移行。
(9.0から9.1betaのときは、9.0のファイルが壊れまくっていてpg_upgradeが動かなかった)
まずpg_upgradeを-cオプション付きで実行。
最低限の環境が合っているか確認する。
このとき、移行元のシステムは動作していて構わない。移行先のシステムは停止させておく。
[postgres@srv ~]$ /usr/local/pgsql91b3/bin/pg_upgrade -c -b /usr/local/pgsql91b1/bin -B /usr/local/pgsql91b3/bin -d /usr/local/pgsql91b1/data -D /usr/local/pgsql91b3/data -p 50911 -P 50913
(pg_upgradeは移行先のものを使うこと)
環境が異なっているとカレントディレクトリにログが吐き出されるので、それを見てライブラリの差違をなくす。
チェックが終わったら、移行元、移行先の両システムを停止させて-cオプション無しでpg_upgradeを実行。
このときはまったのが、ログインロールにdefault_tablespaceの設定がある場合。
環境としてはroleAというロールがspaceBのオーナーであり、default_tablespace='spaceB'となっている。
pg_upgradeは
1.移行先にロールを作成
2.ロールに付属するALTERを実行
3.テーブルスペースを作成
の流れて進んでいく。
このとき、2番の処理で ALTER ROLE ロール名 SET default_tablespace='テーブルスペース'; が実行されて「そんなテーブルスペースはない」と怒られてしまう。
では先にテーブルスペースを作れば良いのかと、移行先にロールとテーブルスペースを作ってしまうと、1番の処理で「既にロールがある」と怒られてしまう。
ロールは作らず、テーブルスペースのオーナーをpostgresにしておいても同様に「既にテーブルスペース(以下略)。
結局、一時的にdefault_tablespaceを解除して実行した。
pg_dumpのときみたいに、CREATE系を先に実行して、ALTER系をあとで実行するとか出来ませんかね?
あと、pg_upgradeがエラーで中止されると、移行元システムの/data/global/pg_controlがpg_control.oldにリネームされて再実行できなくなるので、面倒だがpg_controlにリネームする必要がある。
これは再実行させないためなんでしょうかね? どうせ移行先にロールがあったら失敗するのに、と思ってみたり。
移行中にpg_upgradeの進捗が分からないのも難点。
残り時間までは必要無いので、対象ファイルがいくつあって、現在どこまで進んだのかが分かるだけでも気が楽だと思う。
停止時間を長くしたくない場合は、アプリ側で更新処理を停めて、pg_dump | psqlを流した方が参照だけでも出来るのでpg_upgradeよりマシかも。