aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNathan Bossart <nathan@postgresql.org>2025-04-04 21:05:30 -0500
committerNathan Bossart <nathan@postgresql.org>2025-04-04 21:05:30 -0500
commitf0d0083f52f994989b1bb6723e7bd0fad9f586cd (patch)
treef4468bb077a027d73c87b898f8de29a7b5629822
parent43b8e6c4abfb632bbff5b3a26dc39bf3f188afff (diff)
downloadpostgresql-f0d0083f52f994989b1bb6723e7bd0fad9f586cd.tar.gz
postgresql-f0d0083f52f994989b1bb6723e7bd0fad9f586cd.zip
pg_dump: Fix query for gathering attribute stats on older versions.
Commit 9c02e3a986 taught pg_dump to retrieve attribute statistics for 64 relations at a time. pg_dump supports dumping from v9.2 and newer versions, but our query for retrieving statistics for multiple relations uses WITH ORDINALITY and multi-argument UNNEST(), both of which were introduced in v9.4. To fix, we resort to gathering statistics for a single relation at a time on versions older than v9.4. Per buildfarm member crake. Author: Corey Huinker <corey.huinker@gmail.com> Discussion: https://postgr.es/m/Z_BcWVMvlUIJ_iuZ%40nathan
-rw-r--r--src/bin/pg_dump/pg_dump.c38
1 files changed, 30 insertions, 8 deletions
diff --git a/src/bin/pg_dump/pg_dump.c b/src/bin/pg_dump/pg_dump.c
index 0e915432e77..8e6364d32d7 100644
--- a/src/bin/pg_dump/pg_dump.c
+++ b/src/bin/pg_dump/pg_dump.c
@@ -10571,6 +10571,16 @@ fetchAttributeStats(Archive *fout)
PGresult *res = NULL;
static TocEntry *te;
static bool restarted;
+ int max_rels = MAX_ATTR_STATS_RELS;
+
+ /*
+ * Our query for retrieving statistics for multiple relations uses WITH
+ * ORDINALITY and multi-argument UNNEST(), both of which were introduced
+ * in v9.4. For older versions, we resort to gathering statistics for a
+ * single relation at a time.
+ */
+ if (fout->remoteVersion < 90400)
+ max_rels = 1;
/* If we're just starting, set our TOC pointer. */
if (!te)
@@ -10596,7 +10606,7 @@ fetchAttributeStats(Archive *fout)
* This is perhaps not the sturdiest assumption, so we verify it matches
* reality in dumpRelationStats_dumper().
*/
- for (; te != AH->toc && count < MAX_ATTR_STATS_RELS; te = te->next)
+ for (; te != AH->toc && count < max_rels; te = te->next)
{
if ((te->reqs & REQ_STATS) != 0 &&
strcmp(te->desc, "STATISTICS DATA") == 0)
@@ -10709,14 +10719,26 @@ dumpRelationStats_dumper(Archive *fout, const void *userArg, const TocEntry *te)
* sufficient to convince the planner to use
* pg_class_relname_nsp_index, which avoids a full scan of pg_stats.
* This may not work for all versions.
+ *
+ * Our query for retrieving statistics for multiple relations uses
+ * WITH ORDINALITY and multi-argument UNNEST(), both of which were
+ * introduced in v9.4. For older versions, we resort to gathering
+ * statistics for a single relation at a time.
*/
- appendPQExpBufferStr(query,
- "FROM pg_catalog.pg_stats s "
- "JOIN unnest($1, $2) WITH ORDINALITY AS u (schemaname, tablename, ord) "
- "ON s.schemaname = u.schemaname "
- "AND s.tablename = u.tablename "
- "WHERE s.tablename = ANY($2) "
- "ORDER BY u.ord, s.attname, s.inherited");
+ if (fout->remoteVersion >= 90400)
+ appendPQExpBufferStr(query,
+ "FROM pg_catalog.pg_stats s "
+ "JOIN unnest($1, $2) WITH ORDINALITY AS u (schemaname, tablename, ord) "
+ "ON s.schemaname = u.schemaname "
+ "AND s.tablename = u.tablename "
+ "WHERE s.tablename = ANY($2) "
+ "ORDER BY u.ord, s.attname, s.inherited");
+ else
+ appendPQExpBufferStr(query,
+ "FROM pg_catalog.pg_stats s "
+ "WHERE s.schemaname = $1[1] "
+ "AND s.tablename = $2[1] "
+ "ORDER BY s.attname, s.inherited");
ExecuteSqlStatement(fout, query->data);