PostgreSQL attention : max_standby_archive_delay and max_standby_streaming_delay

今天群里的兄弟提到的一个疑问, 

max_standby_archive_delay = -1

max_standby_streaming_delay = -1

不知道有什么影响?

这两个参数控制了recovery时是否要kill掉hot_standby上与recovery冲突的sql.

如果配置为-1, 那么在hot_standby上可以无限时常的执行sql. 后果是standby只接收但是不recovery xlog. 造成standby xlog文件越来越多, 甚至撑爆磁盘分区. 还有就是造成了standby的延迟. 

所以在设置是需要小心.

为了便于理解, 下面将测试过程展示一下 : 

(primary and standby)安装PostgreSQL

tar -zxvf postgresql-1b1d3d9.tar.gz

cd postgresql-1b1d3d9
./configure --prefix=/home/pg94/pgsql9.4devel --with-pgport=2999 --with-perl --with-tcl --with-python --with-openssl --with-pam --without-ldap --with-libxml --with-libxslt --enable-thread-safety --with-wal-blocksize=16 --enable-dtrace && gmake && gmake install
cd contrib/
gmake && gmake install

(primary)初始化数据库

su - pg94
initdb -D $PGDATA -E UTF8 --locale=C -W -U postgres

(primary)配置

pg94@db-172-16-3-33-> grep "^[a-z]" postgresql.conf

listen_addresses = '0.0.0.0'            # what IP address(es) to listen on;
port = 2999                             # (change requires restart)
max_connections = 100                   # (change requires restart)
superuser_reserved_connections = 13     # (change requires restart)
unix_socket_directories = '.'   # comma-separated list of directories
unix_socket_permissions = 0700          # begin with 0 to use octal notation
shared_buffers = 1024MB                 # min 128kB
maintenance_work_mem = 512MB            # min 1MB
shared_preload_libraries = 'pg_stat_statements'         # (change requires restart)
wal_level = hot_standby                 # minimal, archive, or hot_standby
synchronous_commit = off                # synchronization level;
wal_sync_method = fdatasync             # the default is the first option
wal_buffers = 16384kB                   # min 32kB, -1 sets based on shared_buffers
wal_writer_delay = 20ms         # 1-10000 milliseconds
checkpoint_segments = 32                # in logfile segments, min 1, 16MB each
max_wal_senders = 32            # max number of walsender processes
wal_keep_segments = 128                # in logfile segments, 16MB each; 0 disables
hot_standby = on                        # "on" allows queries during recovery
max_standby_archive_delay = -1  # max delay before canceling queries
max_standby_streaming_delay = -1        # max delay before canceling queries
wal_receiver_status_interval = 1s       # send replies at least this often
hot_standby_feedback = on               # send info from standby to prevent
random_page_cost = 1.0                  # same scale as above
effective_cache_size = 10240MB
log_destination = 'csvlog'              # Valid values are combinations of
logging_collector = on          # Enable capturing of stderr and csvlog
log_directory = 'pg_log'                # directory where log files are written,
log_filename = 'postgresql-%Y-%m-%d_%H%M%S.log' # log file name pattern,
log_file_mode = 0600                    # creation mode for log files,
log_truncate_on_rotation = on           # If on, an existing log file with the
log_rotation_age = 1d                   # Automatic rotation of logfiles will
log_rotation_size = 10MB                # Automatic rotation of logfiles will
log_checkpoints = on
log_connections = on
log_disconnections = on
log_error_verbosity = verbose           # terse, default, or verbose messages
log_lock_waits = on                     # log lock waits >= deadlock_timeout
log_statement = 'ddl'                   # none, ddl, mod, all
log_timezone = 'PRC'
track_activity_query_size = 2048        # (change requires restart)
autovacuum = on                 # Enable autovacuum subprocess?  'on'
log_autovacuum_min_duration = 0 # -1 disables, 0 logs all actions and
datestyle = 'iso, mdy'
timezone = 'PRC'
lc_messages = 'C'                       # locale for system error message
lc_monetary = 'C'                       # locale for monetary formatting
lc_numeric = 'C'                        # locale for number formatting
lc_time = 'C'                           # locale for time formatting
default_text_search_config = 'pg_catalog.english'
pg_stat_statements.max = 1000
pg_stat_statements.track = all

pg94@db-172-16-3-33-> grep "^[a-z]" pg_hba.conf 

local   all             all                                     trust
host    all             all             127.0.0.1/32            trust
host    all             all             ::1/128                 trust
host all all 0.0.0.0/0 md5
host replication postgres 172.16.3.0/24 md5

pg94@db-172-16-3-33-> grep "^[a-z]" recovery.done 

recovery_target_timeline = 'latest'
standby_mode = on
primary_conninfo = 'host=172.16.3.39 port=2999 user=postgres keepalives_idle=60'                # e.g. 'host=localhost port=5432'

standby配置 : 

