ぺろぺろあんてなのPostgreSQLを9.1から9.4にしました( ;´Д`)

Debian wheezyを軽い気持ちでsidにした時にpostgresの9.4というのが入ったようです。
たまたまpsすると9.1と9.4のプロセスが立ちがっている状態でしたのでカッとなって9.4へアップグレードしました。

ググるとアップグレード方法には3種類ほどあるようで、最近はpg_upgradeというコマンドがすごく楽とのことでpg_upgradeを使ってアップグレードすることにしました。

準備

postgresユーザでエラーログをログやシェルスクリプトを吐くので/tmpで作業します。

ドキュメントに書いていなかったんですが、-d -Dオプション(後述)のディレクトリには、postgresql.conf があることが前提のようでそのままpg_upgradeを実行するとnot found的なエラーになります( ;´Д`)
aptで入れたpostgresの場合、postgresql.confは/etc/以下にあるので、-d -Dのディレクトリにpostgresql.confのシンボリックリンクを貼ります。(https://gist.github.com/martinseener/cc1ffb016817c68233a1 に書いていあるのでたぶん大丈夫)

[/tmp]$ sudo -u postgres ln -s /etc/postgresql/9.1/main/postgresql.conf /var/lib/postgresql/9.1/main/postgresql.conf
[/tmp]$ sudo -u postgres ln -s /etc/postgresql/9.4/main/postgresql.conf /var/lib/postgresql/9.4/main/postgresql.conf

posgreサーバが止まっていないとpg_upgradeできないので停止します。

$ sudo service postgresql stop

アップグレードできるか確認

`-bはoldデータディレクトリ、-Bはnewデータディレクトリ、-bはoldバイナリディレクトリ、-Bは(ry
`--check`オプションを渡すと検査のみを行うとのことなので、やってみます。

[/tmp]$ sudo -u postgres /usr/lib/postgresql/9.4/bin/pg_upgrade --check -d /var/lib/postgresql/9.1/main -D /var/lib/postgresql/9.4/main -b /usr/lib/postgresql/9.1/bin -B /usr/lib/postgresql/9.4/bin
Performing Consistency Checks
-----------------------------
Checking cluster versions                                   ok
Checking database user is a superuser                       ok
Checking database connection settings                       ok
Checking for prepared transactions                          ok
Checking for reg* system OID user data types                ok
Checking for contrib/isn with bigint-passing mismatch       ok
Checking for invalid "line" user columns                    ok
Checking for presence of required libraries                 ok
Checking database user is a superuser                       ok
Checking for prepared transactions                          ok

よさそうなのでアップグレードします。

アップグレード

[/tmp]$ sudo -u postgres /usr/lib/postgresql/9.4/bin/pg_upgrade -d /var/lib/postgresql/9.1/main -D /var/lib/postgresql/9.4/main -b /usr/lib/postgresql/9.1/bin -B /usr/lib/postgresql/9.4/bin
Performing Consistency Checks
-----------------------------
Checking cluster versions                                   ok
Checking database user is a superuser                       ok
Checking database connection settings                       ok
Checking for prepared transactions                          ok
Checking for reg* system OID user data types                ok
Checking for contrib/isn with bigint-passing mismatch       ok
Checking for invalid "line" user columns                    ok
Creating dump of global objects                             ok
Creating dump of database schemas
                                                            ok
Checking for presence of required libraries                 ok
Checking database user is a superuser                       ok
Checking for prepared transactions                          ok

If pg_upgrade fails after this point, you must re-initdb the
new cluster before continuing.

Performing Upgrade
------------------
Analyzing all rows in the new cluster                       ok
Freezing all rows on the new cluster                        ok
Deleting files from new pg_clog                             ok
Copying old pg_clog to new server                           ok
Setting next transaction ID and epoch for new cluster       ok
Deleting files from new pg_multixact/offsets                ok
Setting oldest multixact ID on new cluster                  ok
Resetting WAL archives                                      ok
Setting frozenxid and minmxid counters in new cluster       ok
Restoring global objects in the new cluster                 ok
Adding support functions to new cluster                     ok
Restoring database schemas in the new cluster
                                                            ok
Setting minmxid counter in new cluster                      ok
Creating newly-required TOAST tables                        ok
Removing support functions from new cluster                 ok
Copying user relation files
                                                            ok
Setting next OID for new cluster                            ok
Sync data directory to disk                                 ok
Creating script to analyze new cluster                      ok
Creating script to delete old cluster                       ok

Upgrade Complete
----------------
Optimizer statistics are not transferred by pg_upgrade so,
once you start the new server, consider running:
    analyze_new_cluster.sh

Running this script will delete the old cluster's data files:
    delete_old_cluster.sh

成功したっぽい。
532MBくらいのデータベースがあったけど20秒とかくらいしかかからなかった印象。

postgresを起動してanalyze_new_cluster.shを実行します。(統計見てないので実行しなくてよさそうだが)

$ sudo service postgresql start
[/tmp]$ sudo -u postgres ./analyze_new_cluster.sh
This script will generate minimal optimizer statistics rapidly
so your system is usable, and then gather statistics twice more
with increasing accuracy.  When it is done, your system will
have the default level of optimizer statistics.

If you have used ALTER TABLE to modify the statistics target for
any tables, you might want to remove them and restore them after
running this script because they will delay fast statistics generation.

If you would like default statistics as quickly as possible, cancel
this script and run:
    "/usr/lib/postgresql/9.4/bin/vacuumdb" --all --analyze-only

vacuumdb: データベース"prpr_antena_production"を vacuum しています
Generating minimal optimizer statistics (1 target)
............
nerating default (full) optimizer statistics

Done

データが移行できているかの動作確認

この時点で古い9.1を削除するシェルスクリプトが出力されていて、
これを実行すると参照することのない9.1を葬れるんですが、本当に9.4に移行されているのか確認します。

[~]$ sudo netstat -tanp
稼働中のインターネット接続 (サーバと確立)
Proto 受信-Q 送信-Q 内部アドレス            外部アドレス            状態        PID/Program name
tcp        0      0 0.0.0.0:22              0.0.0.0:*               LISTEN      543/sshd
tcp        0      0 127.0.0.1:5432          0.0.0.0:*               LISTEN      21613/postgres
tcp        0      0 127.0.0.1:5433          0.0.0.0:*               LISTEN      21611/postgres

5432 と 5433でリッスンしているようです。たぶん9.1が5332、9.4が5433ですね。

psqlを使う前に接続できるよう認証設定を変更します。

`sudo vi /etc/postgresql/9.4/main/pg_hba.conf“ でhoge_user ユーザでの認証タイプをtrustとかpasswordとか適当なのにします。

[~]$ psql -U user -p 5433
psql (9.1.15, サーバー 9.4.2)
............
............

データベースがあるのを確認しました。

古い(9.1)を削除します

[/tmp]$ sudo -u postgres ./delete_old_cluster.sh

Railsアプリの動作確認をします

[/tmp]$ sudo /etc/init.d/antena_unicorn start

master failed to start, check stderr log for details

だめです( ;´Д`)

unicornのログ
==> /var/www/antena/current/log/unicorn.stderr.log <==
I, [2015-06-12T23:03:00.400994 #23689]  INFO -- : Refreshing Gem list
I, [2015-06-12T23:03:02.579895 #23689]  INFO -- : unlinking existing socket=/tmp/.antena.sock
I, [2015-06-12T23:03:02.580186 #23689]  INFO -- : listening on addr=/tmp/.antena.sock fd=12
E, [2015-06-12T23:03:02.583640 #23689] ERROR -- : could not connect to server: No such file or directory
        Is the server running locally and accepting
        connections on Unix domain socket "/var/run/postgresql/.s.PGSQL.5432"?
 (PG::Error)

9.4は5433で起動しているのだった( ;´Д`)
/etc/postgresql/9.4/main/postgresql.conf に書いているポートを5432に変更してrestartします。

ぺろぺろあんてなが動いた( ;´Д`)

使ってない9.1を削除する

[~]$ sudo apt-get purge postgresql-client-9.1 postgresql-9.1
パッケージリストを読み込んでいます... 完了
依存関係ツリーを作成しています
状態情報を読み取っています... 完了
以下のパッケージは「削除」されます:
  postgresql-9.1* postgresql-client-9.1*
アップグレード: 0 個、新規インストール: 0 個、削除: 2 個、保留: 0 個。
この操作後に 21.3 MB のディスク容量が解放されます。
続行しますか? [Y/n] y
(データベースを読み込んでいます ... 59582 files and directories currently installed.)
postgresql-9.1 (9.1.15-0+deb7u1) を削除しています ...
postgresql-9.1 (9.1.15-0+deb7u1) の設定ファイルを削除しています ...
Dropping cluster main...
warning: corrupted cluster: data directory does not exist
postgresql-client-9.1 (9.1.15-0+deb7u1) を削除しています ...
postgresql-common (168) のトリガを処理しています ...
Building PostgreSQL dictionaries from installed myspell/hunspell packages...
Removing obsolete dictionary files:

[~]$ psql -U postgres
psql (9.4.2)
"help" でヘルプを表示します.

postgres=# \q

変な汗出たしもうやりたくない気持ち( ;´Д`)

http://www.postgresql.org/docs/9.4/static/pgupgrade.html
http://lets.postgresql.jp/documents/technical/contrib/pg_upgrade
https://www.postgresql.jp/document/9.4/html/pgupgrade.html