9.3中文文档:http://58.58.27.50:8079/doc/html/9.3.1_zh/pgupgrade.html
9.4英文文档:http://www.postgresql.org/docs/9.4/static/pgupgrade.html
PostgreSQL自身有两种大版本升级(比如从pg9.2到pg9.4,可以跨一个或多个大版本)的方法:
1.通过pg_upgrede升级.(该方法对数据量较大时,速度更快)
2.先从老版本执行pg_dump,再到新版本执行pg_restore.(该方法在数据量较大时,速度较慢)
本文主要介绍使用pg_upgrade的方法、步骤以及相关的注意事项。
如果使用的是基于版本的安装目录,比如:/opt/PostgreSQL/9.1(一般是图形化安装包安装生成目录),那就不需要移动旧的数据库集簇目录,因为图形化安装包都是使用基于版本的安装目录的。
如果使用的不是基于版本的安装目录,比如:/usr/local/pgsql(一般是源码编译安装生成的目录),那最好移动这个数据库集簇的安装目录,否则的话会干扰新数据库的安装。一旦关闭了当前PostgreSQL的服务,那么重命名漆安装目录就会很安全。假设旧的安装目录为:/usr/local/pgsql,可以通过以下命令来重命名该目录:
mv /usr/local/pgsql /usr/local/pgsql.old
用兼容旧数据库集簇的configure 选项,来构建新的PostgreSQL。在开始升级之前,pg_upgrade 将会检查pg_controldata 来确保所有的设置都兼容。
安装新服务器的二进制可执行文件和支持文件。
用源码安装时,如果你想要在自定义目录安装新服务器,可以使用 prefix 变量:
gmake prefix=/usr/local/pgsql.new install
在新PostgreSQL的安装中,安装 pg_upgrade 二进制文件 and pg_upgrade_support库文件 。
通过initdb初始化新的集簇,并且,要用兼容旧数据库实例的initdb 选项。很多预构建安装会自动完成这一部。不需要启动新的数据库实例。
安装所有旧数据库集簇用到的自定义共享对象文件(或者是DLL文件)到新的数据库集簇中, 例如 pgcrypto.so, 无论他们来自 contrib 或者其它的源。 不需要安装一类模式的定义, 例如pgcrypto.sql, 因为这些也会从旧数据库实例中升级。还有,所有旧数据库集簇中自定义的全文本搜索文件(dictionary, synonym, thesaurus, stop words) 必须拷贝到新的数据库集簇中。
pg_upgrade 会数次连到新、旧数据库实例,所以可以修改 pg_hba.conf的认证设置成 trust 或者是 peer ,或者,也可以使用 md5 的认证方式同时使用~/.pgpass密码文件 (参考 Section 31.15).
要确保新、旧数据库都停止服务,在linux下:
pg_ctl -D /opt/PostgreSQL/8.4 stoppg_ctl -D /opt/PostgreSQL/9.0 stop
或者在windows下,使用相应的服务名称:
NET STOP postgresql-8.4NET STOP postgresql-9.0
或
NET STOP pgsql-8.3 (PostgreSQL 8.3以及更早的版本使用了像这样的,有所不同的服务名称)
总是执行新数据库的pg_upgrade二进制执行文件,而不是旧数据库的。
pg_upgrade 需要指定新旧数据库实例的数据目录和可执行的 (bin) 目录。 当然你还可以指定用户和端口,以及指定是否使用数据硬链接代替使用数据复制(默认方式)。
如果使用链接模式,升级将会非常快(没有文件拷贝)并且占用更少的硬盘,但是你不能再访问你的旧数据库当你升级完成启动新的数据库实例。 链接模式还需要新旧数据库 数据目录使用相同的文件系统。(表空间和 pg_xlog 可以在不同的文件系统。) 参考 pg_upgrade --help 查看完整的帮助选项列表。
如果你修改了pg_hba.conf, 那么还原那些修改的设置. 还有可能需要去调整其它的配置文件去和旧的数据库 实例相匹配,例如:postgresql.conf.
如果有升级后续操作需要执行,pg_upgrade会在完成后发布出警告信息。 同时它会生成必须由管理员运行的脚本文件。 脚本会连到需要执行升级后续操作的新旧数据库。 脚本可以用下面命令执行:
psql --username postgres --file script.sql postgres
脚本可以任意顺序执行,执行完后可以被删除。
Caution:通常情况下在重建脚本运行结束之前不允许访问被引用的表;这样做可能会出现 意想不到的错误结果或者是性能不佳 。不引用的表可以被立限访问。
因为优化统计结果不会被pg_upgrade传递, 你需要指定去运行命令去在升级 完成后生成一些新的信息。你可能需要设置连接参数去匹配新的数据库实例。
设备:一个centos6.3 32bit虚拟机
原数据库PG9.3,端口5432,安装目录:/opt/PostgreSQL/9.3/
新数据库PG9.4 ,端口5434,源码编译安装目录:/opt/pgsql944/
到官网下载pg9.4.4的源码安装包:postgresql-9.4.4.tar.gz
su - root
解压
tar jxvf postgresql-9.4.4.tar.gz
编译
cd postgresql-9.4.4 ./configure --prefix=/opt/pgsql944 --with-pgport=5434
安装
gmake world gmake install -world
安装pg_upgrade客户端程序
cd contrib gamke gmake install
注意:编译安装过程中提示缺包错误的处理思路:http://www.linuxidc.com/Linux/2012-02/53982.htm,如:
1.报错
configure: error: readline library notfound If you have readline already installed, see config.log for detailson the failure. It is possible the compiler isnt lookingin the proper directory. Use --without-readline to disable readlinesupport.
2.首先查找readline包
[[email protected]]# rpm -qa | grep readline readline-5.1-3.el5
说明系统已经安装了 readline包。
3.通过 yum 搜索相关的readline 包
[[email protected]]# yum search readline lftp.i386 : A sophisticated file transfer program lftp.i386 : A sophisticated file transfer program php-readline.i386 : Standard PHP module provides readline librarysupport lftp.i386 : A sophisticated file transfer program readline.i386 : A library for editing typed commandlines. compat-readline43.i386 : The readline 4.3 library for compatibilitywith older software. readline-devel.i386 : Files needed to develop programs which usethe readline library. readline.i386 : A library for editing typed command lines.
根据提示,有一个包引起了我的注意 "readline-devel",猜想可能与这个包有关。
4安装 readline-devel 包
[[email protected]]# yum -y install -y readline-devel
5.继续进行原来的操作即可
在安装目录下创建一个data目录
cd /opt/pgsql944 mkdir data2
新建系统用户postgres(并创建home目录),并添加密码:
useradd -m postgres passwd postgres
将data目录授权给postgres
chown postgres data2
切换到postgres用户下
su - postgres
来到bin目录下
cd .. cd bin
初始化数据库,注意locale的设置要与原数据库的设置兼容,一般用C即可兼容大部分.
./initdb -D ../data2 --locale=C -U postgres
The files belonging to this database system will be owned by user "postgres". This user must also own the server process. The database cluster will be initialized with locale "en_US.UTF-8". The default database encoding has accordingly been set to "UTF8". The default text search configuration will be set to "english". Data page checksums are disabled.fixing permissions on existing directory ../data3 ... ok creating subdirectories ... ok selecting default max_connections ... 100 selecting default shared_buffers ... 128MB selecting dynamic shared memory implementation ... posix creating configuration files ... ok creating template1 database in ../data3/base/1 ... ok initializing pg_authid ... ok initializing dependencies ... ok creating system views ... ok loading system objects' descriptions ... ok creating collations ... ok creating conversions ... ok creating dictionaries ... ok setting privileges on built-in objects ... ok creating information schema ... ok loading PL/pgSQL server-side language ... ok vacuuming database template1 ... ok copying template1 to template0 ... ok copying template1 to postgres ... ok syncing data to disk ... ok WARNING: enabling "trust" authentication for local connections You can change this by editing pg_hba.conf or using the option -A, or--auth-local and --auth-host, the next time you run initdb. Success. You can now start the database server using: ./postgres -D ../data2 or ./pg_ctl -D ../data2 -l logfile start
此时新的PG9.4已安装成功,可以尝试启动服务并登陆。
# "local" is for Unix domain socket connections only local all postgres trust
分别执行
/opt/PostgreSQL/9.3/bin/pg_ctl stop -D ../data /opt/pgsql944/bin/pg_ctl stop -D ../data2
执行pg_upgrade,会在当前目录生成日志,所以该命令执行时的当前目录,必须是postgres有权限的目录(可以用root创建一个目录,授权给postgres之后,到那个目录下去执行,最好不要去data目录下,因为升级过程汇总data目录下的文件可能会被改变),否则无法写日志,导致命令执行失败。
cannot write to log file pg_upgrade_internal.logFailure, exiting
所以我们先创建目录如下:
su - rootcd /opt/pg944mkdir upgradechown postgressu - postgrescd /opt/pg944/upgrade
首先进行使用-c命令进行检查(可以通过pg_upgrade --help查看相关命令选项的含义):
/opt/pgsql944/bin/pg_upgrade -c -b /opt/PostgreSQL/9.3/bin -B /opt/pgsql944/bin -d /opt/PostgreSQL/9.3/data -D /opt/pgsql944/data -p 5432 -P 5434
/opt/pgsql944/bin/pg_upgrade -c -b /opt/PostgreSQL/9.3/bin -B /opt/pgsql944/bin -d /opt/PostgreSQL/9.3/data -D /opt/pgsql944/data2 -p 5432 -P 5434 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 *Clusters are compatible*
pg_upgrade有两种升级方式,一个是缺省的通过拷贝数据文件到新的data目录下,一个是创建硬链接。拷贝的方式升级较慢,但是原库还可用;硬链接的方式升级较快,但是原库不可用。
缺省拷贝方式升级的命令:(硬链接方式升级的命令只需要添加--link)
/opt/pgsql944/bin/pg_upgrade -b /opt/PostgreSQL/9.3/bin -B /opt/pgsql944/bin -d /opt/PostgreSQL/9.3/data -D /opt/pgsql944/data -p 5432 -P 5434
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 thenew 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 Copying old pg_multixact/offsets to new server ok Deleting files from new pg_multixact/members ok Copying old pg_multixact/members to new server ok Setting next multixact ID and offset for 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 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
启动PG9.4并查看数据库内容,能看到升级成功,数据已经从pg9.3移植到9.4.
-bash-4.1$./pg_ctl start -D ../data2 -bash-4.1$ ./psqlpsql (9.4.4) Type "help" for help. postgres=# show port; port ------ 5432 (1 row) postgres=# select version(); version ----------------------------------------------------------------------------------------------------- PostgreSQL 9.4.4 on i686-pc-linux-gnu, compiled by gcc (GCC) 4.4.7 20120313 (Red Hat 4.4.7-11), 32-bit(1 row) postgres=# \l List of databases Name | Owner | Encoding | Collate | Ctype | Access privileges ----------+----------+----------+-------------+-------------+----------------------- postgres | postgres | UTF8 | en_US.UTF-8 | en_US.UTF-8 | template0 | postgres | UTF8 | en_US.UTF-8 | en_US.UTF-8 | =c/postgres+ | postgres=CTc/postgres template1 | postgres | UTF8 | en_US.UTF-8 | en_US.UTF-8 | postgres=CTc/postgres+ | =c/postgres (3 rows) postgres=# \d List of relations Schema | Name | Type | Owner --------+------+-------+---------- public | lyy | table | postgres (1 row) postgres=# select * from lyy; id | name ----+------ 1 | lily 2 | lucy (2 rows)
Optimizer statistics are not transferred by pg_upgrade so,once you start the new server, consider running: analyze_new_cluster.shRunning this script will delete the old cluster's data files: delete_old_cluster.sh
配置pg9.4的pg_hba.conf为应用实际需要的情况。
配置pg9.4的postgresql.conf,使其还原pg9.3中的设置,或者做其他实用的配置。
本案例仅作pg_upgrade的执行示例,实际应用中请自行做相应的调整。