pg94@db-172-16-3-39-> vi ~/.pgpass
172.16.3.33:2999:replication:postgres:postgres
pg94@db-172-16-3-39-> chmod 400 ~/.pgpass
-- 复制节点
pg94@db-172-16-3-39-> pg_basebackup -D $PGDATA -F p -P -v -U postgres -h 172.16.3.33
pg94@db-172-16-3-39-> cd $PGDATA
pg94@db-172-16-3-39-> mv recovery.done recovery.conf
pg94@db-172-16-3-39-> vi recovery.conf
primary_conninfo = 'host=172.16.3.33 port=2999 user=postgres keepalives_idle=60'

启动standby : 

pg94@db-172-16-3-39-> pg_ctl start

(primary)创建测试表 : 

pg94@db-172-16-3-33-> psql postgres postgres
psql (9.4devel)
Type "help" for help.
postgres=# create database digoal;
CREATE DATABASE
\c digoal
digoal=# create table t1 (id int);
CREATE TABLE
digoal=# insert into t1 values (1);
INSERT 0 1

(standby)开启repeatable read查询

digoal=# begin transaction isolation level repeatable read;
BEGIN
digoal=# select * from t1;
 id
----
  1
(1 row)
-- 不要退出事务.

(primary)删除t1表.

删除t1表后, 这部分xlog信息在standby上面做恢复时将和standby上面的事务冲突.

digoal=# drop table t1;
DROP TABLE

查看standby的replay_location, 这个指的是恢复点.

digoal=# select * from pg_stat_replication ;
-[ RECORD 1 ]----+------------------------------
pid              | 5436
usesysid         | 10
usename          | postgres
application_name | walreceiver
client_addr      | 172.16.3.39
client_hostname  |
client_port      | 22422
backend_start    | 2013-08-15 12:36:18.844357+08
state            | streaming
sent_location    | 0/3012680
write_location   | 0/3012680
flush_location   | 0/3012680
replay_location  | 0/3012140
sync_priority    | 0
sync_state       | async

(primary)执行大量的写操作, 意为产生大量的pg_xlog.

digoal=# create table test(id int, info text, crt_time timestamp);
CREATE TABLE
digoal=# insert into test select generate_series(1,1000000),'test',now();
INSERT 0 1000000
digoal=# checkpoint;
CHECKPOINT

查询standby的replay_location, 这个指的是恢复点. 

从write_location看出, 数据在发给standby, 但是standby的replay_location不变. 也就是说现在standby只接收xlog, 但是没有将接收到的xlog做recovery处理.

因为在standby上设置了如下参数 :

max_standby_archive_delay = -1  # max delay before canceling queries
max_standby_streaming_delay = -1        # max delay before canceling queries

这个查询和recovery冲突时, 不会被kill掉, recovery将持续等待.

digoal=# select * from pg_stat_replication ;
-[ RECORD 1 ]----+------------------------------
pid              | 5436
usesysid         | 10
usename          | postgres
application_name | walreceiver
client_addr      | 172.16.3.39
client_hostname  |
client_port      | 22422
backend_start    | 2013-08-15 12:36:18.844357+08
state            | streaming
sent_location    | 0/8CA2BA0
write_location   | 0/8CA2BA0
flush_location   | 0/8CA2BA0
replay_location  | 0/3012140
sync_priority    | 0
sync_state       | async

(standby)开启另外一个会话, 查询是否存在test表.

显然不可能存在, 因为pg_xlog只接收, 却为recovery. 所以standby和primary延迟也随着时间越来越大.

pg94@db-172-16-3-39-> psql
psql (9.4devel)
Type "help" for help.
digoal=# \dt
        List of relations
 Schema | Name | Type  |  Owner
--------+------+-------+----------
 public | t1   | table | postgres
(1 row)

代码如下 : 

1. src/backend/storage/ipc/standby.c

/*
 * Determine the cutoff time at which we want to start canceling conflicting
 * transactions.  Returns zero (a time safely in the past) if we are willing
 * to wait forever.
 */
static TimestampTz
GetStandbyLimitTime(void)
{
        TimestampTz rtime;
        bool            fromStream;

        /*
         * The cutoff time is the last WAL data receipt time plus the appropriate
         * delay variable.  Delay of -1 means wait forever.
         */
        GetXLogReceiptTime(&rtime, &fromStream);
        if (fromStream)
        {
                if (max_standby_streaming_delay < 0)
                        return 0;                       /* wait forever */
                return TimestampTzPlusMilliseconds(rtime, max_standby_streaming_delay);
        }
        else
        {
                if (max_standby_archive_delay < 0)
                        return 0;                       /* wait forever */  // 小于0永久等待.
                return TimestampTzPlusMilliseconds(rtime, max_standby_archive_delay);
        }
}
时间: 2024-08-31 16:08:40

PostgreSQL attention : max_standby_archive_delay and max_standby_streaming_delay的相关文章

如何搭建阿里云RDS PostgreSQL数据库的物理备库

