mirror of
https://github.com/postgres/postgres.git
synced 2025-07-05 07:21:24 +03:00
Switch user ID to the object owner when populating a materialized view.
This makes superuser-issued REFRESH MATERIALIZED VIEW safe regardless of the object's provenance. REINDEX is an earlier example of this pattern. As a downside, functions called from materialized views must tolerate running in a security-restricted operation. CREATE MATERIALIZED VIEW need not change user ID. Nonetheless, avoid creation of materialized views that will invariably fail REFRESH by making it, too, start a security-restricted operation. Back-patch to 9.3 so materialized views have this from the beginning. Reviewed by Kevin Grittner.
This commit is contained in:
@ -122,6 +122,9 @@ ExecRefreshMatView(RefreshMatViewStmt *stmt, const char *queryString,
|
||||
RewriteRule *rule;
|
||||
List *actions;
|
||||
Query *dataQuery;
|
||||
Oid save_userid;
|
||||
int save_sec_context;
|
||||
int save_nestlevel;
|
||||
Oid tableSpace;
|
||||
Oid OIDNewHeap;
|
||||
DestReceiver *dest;
|
||||
@ -191,6 +194,16 @@ ExecRefreshMatView(RefreshMatViewStmt *stmt, const char *queryString,
|
||||
*/
|
||||
CheckTableNotInUse(matviewRel, "REFRESH MATERIALIZED VIEW");
|
||||
|
||||
/*
|
||||
* Switch to the owner's userid, so that any functions are run as that
|
||||
* user. Also lock down security-restricted operations and arrange to
|
||||
* make GUC variable changes local to this command.
|
||||
*/
|
||||
GetUserIdAndSecContext(&save_userid, &save_sec_context);
|
||||
SetUserIdAndSecContext(matviewRel->rd_rel->relowner,
|
||||
save_sec_context | SECURITY_RESTRICTED_OPERATION);
|
||||
save_nestlevel = NewGUCNestLevel();
|
||||
|
||||
/*
|
||||
* Tentatively mark the matview as populated or not (this will roll back
|
||||
* if we fail later).
|
||||
@ -217,6 +230,12 @@ ExecRefreshMatView(RefreshMatViewStmt *stmt, const char *queryString,
|
||||
RecentXmin, ReadNextMultiXactId());
|
||||
|
||||
RelationCacheInvalidateEntry(matviewOid);
|
||||
|
||||
/* Roll back any GUC changes */
|
||||
AtEOXact_GUC(false, save_nestlevel);
|
||||
|
||||
/* Restore userid and security context */
|
||||
SetUserIdAndSecContext(save_userid, save_sec_context);
|
||||
}
|
||||
|
||||
/*
|
||||
|
Reference in New Issue
Block a user