postgres.git / summary / log / commit / refs

commit    34fcd735f1ebd5efba8653cdbfbfd076b081660a
Author:   Michael Paquier <michael@paquier.xyz>
Date:     Fri Sep 11 01:54:48 2026 +0000

    Add support for TOAST chunk_id type in binary upgrades
    
    This commit adds a new SQL function able to set the type of a chunk_id
    attribute for a TOAST table across binary upgrades.  The value is set
    when the creation of a TOAST table is required across upgrades, in the
    same fashion as the TOAST relation's oid and relfilenode.
    
    Note that this piece currently works only with a TOAST table's chunk_id
    set at OIDOID, because it is currently the only type of on-disk external
    TOAST pointer supported.  This change is required for a follow-up
    feature that aims to introduce support for 8-byte OIDs in external TOAST
    pointers.
    
    Taking care of this issue separately is less code churn for the next
    changes, and perhaps some of the surrounding discussions with support
    for different types of external on-disk TOAST pointers will find this
    new facility useful.
    
    Bump catalog version.
    
    Author: Michael Paquier <michael@paquier.xyz>
    Reviewed-by: Greg Burd <greg@burd.me>
    Reviewed-by: Bharath Rupireddy <bharath.rupireddyforpostgres@gmail.com>
    Reviewed-by: Yugo Nagata <nagata@sraoss.co.jp>
    Discussion: https://postgr.es/m/af19kUjwjhaoUTLn@paquier.xyz