如何搭建阿里云RDS PostgreSQL数据库的物理备库 用户在阿里云购买了RDS PostgreSQL,如何在自己的机房或者ECS上建立备库?关于如何构建逻辑备库,在我以前的文章有详细的讲解,所谓逻辑备库,是可以跨版本,甚至仅仅同步一部分相同步的表的备库.https://yq.aliyun.com/articles/7240 如果用户需要构建一个和RDS PostgreSQL一模一样的备库,则可以通过流复制或者归档来完成. 步骤如下.1. 准备备库环境 安装64位Linux 安装与RDS P

PostgreSQL 9.0.2 Replication Best Practices

PostgreSQL的基于日志的数据库复制技术自8.2版本以来就已经有了,到了9.0更加的完善,standby库已经支持READ ONLY的模式提供用户使用. 1. 基于WAL文件恢复的数据库复制2. 基于stream的数据库复制在设计以上两中复制场景时,需要注意以下几点:1. 尽量使用类似的硬件和相同操作系统.    数据库复制的目的无外乎standby或提供查询用,硬件和primary节点差的太离谱当然不恰当的,所以为了安全,建议使用同等配置的硬件.2. 尽量使用相同的系统配置.    如相

PostgreSQL 10 流式物理、逻辑主从 最佳实践

标签 PostgreSQL , 流复制 , 主从 , 逻辑订阅 背景 流复制起源 PostgreSQL 自从2010年推出的9.0版本开始,支持流式物理复制,用户可以通过流式复制,构建只读备库(主备物理复制,块级别一致).流式物理复制可以做到极低的延迟(通常在1毫秒以内). 同步流复制 2011年推出的9.1版本,支持同步复制,当时只支持一个同步流复制备节点(例如配置了3个备,只有一个是同步模式的,其他都是异步模式). 在同步复制模式下,当用户提交事务时,需要等待这笔事务的WAL日志复制到同步流

PostgreSQL DaaS设计注意 - schema与database的抉择

PostgreSQL DaaS设计注意 - schema与database的抉择 作者 digoal 日期 2016-10-12 标签 PostgreSQL , DaaS , 模板 , schema , database , apply delay , standby 背景 市面上有一些提供DaaS服务的厂商,例如heroKu,可能有上百万的数据库服务: 又比如提供PaaS平台的服务商,数据库也会有很多,同事这些数据库可能也是模板化的,这些厂商并不一定是为每个客户都新建一个数据库集群来满足数据库

PostgreSQL物理&quot;备库&quot;的哪些操作或配置,可能影响&quot;主库&quot;的性能、垃圾回收、IO波动

标签 PostgreSQL , 物理复制 , 垃圾回收 , vacuum_defer_cleanup_age , hot_standby_feedback , max_standby_archive_delay , max_standby_streaming_delay 背景 PostgreSQL 物理备库的哪些配置,或者哪些操作,可能影响到主库呢? 首先,简单介绍一下PostgreSQL的物理备库,物理备库就是基于PostgreSQL WAL流式复制,实时恢复的备库.物理备库在物理层面与主库完

Pay attention: Oracle INTEGER is NUMBER(p) not INT4 in PostgreSQL

今天一位朋友问我Oracle转换到PostgreSQL时,Oracle的INT应该转换为PostgreSQL的什么类型? 差点被integer这个词迷惑,其实在Oracle中,integer使用NUMBER来存储的,只是不存储小数. 例如: SQL> set numwidth 50 SQL> create table test(id int); Table created. SQL> insert into test values (9999999999999999999); 1 row

PostgreSQL服务器管理:服务器配置

本文档为PostgreSQL 9.6.0文档,本转载已得到原译者彭煜玮授权. 1. 设置参数 1.1. 参数名称和值 所有参数名都是大小写不敏感的.每个参数都可以接受五种类型之一的值: 布尔.字符串.整数. 浮点数或枚举.该类型决定了设置该参数的语法: 布尔: 值可以被写成 on, off, true, false, yes, no, 1, 0 (都是大小写不敏感的)或者这些值的任何无歧义前缀. 字符串: 通常值被包括在单引号内,值内部的任何单引号都需要被双写.不过,如果值是一个简单数字或者 标

PostgreSQL pending patch : fail-back without fresh backup (have bug?)

[补充说明] 本文测试fail-back未成功的bug是-m immediate的一个bug, 已经修复 :  http://git.postgresql.org/gitweb/?p=postgresql.git;a=commit;h=91c3613d3748d881706c3e60d8221ea92833ac1a http://blog.163.com/digoal@126/blog/static/16387704020137894542352/ [正文] PostgreSQL的流复制应用非常

为PostgreSQL讨说法 - 浅析《UBER ENGINEERING SWITCHED FROM POSTGRES TO MYSQL》

背景 最近有一篇文档,在国外闹得沸沸扬扬,是关于UBER使用mysql替换postgres原因的文章. 英文原文https://eng.uber.com/mysql-migration/ 来自高可用架构的 中文翻译 文章涉及到 PG数据库的部分,背后的原理并没有深入的剖析,导致读者对PostgreSQL的误解 . uber在文章阐述的遇到的PG问题 We encountered many Postgres limitations: Inefficient architecture for wri