pgbench 简介:
pgbench是一种在PostgreSQL上运行基准测试的简单程序。它可能在并发的数据库会话中一遍一遍地运行相同序列的 SQL 命令,并且计算平均事务率(每秒的事务数)。默认情况下,pgbench会测试一种基于 TPC-B 但是要更宽松的场景,其中在每个事务中涉及五个SELECT、UPDATE以及INSERT命令。但是,通过编写自己的事务脚本文件很容易用来测试其他情况。
使用方法
pgbench [OPTION]... [DBNAME]
初始化选项
-i, --initialize 调用初始化模式
-F, --fillfactor=NUM 设置填充因数
-n, --no-vacuum 初始化后不运行vacuum
-q, --quiet 安静模式
-s, --scale=NUM 比例因子
标准选项
-c, --client=NUM 数据库客户端并发数量(默认值:1)
-C, --connect 为每个事务建立新的连接
-D, --define=VARNAME=VALUE 定义自定义脚本使用的变量
-f, --file=FILENAME 从文件名中读取事务脚本
-j, --jobs=NUM 线程数(默认为1)
-l, --log 写入日志文件
-L, --latency-limit=NUM 将持续时间超过毫秒(ms)的事务算作延迟
-M, --protocol=simple|extended|prepared 提交查询的协议(默认:simple)
-n, --no-vacuum 测试前不要运行vacuum
-N, --skip-some-updates 跳过pgbench_tellers和pgbench_branches的更新
-P, --progress=NUM 每隔指定秒显示线程进度报告
-r, --report-latencies 报告每个命令的平均延迟
-R, --rate=NUM 每秒事务的目标速率
-s, --scale=NUM 在输出中报告这个比例因子
-S, --select-only 执行只读查询
-t, --transactions=NUM 每个客户端运行的事务数(默认为10)
-T, --time=NUM 基准测试持续时间(秒)
-v, --vacuum-all 测试前vacuum全部4张标准表
硬件环境
数量
3台服务器
型号
华为2488H V5
CPU
4*16核 Intel Xeon 6130 2.10GHz
存储
2*480GB SSD 、22*1.2T SAS
内存
1T(33*32 GB) 2666MHz DDR4
网口
2块双口千兆、2块双口万兆以太网卡
Linux发行版
Red Hat Enterprise Linux Server release 7.5
Linux内核
3.10.0-862.el7.x86_64
环境配置
GP版本
Greenplum6.2.1
Greenplum5.20
内核版本
PostgreSQL 9.4.24
PostgreSQL 8.3.23
环境配置
Master:mas01 Segment:mas01、mas02、seg08
集群参数设置
Greenplum6
gpconfig -c 'optimizer' -v off
gpconfig -c 'gp_enable_global_deadlock_detector' -v on
gpconfig -c 'resource_scheduler' -v off
gpconfig -c log_statement -v none
gpconfig -c checkpoint_segments -v 2 --skipvalidation
Greenplum5
gpconfig -c 'optimizer' -v off
gpconfig -c 'resource_scheduler' -v off
gpconfig -c log_statement -v none
gpconfig -c checkpoint_segments -v 2 --skipvalidation
参数说明
gp_enable_global_deadlock_detector
此GUC用于控制是否开启全局死锁检测功能,在Greenplum 6中其默认关闭,需要打开它才可以支持并发更新/删除操作;Greenplum 5并不支持此GUC。
log_statement
此GUC减少不必要的日志,避免日志输出对I/O性能的干扰。
checkpoint_segments
此GUC影响checkpoint主动刷盘的频率,默认值8会降低刷盘频率,但是每次刷盘的数据量较大,导致整个集群瞬时的性能下降。针对OLTP大量更新类语句适当调小此设置会增加刷盘频率,但由于每次刷盘数据量变小,平均性能会有较明显提升;Greenplum 5支持此GUC但是并无明显效果,这是由于Greenplum 5的性能瓶颈并不在于I/O,而是在表锁导致的串行化。
测试方法
数据库建立test库,采用pgbench进行,数据规模为1000倍,持续60秒进行测试。
- 初始化命令
pgbench -h mas01 -U gpadmin6 -p 6666 -i -s 1000 test
- 基准测试命令
pgbench -h mas01 -U $user -p $port -c $N -T 60 -r test
- 单查询测试命令
pgbench -h mas01 -U $user -p $port -c $N -S -T 60 -r test
- 单更新测试命令
pgbench -h mas01 -U $user -p $port -c $N -S -T 60 -r test -f update.sql
# vi update.sql
\set naccounts 100000 * :scale
\setrandom aid 1 :naccounts
\setrandom delta -5000 5000
BEGIN;
UPDATE pgbench_accounts SET abalance = abalance + :delta WHERE aid = :aid;
END;
- 单插入测试命令
pgbench -h mas01 -U $user -p $port -c $N -S -T 60 -r test -f insert.sql
# vi insert.sql
\set nbranches 1 * :scale
\set ntellers 10 * :scale
\set naccounts 100000 * :scale
\setrandom aid 1 :naccounts
\setrandom bid 1 :nbranches
\setrandom tid 1 :ntellers
\setrandom delta -5000 5000
BEGIN;
INSERT INTO pgbench_history (tid, bid, aid, delta, mtime) VALUES (:tid, :bid, :aid, :delta, CURRENT_TIMESTAMP);
END;
总结
执行过程中观察到Greenplum 5在涉及更新时,有大量的锁情况,有单查询和单插入时,因为两段事务的原因,没有及时commit导致lwlock(系统共享资源锁)的冲突,而Greenplum 6引入了全局死锁检测功能从而支持了HEAP表数据表的并发更新,解决了这个问题,在并发更新测试时master上的lwlock没有,节点上的lwlock有但很少总和才几个,因此性能大大提高。
如果是ao表会是怎样的情况?接着把表pgbench_accounts修改成ao表,再进行测试:
test=# create table pgbench_accounts_ao(like pgbench_accounts)WITH (appendonly=true,compresstype=zlib,COMPRESSLEVEL=5);
test=# insert into pgbench_accounts_ao select * from pgbench_accounts;
test=# alter table pgbench_accounts rename to pgbench_accounts_bak;
test=# alter table pgbench_accounts_ao rename to pgbench_accounts;
test=# vacuum analyze pgbench_accounts;
果然对ao表的更新有问题,观察到只有一个进程在跑,其它都在等待锁。
对ao表进行插入并发测试:
create table pgbench_history_ao(like pgbench_history)WITH (appendonly=true,compresstype=zlib,COMPRESSLEVEL=5);
insert into pgbench_history_ao select * from pgbench_history;
alter table pgbench_history rename to pgbench_history_bak;
alter table pgbench_history_ao rename to pgbench_history;
vacuum analyze pgbench_history;
性能下降很明显,ao表是不适合频繁的插入。
对ao表进行查询并发测试:
同样TPS也是很低,看来GP6的OLTP提升只是对heap表起作用。
接着我们对Greenplum6的参数进行优化,以TPC-B基准测试为例,并以CPU的核数64为并发数来进行调整
1、Greenplum6和5的对比没有开启线程,是为了减少Greenplum5不受pgbench线程参数的影响,现在调整pgbench命令,开启线程 –j 参数,采用值16。
测试命令
pgbench -h mas01 -U gpadmin6 -p 6666 -c 64 -j 16 -T 30 -r test
测试结果
2、调整共享内存参数shared_buffers,存储共享数据至内存。
gpconfig -c shared_buffers -v '2GB'
测试结果
3、调整事务提交参数,不强制将 WAL写入磁盘,只需写到缓存中就会向客户端返回提交成功,延迟wal_writer_delay*3毫秒写入磁盘,可提升TPS但会有事务丢失风险。
gpconfig -c synchronous_commit -v off
测试结果
4、关闭持久化调用,不强制刷新数据到磁盘,在断电或者系统出现问题时有数据丢失的风险。
gpconfig -c fsync -v 'off' –skipvalidation
测试结果
在之前对比测试命令基础上,加上-j $N参数开启线程,并在当前参数设置下测试Greenplum6的性能结果
RT(平均响应时间),单位毫秒
基准测试测试结果截图
在之前测试命令基础上,加上-j $N参数开启线程,并在当前参数设置下测试结果
基准测试测试结果截图
单查询测试结果截图
单更新测试结果截图
单插入测试结果截图
作者简介叶健锋,MPP数据库研发管理
坐标广州,2012年开始学习使用Greenplum至今,熟练数据库的规划部署、SQL开发及调优、ETL数据加载,数据库运维和性能调优等工作。