From 903e079ec1e80fb68aa165b23ab77820917d33b8 Mon Sep 17 00:00:00 2001 From: arthurprs Date: Wed, 6 Jun 2018 13:28:10 +0200 Subject: [PATCH] Add options for lock statement timeout --- bin/pg_repack.c | 13 +++++++++++-- doc/pg_repack.rst | 8 ++++++++ doc/pg_repack_jp.rst | 1 + 3 files changed, 20 insertions(+), 2 deletions(-) diff --git a/bin/pg_repack.c b/bin/pg_repack.c index 7793f619..f677ca64 100644 --- a/bin/pg_repack.c +++ b/bin/pg_repack.c @@ -255,6 +255,7 @@ static unsigned int temp_obj_num = 0; /* temporary objects counter */ static bool no_kill_backend = false; /* abandon when timed-out */ static bool no_superuser_check = false; static SimpleStringList exclude_extension_list = {NULL, NULL}; /* don't repack tables of these extensions */ +static int lock_wait_max = 1; /* Max lock statement timeout, in seconds */ /* buffer should have at least 11 bytes */ static char * @@ -284,6 +285,7 @@ static pgut_option options[] = { 'b', 'D', "no-kill-backend", &no_kill_backend }, { 'b', 'k', "no-superuser-check", &no_superuser_check }, { 'l', 'C', "exclude-extension", &exclude_extension_list }, + { 'i', 'L', "lock-wait-max", &lock_wait_max }, { 0 }, }; @@ -307,6 +309,12 @@ main(int argc, char *argv[]) if (dryrun) elog(INFO, "Dry run enabled, not executing repack"); + if (wait_timeout < lock_wait_max) + { + ereport(ERROR, (errcode(EINVAL), + errmsg("wait-timeout needs to be >= lock-wait-max"))); + } + if (r_index.head || only_indexes) { if (r_index.head && table_list.head) @@ -1673,7 +1681,7 @@ lock_access_share(PGconn *conn, Oid relid, const char *target_name) break; /* wait for a while to lock the table. */ - wait_msec = Min(1000, i * 100); + wait_msec = Min(lock_wait_max * 1000, Max(lock_wait_max * 1000 * i / 10, 100)); printfStringInfo(&sql, "SET LOCAL statement_timeout = %d", wait_msec); pgut_command(conn, sql.data, 0, NULL); @@ -1814,7 +1822,7 @@ lock_exclusive(PGconn *conn, const char *relid, const char *lock_query, bool sta } /* wait for a while to lock the table. */ - wait_msec = Min(1000, i * 100); + wait_msec = Min(lock_wait_max * 1000, Max(lock_wait_max * 1000 * i / 10, 100)); snprintf(sql, lengthof(sql), "SET LOCAL statement_timeout = %d", wait_msec); pgut_command(conn, sql, 0, NULL); @@ -2236,6 +2244,7 @@ pgut_help(bool details) printf(" -i, --index=INDEX move only the specified index\n"); printf(" -x, --only-indexes move only indexes of the specified table\n"); printf(" -T, --wait-timeout=SECS timeout to cancel other backends on conflict\n"); + printf(" -L, --lock-wait-max=SECS lock statement max wait time\n"); printf(" -D, --no-kill-backend don't kill other backends when timed out\n"); printf(" -Z, --no-analyze don't analyze at end\n"); printf(" -k, --no-superuser-check skip superuser checks in client\n"); diff --git a/doc/pg_repack.rst b/doc/pg_repack.rst index 9e26b24e..3b4a8dca 100644 --- a/doc/pg_repack.rst +++ b/doc/pg_repack.rst @@ -119,6 +119,7 @@ Options: -i, --index=INDEX move only the specified index -x, --only-indexes move only indexes of the specified table -T, --wait-timeout=SECS timeout to cancel other backends on conflict + -L, --lock-wait-max=SECS lock statement max wait time -D, --no-kill-backend don't kill other backends when timed out -Z, --no-analyze don't analyze at end -k, --no-superuser-check skip superuser checks in client @@ -206,6 +207,13 @@ Reorg Options disconnect any remaining backends after twice this timeout has passed. The default is 60 seconds. +``-L SECS``, ``--lock-wait-max=SECS`` + When pg_repack needs to take table locks (shared or exclusive) it'll wait + up to this many seconds before canceling the lock request and trying again. + This is done to allow concurrent queries to make progress and not get + queued up behind the pg_repack lock request. Consider increasing this + timeout if pg_repack fails to acquire table locks. The default is 1 second. + ``-D``, ``--no-kill-backend`` Skip to repack table if the lock cannot be taken for duration specified ``--wait-timeout``, instead of cancelling conflicting queries. The default diff --git a/doc/pg_repack_jp.rst b/doc/pg_repack_jp.rst index 4f5fac6f..b429c86f 100644 --- a/doc/pg_repack_jp.rst +++ b/doc/pg_repack_jp.rst @@ -207,6 +207,7 @@ pg_repackもしくはpg_reorgの古いバージョンからのアップグレー -i, --index=INDEX move only the specified index -x, --only-indexes move only indexes of the specified table -T, --wait-timeout=SECS timeout to cancel other backends on conflict + -L, --lock-wait-max=SECS lock statement max wait time -D, --no-kill-backend don't kill other backends when timed out -Z, --no-analyze don't analyze at end -k, --no-superuser-check skip superuser checks in client