src/backend/catalog/heap.c | 1 + src/backend/catalog/toasting.c | 20 +++++++++++++++++++- src/backend/utils/adt/pg_upgrade_support.c | 11 +++++++++++ src/bin/pg_dump/pg_dump.c | 14 +++++++++++--- src/include/catalog/binary_upgrade.h | 1 + src/include/catalog/catversion.h | 2 +- src/include/catalog/pg_proc.dat | 5 +++++ .../spgist_name_ops/expected/spgist_name_ops.out | 6 ++++-- 8 files changed, 53 insertions(+), 7 deletions(-) diff --git a/src/backend/catalog/heap.c b/src/backend/catalog/heap.c index a107193d7ab..1c188b7a0ff 100644 --- a/src/backend/catalog/heap.c +++ b/src/backend/catalog/heap.c @@ -80,6 +80,7 @@ /* Potentially set by pg_upgrade_support functions */ Oid binary_upgrade_next_heap_pg_class_oid = InvalidOid; Oid binary_upgrade_next_toast_pg_class_oid = InvalidOid; +Oid binary_upgrade_next_toast_chunk_id_typoid = InvalidOid; RelFileNumber binary_upgrade_next_heap_pg_class_relfilenumber = InvalidRelFileNumber; RelFileNumber binary_upgrade_next_toast_pg_class_relfilenumber = InvalidRelFileNumber; diff --git a/src/backend/catalog/toasting.c b/src/backend/catalog/toasting.c index 4aa52a4bd25..b19478ba072 100644 --- a/src/backend/catalog/toasting.c +++ b/src/backend/catalog/toasting.c @@ -146,6 +146,7 @@ create_toast_table(Relation rel, Oid toastOid, Oid toastIndexOid, int16 coloptions[2]; ObjectAddress baseobject, toastobject; + Oid toast_chunkid_typid = OIDOID; /* * Is it already toasted? @@ -184,6 +185,23 @@ create_toast_table(Relation rel, Oid toastOid, Oid toastIndexOid, */ if (!OidIsValid(binary_upgrade_next_toast_pg_class_oid)) return false; + + /* + * The attribute type for chunk_id should have been set when + * requesting a TOAST table creation. + */ + if (!OidIsValid(binary_upgrade_next_toast_chunk_id_typoid)) + ereport(ERROR, + (errcode(ERRCODE_INVALID_PARAMETER_VALUE), + errmsg("toast chunk_id type not set while in binary upgrade mode"))); + if (binary_upgrade_next_toast_chunk_id_typoid != OIDOID) + ereport(ERROR, + (errcode(ERRCODE_INVALID_PARAMETER_VALUE), + errmsg("cannot support toast chunk_id type %u in binary upgrade mode", + binary_upgrade_next_toast_chunk_id_typoid))); + + toast_chunkid_typid = binary_upgrade_next_toast_chunk_id_typoid; + binary_upgrade_next_toast_chunk_id_typoid = InvalidOid; } /* @@ -205,7 +223,7 @@ create_toast_table(Relation rel, Oid toastOid, Oid toastIndexOid, tupdesc = CreateTemplateTupleDesc(3); TupleDescInitEntry(tupdesc, (AttrNumber) 1, "chunk_id", - OIDOID, + toast_chunkid_typid, -1, 0); TupleDescInitEntry(tupdesc, (AttrNumber) 2, "chunk_seq", diff --git a/src/backend/utils/adt/pg_upgrade_support.c b/src/backend/utils/adt/pg_upgrade_support.c index 760991f1adc..f5017022d2e 100644 --- a/src/backend/utils/adt/pg_upgrade_support.c +++ b/src/backend/utils/adt/pg_upgrade_support.c @@ -149,6 +149,17 @@ binary_upgrade_set_next_toast_pg_class_oid(PG_FUNCTION_ARGS) PG_RETURN_VOID(); } +Datum +binary_upgrade_set_next_toast_chunk_id_typoid(PG_FUNCTION_ARGS) +{ + Oid typoid = PG_GETARG_OID(0); + + CHECK_IS_BINARY_UPGRADE; + binary_upgrade_next_toast_chunk_id_typoid = typoid; + + PG_RETURN_VOID(); +} + Datum binary_upgrade_set_next_toast_relfilenode(PG_FUNCTION_ARGS) { diff --git a/src/bin/pg_dump/pg_dump.c b/src/bin/pg_dump/pg_dump.c index 7a12e03ca02..388c3b9c346 100644 --- a/src/bin/pg_dump/pg_dump.c +++ b/src/bin/pg_dump/pg_dump.c @@ -104,6 +104,7 @@ typedef struct RelFileNumber relfilenumber; /* object filenode */ Oid toast_oid; /* toast table OID */ RelFileNumber toast_relfilenumber; /* toast table filenode */ + Oid toast_chunk_id_typoid; /* type of chunk_id attribute */ Oid toast_index_oid; /* toast table index OID */ RelFileNumber toast_index_relfilenumber; /* toast table index filenode */ } BinaryUpgradeClassOidItem; @@ -5869,7 +5870,10 @@ collectBinaryUpgradeClassOids(Archive *fout) const char *query; query = "SELECT c.oid, c.relkind, c.relfilenode, c.reltoastrelid, " - "ct.relfilenode, i.indexrelid, cti.relfilenode " + "ct.relfilenode, i.indexrelid, cti.relfilenode, " + "(SELECT a.atttypid FROM pg_attribute AS a " + " WHERE a.attrelid = c.reltoastrelid AND attname = 'chunk_id'::text) " + " AS toastchunktypid " "FROM pg_catalog.pg_class c LEFT JOIN pg_catalog.pg_index i " "ON (c.reltoastrelid = i.indrelid AND i.indisvalid) " "LEFT JOIN pg_catalog.pg_class ct ON (c.reltoastrelid = ct.oid) " @@ -5891,6 +5895,7 @@ collectBinaryUpgradeClassOids(Archive *fout) binaryUpgradeClassOids[i].toast_relfilenumber = atooid(PQgetvalue(res, i, 4)); binaryUpgradeClassOids[i].toast_index_oid = atooid(PQgetvalue(res, i, 5)); binaryUpgradeClassOids[i].toast_index_relfilenumber = atooid(PQgetvalue(res, i, 6)); + binaryUpgradeClassOids[i].toast_chunk_id_typoid = atooid(PQgetvalue(res, i, 7)); } PQclear(res); @@ -5907,7 +5912,7 @@ binary_upgrade_set_pg_class_oids(Archive *fout, /* * Preserve the OID and relfilenumber of the table, table's index, table's - * toast table and toast table's index if any. + * toast table, toast table's chunk type and toast table's index if any. * * One complexity is that the current table definition might not require * the creation of a TOAST table, but the old database might have a TOAST @@ -5922,7 +5927,7 @@ binary_upgrade_set_pg_class_oids(Archive *fout, BinaryUpgradeClassOidItemCmp); appendPQExpBufferStr(upgrade_buffer, - "\n-- For binary upgrade, must preserve pg_class oids and relfilenodes\n"); + "\n-- For binary upgrade, must preserve pg_class oids, toast chunk type oids and relfilenodes\n"); if (entry->relkind != RELKIND_INDEX && entry->relkind != RELKIND_PARTITIONED_INDEX) @@ -5955,6 +5960,9 @@ binary_upgrade_set_pg_class_oids(Archive *fout, appendPQExpBuffer(upgrade_buffer, "SELECT pg_catalog.binary_upgrade_set_next_toast_relfilenode('%u'::pg_catalog.oid);\n", entry->toast_relfilenumber); + appendPQExpBuffer(upgrade_buffer, + "SELECT pg_catalog.binary_upgrade_set_next_toast_chunk_id_typoid('%u'::pg_catalog.oid);\n", + entry->toast_chunk_id_typoid); /* every toast table has an index */ appendPQExpBuffer(upgrade_buffer, diff --git a/src/include/catalog/binary_upgrade.h b/src/include/catalog/binary_upgrade.h index 7bf7ae44385..117f3e3f774 100644 --- a/src/include/catalog/binary_upgrade.h +++ b/src/include/catalog/binary_upgrade.h @@ -29,6 +29,7 @@ extern PGDLLIMPORT Oid binary_upgrade_next_index_pg_class_oid; extern PGDLLIMPORT RelFileNumber binary_upgrade_next_index_pg_class_relfilenumber; extern PGDLLIMPORT Oid binary_upgrade_next_toast_pg_class_oid; extern PGDLLIMPORT RelFileNumber binary_upgrade_next_toast_pg_class_relfilenumber; +extern PGDLLIMPORT Oid binary_upgrade_next_toast_chunk_id_typoid; extern PGDLLIMPORT Oid binary_upgrade_next_pg_enum_oid; extern PGDLLIMPORT Oid binary_upgrade_next_pg_authid_oid; diff --git a/src/include/catalog/catversion.h b/src/include/catalog/catversion.h index f8aaf9aab02..12ae8f4331a 100644 --- a/src/include/catalog/catversion.h +++ b/src/include/catalog/catversion.h @@ -57,6 +57,6 @@ */ /* yyyymmddN */ -#define CATALOG_VERSION_NO 202609102 +#define CATALOG_VERSION_NO 202609111 #endif diff --git a/src/include/catalog/pg_proc.dat b/src/include/catalog/pg_proc.dat index c53ce68c717..74d386b868b 100644 --- a/src/include/catalog/pg_proc.dat +++ b/src/include/catalog/pg_proc.dat @@ -11992,6 +11992,11 @@ proname => 'binary_upgrade_set_next_toast_pg_class_oid', provolatile => 'v', proparallel => 'r', prorettype => 'void', proargtypes => 'oid', prosrc => 'binary_upgrade_set_next_toast_pg_class_oid' }, +{ oid => '8219', descr => 'for use by pg_upgrade', + proname => 'binary_upgrade_set_next_toast_chunk_id_typoid', + provolatile => 'v', proparallel => 'r', prorettype => 'void', + proargtypes => 'oid', + prosrc => 'binary_upgrade_set_next_toast_chunk_id_typoid' }, { oid => '3589', descr => 'for use by pg_upgrade', proname => 'binary_upgrade_set_next_pg_enum_oid', provolatile => 'v', proparallel => 'r', prorettype => 'void', proargtypes => 'oid', diff --git a/src/test/modules/spgist_name_ops/expected/spgist_name_ops.out b/src/test/modules/spgist_name_ops/expected/spgist_name_ops.out index 1ee65ede243..35e59d0cd83 100644 --- a/src/test/modules/spgist_name_ops/expected/spgist_name_ops.out +++ b/src/test/modules/spgist_name_ops/expected/spgist_name_ops.out @@ -61,9 +61,10 @@ select * from t binary_upgrade_set_next_pg_enum_oid | | binary_upgrade_set_next_pg_enum_oid binary_upgrade_set_next_pg_tablespace_oid | | binary_upgrade_set_next_pg_tablespace_oid binary_upgrade_set_next_pg_type_oid | | binary_upgrade_set_next_pg_type_oid + binary_upgrade_set_next_toast_chunk_id_typoid | | binary_upgrade_set_next_toast_chunk_id_typoid binary_upgrade_set_next_toast_pg_class_oid | 1 | binary_upgrade_set_next_toast_pg_class_oid binary_upgrade_set_next_toast_relfilenode | | binary_upgrade_set_next_toast_relfilenode -(13 rows) +(14 rows) -- Verify clean failure when INCLUDE'd columns result in overlength tuple -- The error message details are platform-dependent, so show only SQLSTATE @@ -110,9 +111,10 @@ select * from t binary_upgrade_set_next_pg_enum_oid | | binary_upgrade_set_next_pg_enum_oid binary_upgrade_set_next_pg_tablespace_oid | | binary_upgrade_set_next_pg_tablespace_oid binary_upgrade_set_next_pg_type_oid | | binary_upgrade_set_next_pg_type_oid + binary_upgrade_set_next_toast_chunk_id_typoid | | binary_upgrade_set_next_toast_chunk_id_typoid binary_upgrade_set_next_toast_pg_class_oid | 1 | binary_upgrade_set_next_toast_pg_class_oid binary_upgrade_set_next_toast_relfilenode | | binary_upgrade_set_next_toast_relfilenode -(13 rows) +(14 rows) \set VERBOSITY sqlstate insert into t values(repeat('xyzzy', 12), 42, repeat('xyzzy', 4000)); [parent: ba9e747c49a6]