暂无图片
暂无图片
2
暂无图片
暂无图片
暂无图片

记一次pg_wal目录膨胀异常分析

这几天,客户有一个postgresql数据库的数据目录增长量非常大,总共分配了2t,整个目录使用已经达到1.9t。
但是通过检查发现,在postgresql数据库实例中的最大数据库只有27g,剩余的均为几十兆,整个下来数据库的大小也就只有40-50g左右;

经过du -sh|sort -n对data目录分析,发现大部分的空间,都被pg_wal目录下的wal日志占用;
对pg_wal中的wal进行统计,发现该目录下的文件已经达到7w+

通过对wal参数查看:

max_wal_size=80gb
min_wal_size=80mb
checkpoint_timeout=1h
wal_keep_segments=1024

其中,max_wal_size为80gb,checkpoint_timeout=1h,是可能造成pg_wal大量生成的原因之一,因为默认情况下,在最初编译的时候,wal日志的大小默认为16m,通过pg_wal日志下对文件查看,确实每一个文件的大小为16m,而max_wal_size为80g的时候,可能会出现在进行checkpoint之间,如果出现大事物或者写入量非常大的时候,最大可能会生成(80*1024)/16=5120个wal文件。

但是适当调整后,发现由于事务量比较大,即使调小参数,还是会不断生成文件;

正常情况下,pg_wal目录在开启归档的状态下,会自动维护,除非归档失败,wal日志则会一直保持;所以,我们查看归档参数的配置:

archive_mode=on
archive_command=true

其中,archive_command=true表示,归档生效,但是不进行实际的归档动作;起初怀疑是由于没有实际的归档动作,导致postgresql认为当前无法进行归档。但是在archive_status文件中,所有的wal日志归档状态文件都显示了done,也就是说postgresql认为这些归档是成功的(虽然没有产生实际的归档动作);

此时,就排除了wal日志归档错误问题。

除此之外,还有两种可能,会造成pg_wal日志没有自动维护(或者说是强制保留,无法删除):
1.数据库中存在主备流复制环境,因为流复制环境中,主要就是靠wal日志进行主备同步,所以当主备环境之间的同步差异过大,或者出问题后,造成主备没有同步,则会保留wal日志不进行删除(此时,如果有差异的话,wal_keep_segments参数会生效,为备库保留1024个wal日志文件,但此时其实wal日志远远超过1024个)。
2.数据库中存在复制槽(物理或者逻辑),此时我们可以将wal日志想象为ogg中的队列文件或者消息队列中的消息。备库如果没有进行同步或者说没有消费wal日志,那么该复制槽不可用,wal日志也会一直保留,造成wal日志不断增加;

所以,我们下一步的重点排查就是上面两个方面:
1.查看该数据库是否存在主备流复制,且流复制目前是否正常:

select * from pg_stat_replication ;

 pid | usesysid | usename | application_name | client_addr | client_hostname | client_port | backend_start | backend_xmin | state | sent_lsn | write_lsn | flush_lsn | replay
_lsn | write_lag | flush_lag | replay_lag | sync_priority | sync_state | reply_time 
-----+----------+---------+------------------+-------------+-----------------+-------------+---------------+--------------+-------+----------+-----------+-----------+-------
-----+-----------+-----------+------------+---------------+------------+------------
(0 rows)

发现该数据库并没有备库环境。

2.查看复制槽:

postgres=# select * from pg_replication_slots;
      slot_name       | plugin | slot_type | datoid | database | temporary | active | active_pid | xmin | catalog_xmin | restart_lsn | confirmed_flush_lsn 
----------------------+--------+-----------+--------+----------+-----------+--------+------------+------+--------------+-------------+---------------------
 1_359822327485039616 |        | physical  |        |          | f         | f      |            |      |              | 0/CA000000  | 
(1 row)

可以发现在该数据库中果然存在一个物理复制槽,且该复制槽的active状态为f。

参考文档:https://zhuanlan.zhihu.com/p/166218704

至此,我们找到了pg_wal目录膨胀的问题,其实就是一个电信的因为复制槽导致pg_wal目录膨胀的问题。

接下来,我们删除该没有使用的复制槽:

SELECT * FROM pg_drop_replication_slot('1_359822327485039616');

删除后,发现pg_wal日志不再增长,过了一段时间,可以发现该目录空间已经释放:

df -h

Filesystem                    Size  Used Avail Use% Mounted on
devtmpfs                       63G     0   63G   0% /dev
tmpfs                          63G  832K   63G   1% /dev/shm
tmpfs                          63G  122M   63G   1% /run
tmpfs                          63G     0   63G   0% /sys/fs/cgroup
/dev/mapper/centos-lv_root     16G  1.9G   15G  12% /
/dev/sda1                    1014M  175M  840M  18% /boot
/dev/sda2                    1022M   12K 1022M   1% /boot/efi
/dev/mapper/centos-lv_var      16G  271M   16G   2% /var
/dev/mapper/centos-lv_home     16G   91M   16G   1% /home
tmpfs                          13G     0   13G   0% /run/user/0
tmpfs                          13G     0   13G   0% /run/user/1002
/dev/mapper/datavg-lv_app     500G   11G  489G   3% /app
/dev/mapper/datavg-lv_data01  2.0T  151G  1.9T   8% /data01
/dev/mapper/datavg-lv_data02  2.0T  152M  2.0T   1% /data02
/dev/mapper/datavg-lv_data03  2.0T  1.2T  901G  56% /data03
tmpfs                          13G     0   13G   0% /run/user/1000

pg_wal目录的文件已经被自动维护清理,剩余3000多个的文件:

ls|wc -l
3096
「喜欢这篇文章,您的关注和赞赏是给作者最好的鼓励」
关注作者
【版权声明】本文为墨天轮用户原创内容,转载时必须标注文章的来源(墨天轮),文章链接,文章作者等基本信息,否则作者和墨天轮有权追究责任。如果您发现墨天轮中有涉嫌抄袭或者侵权的内容,欢迎发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

评论