Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1lNkti-0006ks-9v for pgsql-hackers@arkaria.postgresql.org; Sat, 20 Mar 2021 23:20:46 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.92) (envelope-from ) id 1lNkth-0006sV-8t for pgsql-hackers@arkaria.postgresql.org; Sat, 20 Mar 2021 23:20:45 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1lNktg-0006sN-Vc for pgsql-hackers@lists.postgresql.org; Sat, 20 Mar 2021 23:20:45 +0000 Received: from mail-io1-xd2b.google.com ([2607:f8b0:4864:20::d2b]) by magus.postgresql.org with esmtps (TLS1.3:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.92) (envelope-from ) id 1lNktf-00041B-2W for pgsql-hackers@lists.postgresql.org; Sat, 20 Mar 2021 23:20:44 +0000 Received: by mail-io1-xd2b.google.com with SMTP id z136so10053395iof.10 for ; Sat, 20 Mar 2021 16:20:42 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=telsasoft-com.20150623.gappssmtp.com; s=20150623; h=date:from:to:cc:subject:message-id:references:mime-version :content-disposition:content-transfer-encoding:in-reply-to :user-agent; bh=S233LZsmjntRvTsv/UWaapA01elRCs42o1qOlCf1FPo=; b=PfvblQyGFeh/UW+B8Dxi2xymByXzZbR/VisRaZFzb4qLBfHSBzSdkMhnUnhX+sQrJv J1/QGgx2LS6Yl9IPBdcpUd0U946EPhsTreuEiyjFBUsFq+LqqQRfDK1bZVwPY6u5hV9D yi1ZiWhhwV4hwrdRgYn5KaDaamQCjpj1l3FWExcMrRqVPZPsPC/c4OOYk4JxhrvKbQJa fpezZerGQK0NgbkEMD81LPEnasv1ptFQd0vWFSyHtnymlKTjPGIE+G4Cr/XmWsgPmLhf EVeswClCbAkdgU6cNd5K4hROOBDweON/b35kNigCxumEf3ALdg32Ef7R8IlabiGkZ0GZ KKeA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:date:from:to:cc:subject:message-id:references :mime-version:content-disposition:content-transfer-encoding :in-reply-to:user-agent; bh=S233LZsmjntRvTsv/UWaapA01elRCs42o1qOlCf1FPo=; b=R4PPShxO4MW0qoq5m9hYqRLdS4LdNCxs30HmY+Lmbk/bcqn/bV7U2OTZhGgPLTLPao SbADY1opOFZE8bKVqxCxCRWFKV3ZzPK3Ahoc8JHsbXTPWmMMbmnLC0YhDoVA2RDiYLlY XW42KY9EoLcHEwVzyWrPxnyO2zjrGbSxkT90Hd0cMmLi0/Np5FZ8QjvKyX1cuGYW3krE aSS0xM+NtVYl89x1sPj23COyMC93Ooa0WarWurhxsVscEZfu/Vs/po8Kls4TGp0RuApY SPPRwMxU3qhCo7WaSwHQjqqDPQ/AanIhOSGi4roP+mtY+xbm7sAhyYHIlgHMPDvHP6te lcIQ== X-Gm-Message-State: AOAM533DYWTGDJqdFHDxBlrMXVZmTC2YbgSvA8AWtHtyyo/n4o74OKJr jbtxFHXihwNp9rf8BtJJglPUVg== X-Google-Smtp-Source: ABdhPJyHKVSlmiTN55DS45hElYZ9nUrvoR/RrWKatwPYxKqcbFCFl+jSDmKJx4oilychJBdXJU8PaA== X-Received: by 2002:a02:3304:: with SMTP id c4mr6293401jae.68.1616282441696; Sat, 20 Mar 2021 16:20:41 -0700 (PDT) Received: from pryzbyj.telsasoft (charmander.telsasoft.com. [50.244.222.1]) by smtp.gmail.com with ESMTPSA id o19sm5019775ioh.47.2021.03.20.16.20.40 (version=TLS1_2 cipher=ECDHE-ECDSA-AES128-GCM-SHA256 bits=128/128); Sat, 20 Mar 2021 16:20:40 -0700 (PDT) Received: by pryzbyj.telsasoft (Postfix, from userid 1000) id BF4C380083D; Sat, 20 Mar 2021 18:20:39 -0500 (CDT) Date: Sat, 20 Mar 2021 18:20:39 -0500 From: Justin Pryzby To: Tom Lane , Robert Haas , Alvaro Herrera Cc: Dilip Kumar , Andres Freund , Tomas Vondra , Alexander Korotkov , David Steele , Ildus Kurbangaliev , Dmitry Dolgov <9erthalion6@gmail.com>, pgsql-hackers@lists.postgresql.org Subject: Re: [HACKERS] Custom compression methods Message-ID: <20210320232039.GY11765@telsasoft.com> References: <20210319222242.GA23930@alvherre.pgsql> <4158590.1616185209@sss.pgh.pa.us> <20210320000625.GP11765@telsasoft.com> <20210320074420.GR11765@telsasoft.com> MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="poemUeGtc2GQvHuH" Content-Disposition: inline Content-Transfer-Encoding: 8bit In-Reply-To: <20210320074420.GR11765@telsasoft.com> User-Agent: Mutt/1.9.4 (2018-02-28) List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Archived-At: Precedence: bulk --poemUeGtc2GQvHuH Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Rebased on HEAD. 0005 forgot to update compression_1.out. Included changes to ./configure.ac and some other patches, but not Tomas's, since it'll make CFBOT get mad as soon as that's pushed. -- Justin --poemUeGtc2GQvHuH Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v2-0001-Add-docs-for-default_toast_compression.patch" From bf1336d284792b29e30b42af2ec820bb0c256916 Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Fri, 19 Mar 2021 19:12:53 -0500 Subject: [PATCH v2 01/10] Add docs for default_toast_compression.. bbe0a81db69bd10bd166907c3701492a29aca294 --- doc/src/sgml/config.sgml | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml index ee4925d6d9..5cb851a5eb 100644 --- a/doc/src/sgml/config.sgml +++ b/doc/src/sgml/config.sgml @@ -8151,6 +8151,29 @@ COPY postgres_log FROM '/full/path/to/logfile.csv' WITH csv; + + default_toast_compression (string) + + default_toast_compression configuration parameter + + + + + This parameter specifies the default compression method to use + when compressing data in TOAST tables. + It applies only to variable-width data types. + It may be overriden by compression clauses in the + CREATE command, or changed after the relation is + created by ALTER TABLE ... SET COMPRESSION. + + The supported compression methods are pglz and + (if configured at the time PostgreSQL was + built) lz4. + The default is pglz. + + + + temp_tablespaces (string) -- 2.17.0 --poemUeGtc2GQvHuH Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v2-0002-doc-pg_dump-no-toast-compression.patch" From 3184c87f129ec935fa46773728869c7c6af88025 Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Fri, 19 Mar 2021 21:52:28 -0500 Subject: [PATCH v2 02/10] doc: pg_dump --no-toast-compression --- doc/src/sgml/ref/pg_dump.sgml | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/doc/src/sgml/ref/pg_dump.sgml b/doc/src/sgml/ref/pg_dump.sgml index bcbb7a25fb..4a521186fb 100644 --- a/doc/src/sgml/ref/pg_dump.sgml +++ b/doc/src/sgml/ref/pg_dump.sgml @@ -931,6 +931,18 @@ PostgreSQL documentation + + + + + Do not output commands to set TOASTcompression + methods. + With this option, all objects will be created using whichever + compression method is the default during restore. + + + + -- 2.17.0 --poemUeGtc2GQvHuH Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v2-0003-Compression-method-is-an-char-not-an-OID.patch" From 2212020a50478c66a830f15b23c3410e4d7bb501 Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Fri, 19 Mar 2021 20:23:40 -0500 Subject: [PATCH v2 03/10] Compression method is an char not an OID --- src/backend/commands/tablecmds.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/src/backend/commands/tablecmds.c b/src/backend/commands/tablecmds.c index 9b2800bf5e..8e756e59d5 100644 --- a/src/backend/commands/tablecmds.c +++ b/src/backend/commands/tablecmds.c @@ -7847,6 +7847,7 @@ SetIndexStorageProperties(Relation rel, Relation attrelation, index_close(indrel, lockmode); } } + /* * ALTER TABLE ALTER COLUMN SET STORAGE * @@ -15070,7 +15071,7 @@ ATExecSetCompression(AlteredTableInfo *tab, AttrNumber attnum; char *compression; char typstorage; - Oid cmoid; + char cmethod; Datum values[Natts_pg_attribute]; bool nulls[Natts_pg_attribute]; bool replace[Natts_pg_attribute]; @@ -15111,9 +15112,9 @@ ATExecSetCompression(AlteredTableInfo *tab, memset(replace, false, sizeof(replace)); /* get the attribute compression method. */ - cmoid = GetAttributeCompression(atttableform, compression); + cmethod = GetAttributeCompression(atttableform, compression); - atttableform->attcompression = cmoid; + atttableform->attcompression = cmethod; CatalogTupleUpdate(attrel, &tuple->t_self, tuple); InvokeObjectPostAlterHook(RelationRelationId, @@ -15123,7 +15124,7 @@ ATExecSetCompression(AlteredTableInfo *tab, ReleaseSysCache(tuple); /* apply changes to the index column as well */ - SetIndexStorageProperties(rel, attrel, attnum, cmoid, '\0', lockmode); + SetIndexStorageProperties(rel, attrel, attnum, cmethod, '\0', lockmode); table_close(attrel, RowExclusiveLock); /* make changes visible */ -- 2.17.0 --poemUeGtc2GQvHuH Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v2-0004-Remove-duplicative-macro.patch" From d73643d7569ef74b9008d232f8c0ea33cb96ff3c Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Fri, 19 Mar 2021 20:07:31 -0500 Subject: [PATCH v2 04/10] Remove duplicative macro --- src/include/access/toast_compression.h | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/include/access/toast_compression.h b/src/include/access/toast_compression.h index 514df0bed1..09af6e7810 100644 --- a/src/include/access/toast_compression.h +++ b/src/include/access/toast_compression.h @@ -50,8 +50,6 @@ typedef enum ToastCompressionId errdetail("This functionality requires the server to be built with lz4 support."), \ errhint("You need to rebuild PostgreSQL using --with-lz4."))) -#define IsValidCompression(cm) ((cm) != InvalidCompressionMethod) - #define IsStorageCompressible(storage) ((storage) != TYPSTORAGE_PLAIN && \ (storage) != TYPSTORAGE_EXTERNAL) -- 2.17.0 --poemUeGtc2GQvHuH Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v2-0005-Error-on-invalid-compression-in-CREATE-and-ALTER.patch" From 79e6dd441a0624f611ee1f7ee037285feccda426 Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Fri, 19 Mar 2021 20:19:55 -0500 Subject: [PATCH v2 05/10] Error on invalid compression in CREATE and ALTER --- src/backend/commands/tablecmds.c | 10 +++++++--- src/test/regress/expected/compression.out | 6 ++++++ src/test/regress/expected/compression_1.out | 6 ++++++ src/test/regress/sql/compression.sql | 5 +++++ 4 files changed, 24 insertions(+), 3 deletions(-) diff --git a/src/backend/commands/tablecmds.c b/src/backend/commands/tablecmds.c index 8e756e59d5..7efe27ac6c 100644 --- a/src/backend/commands/tablecmds.c +++ b/src/backend/commands/tablecmds.c @@ -17865,9 +17865,13 @@ GetAttributeCompression(Form_pg_attribute att, char *compression) /* fallback to default compression if it's not specified */ if (compression == NULL) - cmethod = GetDefaultToastCompression(); - else - cmethod = CompressionNameToMethod(compression); + return GetDefaultToastCompression(); + + cmethod = CompressionNameToMethod(compression); + if (!CompressionMethodIsValid(cmethod)) + ereport(ERROR, + (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), + errmsg("invalid compression method \"%s\"", compression))); return cmethod; } diff --git a/src/test/regress/expected/compression.out b/src/test/regress/expected/compression.out index 3de2886de0..501e0ead14 100644 --- a/src/test/regress/expected/compression.out +++ b/src/test/regress/expected/compression.out @@ -344,4 +344,10 @@ SELECT length(f1) FROM cmmove3; 10040 (2 rows) +CREATE TABLE t (a text COMPRESSION I_Do_Not_Exist_Compression); -- fails +ERROR: invalid compression method "i_do_not_exist_compression" +CREATE TABLE t (a text); +ALTER TABLE t ALTER a SET COMPRESSION I_Do_Not_Exist_Compression; -- fails +ERROR: invalid compression method "i_do_not_exist_compression" +DROP TABLE t; \set HIDE_TOAST_COMPRESSION true diff --git a/src/test/regress/expected/compression_1.out b/src/test/regress/expected/compression_1.out index 40aad81fa1..2a704e9b14 100644 --- a/src/test/regress/expected/compression_1.out +++ b/src/test/regress/expected/compression_1.out @@ -337,4 +337,10 @@ SELECT length(f1) FROM cmmove3; 10000 (1 row) +CREATE TABLE t (a text COMPRESSION I_Do_Not_Exist_Compression); -- fails +ERROR: invalid compression method "i_do_not_exist_compression" +CREATE TABLE t (a text); +ALTER TABLE t ALTER a SET COMPRESSION I_Do_Not_Exist_Compression; -- fails +ERROR: invalid compression method "i_do_not_exist_compression" +DROP TABLE t; \set HIDE_TOAST_COMPRESSION true diff --git a/src/test/regress/sql/compression.sql b/src/test/regress/sql/compression.sql index d97e26b6ee..afddd5a134 100644 --- a/src/test/regress/sql/compression.sql +++ b/src/test/regress/sql/compression.sql @@ -133,4 +133,9 @@ SELECT length(f1) FROM cmmove1; SELECT length(f1) FROM cmmove2; SELECT length(f1) FROM cmmove3; +CREATE TABLE t (a text COMPRESSION I_Do_Not_Exist_Compression); -- fails +CREATE TABLE t (a text); +ALTER TABLE t ALTER a SET COMPRESSION I_Do_Not_Exist_Compression; -- fails +DROP TABLE t; + \set HIDE_TOAST_COMPRESSION true -- 2.17.0 --poemUeGtc2GQvHuH Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v2-0006-.-configure-Avoid-warnings-on-Mac-with-lz4.patch" From 2382b3fe3e609e99ee1742b872de5b4ae61b2ecc Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Sat, 20 Mar 2021 17:09:36 -0500 Subject: [PATCH v2 06/10] ./configure: Avoid warnings on Mac --with-lz4 Reported by Andrey Borodin and Tom Lane. >>> configure: WARNING: lz4.h: accepted by the compiler, rejected by the preprocessor! >>> configure: WARNING: lz4.h: proceeding with the compiler's result Possibly we could instead just *remove* the AC_CHECK_HEADERS? --- configure | 6 ++++++ configure.ac | 6 ++++++ 2 files changed, 12 insertions(+) diff --git a/configure b/configure index 6d34243dca..fa2b7692ca 100755 --- a/configure +++ b/configure @@ -13522,6 +13522,10 @@ fi fi if test "$with_lz4" = yes; then + ac_save_CPPFLAGS=$CPPFLAGS + CPPFLAGS="$LZ4_CFLAGS $CPPFLAGS" + + # Verify we have LZ4's header files for ac_header in lz4/lz4.h do : ac_fn_c_check_header_mongrel "$LINENO" "lz4/lz4.h" "ac_cv_header_lz4_lz4_h" "$ac_includes_default" @@ -13549,6 +13553,8 @@ fi done + + CPPFLAGS=$ac_save_CPPFLAGS fi if test "$with_gssapi" = yes ; then diff --git a/configure.ac b/configure.ac index e54e2fb632..bd92643a3b 100644 --- a/configure.ac +++ b/configure.ac @@ -1426,8 +1426,14 @@ Use --without-zlib to disable zlib support.])]) fi if test "$with_lz4" = yes; then + ac_save_CPPFLAGS=$CPPFLAGS + CPPFLAGS="$LZ4_CFLAGS $CPPFLAGS" + + # Verify we have LZ4's header files AC_CHECK_HEADERS(lz4/lz4.h, [], [AC_CHECK_HEADERS(lz4.h, [], [AC_MSG_ERROR([lz4.h header file is required for LZ4])])]) + + CPPFLAGS=$ac_save_CPPFLAGS fi if test "$with_gssapi" = yes ; then -- 2.17.0 --poemUeGtc2GQvHuH Content-Type: text/x-diff; charset=iso-8859-1 Content-Disposition: attachment; filename="v2-0007-Commentary-about-slicing.patch" Content-Transfer-Encoding: 8bit From 533a7281906e42db7329c6e44ca236094ab60ab9 Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Sat, 20 Mar 2021 16:13:44 -0500 Subject: [PATCH v2 07/10] Commentary about slicing MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit My language, per gripe from Álvaro Herrera: | I updated the coverage script to use --with-lz4; results are updated. | While eyeballing the results I noticed this bit in | lz4_decompress_datum_slice(): | | + /* slice decompression not supported prior to 1.8.3 */ | + if (LZ4_versionNumber() < 10803) | + return lz4_decompress_datum(value); | | which I read as returning the complete decompressed datum if slice | decompression is not supported. I thought that was a bug, but looking | at the caller I realize that this isn't really a problem, since it's | detoast_attr_slice's responsibility to slice the result further -- no | bug, it's just wasteful. I suggest to add comments to this effect, | perhaps as the attached (feel free to reword, I think mine is awkward.) --- src/backend/access/common/detoast.c | 3 +++ src/backend/access/common/toast_compression.c | 3 +++ 2 files changed, 6 insertions(+) diff --git a/src/backend/access/common/detoast.c b/src/backend/access/common/detoast.c index 2fef40c2e9..316f5715e1 100644 --- a/src/backend/access/common/detoast.c +++ b/src/backend/access/common/detoast.c @@ -497,6 +497,9 @@ toast_decompress_datum(struct varlena *attr) * Decompress the front of a compressed version of a varlena datum. * offset handling happens in detoast_attr_slice. * Here we just decompress a slice from the front. + * + * If slice decompression is not supported, the full datum is decompressed, and + * then sliced by detoast_attr_slice. */ static struct varlena * toast_decompress_datum_slice(struct varlena *attr, int32 slicelength) diff --git a/src/backend/access/common/toast_compression.c b/src/backend/access/common/toast_compression.c index a6f8b79a9e..dd31a54b77 100644 --- a/src/backend/access/common/toast_compression.c +++ b/src/backend/access/common/toast_compression.c @@ -203,6 +203,9 @@ lz4_decompress_datum(const struct varlena *value) /* * Decompress part of a varlena that was compressed using LZ4. + * + * If slice decompression is not supported, the full datum is decompressed, and + * then sliced by detoast_attr_slice. */ struct varlena * lz4_decompress_datum_slice(const struct varlena *value, int32 slicelength) -- 2.17.0 --poemUeGtc2GQvHuH Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v2-0008-specially-handle-SET-default_toast_compression-lz.patch" From adc6eb10f79d1edf3df0d241557b7d23106b7cc6 Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Sat, 20 Mar 2021 17:25:46 -0500 Subject: [PATCH v2 08/10] specially handle SET default_toast_compression=lz4 --- src/backend/access/common/toast_compression.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/backend/access/common/toast_compression.c b/src/backend/access/common/toast_compression.c index dd31a54b77..1617c382c2 100644 --- a/src/backend/access/common/toast_compression.c +++ b/src/backend/access/common/toast_compression.c @@ -304,6 +304,11 @@ check_default_toast_compression(char **newval, void **extra, GucSource source) errmsg("compression method \"%s\" does not exist", *newval))); } + else if (strcmp(*newval, "lz4") == 0) + { + GUC_check_errdetail("This functionality requires the server to be built with lz4 support."); + GUC_check_errhint("You need to rebuild PostgreSQL using --with-lz4."); + } else { GUC_check_errdetail("Compression method \"%s\" does not exist.", -- 2.17.0 --poemUeGtc2GQvHuH Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v2-0009-Alternately-WIP-Change-default_toast_compression-.patch" From 232987c6b79de7cf635664c28fa0062498485146 Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Fri, 19 Mar 2021 19:39:10 -0500 Subject: [PATCH v2 09/10] Alternately: WIP: Change default_toast_compression GUC to an enum.. ..since the final version of the TOAST patch doesn't require catalog access --- src/backend/access/common/toast_compression.c | 54 +------------------ src/backend/utils/misc/guc.c | 30 +++++++---- src/include/access/toast_compression.h | 10 ++-- src/test/regress/expected/compression.out | 4 +- 4 files changed, 28 insertions(+), 70 deletions(-) diff --git a/src/backend/access/common/toast_compression.c b/src/backend/access/common/toast_compression.c index 1617c382c2..9d9ffc6f97 100644 --- a/src/backend/access/common/toast_compression.c +++ b/src/backend/access/common/toast_compression.c @@ -23,8 +23,8 @@ #include "fmgr.h" #include "utils/builtins.h" -/* Compile-time default */ -char *default_toast_compression = DEFAULT_TOAST_COMPRESSION; +/* GUC */ +int default_toast_compression = TOAST_PGLZ_COMPRESSION_ID; /* * Compress a varlena using PGLZ. @@ -269,53 +269,3 @@ toast_get_compression_id(struct varlena *attr) return cmid; } - -/* - * Validate a new value for the default_toast_compression GUC. - */ -bool -check_default_toast_compression(char **newval, void **extra, GucSource source) -{ - if (**newval == '\0') - { - GUC_check_errdetail("%s cannot be empty.", - "default_toast_compression"); - return false; - } - - if (strlen(*newval) >= NAMEDATALEN) - { - GUC_check_errdetail("%s is too long (maximum %d characters).", - "default_toast_compression", NAMEDATALEN - 1); - return false; - } - - if (!CompressionMethodIsValid(CompressionNameToMethod(*newval))) - { - /* - * When source == PGC_S_TEST, don't throw a hard error for a - * nonexistent compression method, only a NOTICE. See comments in - * guc.h. - */ - if (source == PGC_S_TEST) - { - ereport(NOTICE, - (errcode(ERRCODE_UNDEFINED_OBJECT), - errmsg("compression method \"%s\" does not exist", - *newval))); - } - else if (strcmp(*newval, "lz4") == 0) - { - GUC_check_errdetail("This functionality requires the server to be built with lz4 support."); - GUC_check_errhint("You need to rebuild PostgreSQL using --with-lz4."); - } - else - { - GUC_check_errdetail("Compression method \"%s\" does not exist.", - *newval); - return false; - } - } - - return true; -} diff --git a/src/backend/utils/misc/guc.c b/src/backend/utils/misc/guc.c index 4272cf4821..eb1b343c09 100644 --- a/src/backend/utils/misc/guc.c +++ b/src/backend/utils/misc/guc.c @@ -510,6 +510,14 @@ static struct config_enum_entry shared_memory_options[] = { {NULL, 0, false} }; +static struct config_enum_entry default_toast_compression_options[] = { + {"pglz", TOAST_PGLZ_COMPRESSION_ID, false}, +#ifdef USE_LZ4 + {"lz4", TOAST_LZ4_COMPRESSION_ID, false}, +#endif + {NULL, 0, false} +}; + /* * Options for enum values stored in other modules */ @@ -3953,17 +3961,6 @@ static struct config_string ConfigureNamesString[] = check_default_table_access_method, NULL, NULL }, - { - {"default_toast_compression", PGC_USERSET, CLIENT_CONN_STATEMENT, - gettext_noop("Sets the default compression for new columns."), - NULL, - GUC_IS_NAME - }, - &default_toast_compression, - DEFAULT_TOAST_COMPRESSION, - check_default_toast_compression, NULL, NULL - }, - { {"default_tablespace", PGC_USERSET, CLIENT_CONN_STATEMENT, gettext_noop("Sets the default tablespace to create tables and indexes in."), @@ -4605,6 +4602,17 @@ static struct config_enum ConfigureNamesEnum[] = NULL, NULL, NULL }, + { + {"default_toast_compression", PGC_USERSET, CLIENT_CONN_STATEMENT, + gettext_noop("Sets the default compression for new columns."), + NULL, + GUC_IS_NAME + }, + &default_toast_compression, + 0, /* pglz */ + default_toast_compression_options, NULL, NULL + }, + { {"default_transaction_isolation", PGC_USERSET, CLIENT_CONN_STATEMENT, gettext_noop("Sets the transaction isolation level of each new transaction."), diff --git a/src/include/access/toast_compression.h b/src/include/access/toast_compression.h index 09af6e7810..88a46e264d 100644 --- a/src/include/access/toast_compression.h +++ b/src/include/access/toast_compression.h @@ -16,10 +16,7 @@ #include "utils/guc.h" /* GUCs */ -extern char *default_toast_compression; - -/* default compression method if not specified. */ -#define DEFAULT_TOAST_COMPRESSION "pglz" +extern int default_toast_compression; /* * Built-in compression method-id. The toast compression header will store @@ -100,7 +97,10 @@ CompressionNameToMethod(char *compression) static inline char GetDefaultToastCompression(void) { - return CompressionNameToMethod(default_toast_compression); + /* See also guc.c */ + char *const enumtoname[] = {"pglz", "lz4"}; + Assert(default_toast_compression < lengthof(enumtoname)); + return CompressionNameToMethod(enumtoname[default_toast_compression]); } /* pglz compression/decompression routines */ diff --git a/src/test/regress/expected/compression.out b/src/test/regress/expected/compression.out index 501e0ead14..5cc76cdcd6 100644 --- a/src/test/regress/expected/compression.out +++ b/src/test/regress/expected/compression.out @@ -232,10 +232,10 @@ DETAIL: pglz versus lz4 -- test default_toast_compression GUC SET default_toast_compression = ''; ERROR: invalid value for parameter "default_toast_compression": "" -DETAIL: default_toast_compression cannot be empty. +HINT: Available values: pglz, lz4. SET default_toast_compression = 'I do not exist compression'; ERROR: invalid value for parameter "default_toast_compression": "I do not exist compression" -DETAIL: Compression method "I do not exist compression" does not exist. +HINT: Available values: pglz, lz4. SET default_toast_compression = 'lz4'; DROP TABLE cmdata2; CREATE TABLE cmdata2 (f1 text); -- 2.17.0 --poemUeGtc2GQvHuH--