From: Tom Lane Date: Mon, 3 Mar 2003 04:37:48 +0000 (+0000) Subject: Prevent clustering on incomplete indexes: partial indexes are verboten, X-Git-Tag: REL7_3_3~70 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=6b305090ed2f307c9189fe938aa0054add6ef872;p=thirdparty%2Fpostgresql.git Prevent clustering on incomplete indexes: partial indexes are verboten, as are non-amindexnulls AMs unless first column is attnotnull. --- diff --git a/src/backend/commands/cluster.c b/src/backend/commands/cluster.c index fa414320a31..313b0eff137 100644 --- a/src/backend/commands/cluster.c +++ b/src/backend/commands/cluster.c @@ -11,7 +11,7 @@ * * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/backend/commands/cluster.c,v 1.91 2002/11/02 21:20:40 tgl Exp $ + * $Header: /cvsroot/pgsql/src/backend/commands/cluster.c,v 1.91.2.1 2003/03/03 04:37:48 tgl Exp $ * *------------------------------------------------------------------------- */ @@ -110,6 +110,34 @@ cluster(RangeVar *oldrelation, char *oldindexname) RelationGetRelationName(OldIndex), RelationGetRelationName(OldHeap)); + /* + * Disallow clustering on incomplete indexes (those that might not index + * every row of the relation). We could relax this by making a separate + * seqscan pass over the table to copy the missing rows, but that seems + * expensive and tedious. + */ + if (VARSIZE(&OldIndex->rd_index->indpred) > VARHDRSZ) /* partial? */ + elog(ERROR, "CLUSTER: cannot cluster on partial index"); + if (!OldIndex->rd_am->amindexnulls) + { + AttrNumber colno; + + /* + * If the AM doesn't index nulls, then it's a partial index unless + * we can prove all the rows are non-null. Note we only need look + * at the first column; multicolumn-capable AMs are *required* to + * index nulls in columns after the first. + */ + if (OidIsValid(OldIndex->rd_index->indproc)) + elog(ERROR, "CLUSTER: cannot cluster on functional index when index access method does not handle nulls"); + colno = OldIndex->rd_index->indkey[0]; + if (colno > 0) /* system columns are non-null */ + if (!OldHeap->rd_att->attrs[colno - 1]->attnotnull) + elog(ERROR, "CLUSTER: cannot cluster when index access method does not handle nulls" + "\n\tYou may be able to work around this by marking column \"%s\" NOT NULL", + NameStr(OldHeap->rd_att->attrs[colno - 1]->attname)); + } + /* * Disallow clustering system relations. This will definitely NOT * work for shared relations (we have no way to update pg_class rows