47bb9db75 modified the ApplyRetrieveRule()'s conversion of a view's
original RTE_RELATION entry into an RTE_SUBQUERY one to retain relid,
rellockmode, and perminfoindex so that the executor can lock the view
and check its permissions. It seems better to also retain
relkind for cross-checking that the exception of an
RTE_SUBQUERY entry being allowed to carry relation details only
applies to views, so do so.
Bump catversion because this changes the output format of
RTE_SUBQUERY RTEs.
Suggested-by: David Steele <david@pgmasters.net>
Reviewed-by: David Steele <david@pgmasters.net>
Reviewed-by: Álvaro Herrera <alvherre@alvh.no-ip.org>
Discussion: https://postgr.es/m/
3953179e-9540-e5d1-a743-
4bef368785b0%40pgmasters.net
if (rte->perminfoindex != 0)
{
/* Sanity checks */
+
+ /*
+ * Only relation RTEs and subquery RTEs that were once relation
+ * RTEs (views) have their perminfoindex set.
+ */
+ Assert(rte->rtekind == RTE_RELATION ||
+ (rte->rtekind == RTE_SUBQUERY &&
+ rte->relkind == RELKIND_VIEW));
+
(void) getRTEPermissionInfo(rteperminfos, rte);
/* Many-to-one mapping not allowed */
Assert(!bms_is_member(rte->perminfoindex, indexset));
WRITE_BOOL_FIELD(security_barrier);
/* we re-use these RELATION fields, too: */
WRITE_OID_FIELD(relid);
+ WRITE_CHAR_FIELD(relkind);
WRITE_INT_FIELD(rellockmode);
WRITE_UINT_FIELD(perminfoindex);
break;
READ_BOOL_FIELD(security_barrier);
/* we re-use these RELATION fields, too: */
READ_OID_FIELD(relid);
+ READ_CHAR_FIELD(relkind);
READ_INT_FIELD(rellockmode);
READ_UINT_FIELD(perminfoindex);
break;
/*
* Clear fields that should not be set in a subquery RTE. Note that we
- * leave the relid, rellockmode, and perminfoindex fields set, so that the
- * view relation can be appropriately locked before execution and its
- * permissions checked.
+ * leave the relid, relkind, rellockmode, and perminfoindex fields set, so
+ * that the view relation can be appropriately locked before execution and
+ * its permissions checked.
*/
- rte->relkind = 0;
rte->tablesample = NULL;
rte->inh = false; /* must not be set for a subquery */
*/
/* yyyymmddN */
-#define CATALOG_VERSION_NO 202305211
+#define CATALOG_VERSION_NO 202306141
#endif
* this RTE in the containing struct's list of same; 0 if permissions need
* not be checked for this RTE.
*
- * As a special case, relid, rellockmode, and perminfoindex can also be
- * set (nonzero) in an RTE_SUBQUERY RTE. This occurs when we convert an
- * RTE_RELATION RTE naming a view into an RTE_SUBQUERY containing the
- * view's query. We still need to perform run-time locking and permission
- * checks on the view, even though it's not directly used in the query
- * anymore, and the most expedient way to do that is to retain these
- * fields from the old state of the RTE.
+ * As a special case, relid, relkind, rellockmode, and perminfoindex can
+ * also be set (nonzero) in an RTE_SUBQUERY RTE. This occurs when we
+ * convert an RTE_RELATION RTE naming a view into an RTE_SUBQUERY
+ * containing the view's query. We still need to perform run-time locking
+ * and permission checks on the view, even though it's not directly used
+ * in the query anymore, and the most expedient way to do that is to
+ * retain these fields from the old state of the RTE.
*
* As a special case, RTE_NAMEDTUPLESTORE can also set relid to indicate
* that the tuple format of the tuplestore is the same as the referenced