@@ -2278,6 +2278,13 @@ query_tree_walker(Query *query,
2278
2278
{
2279
2279
Assert (query != NULL && IsA (query , Query ));
2280
2280
2281
+ /*
2282
+ * We don't walk any utilityStmt here. However, we can't easily assert
2283
+ * that it is absent, since there are at least two code paths by which
2284
+ * action statements from CREATE RULE end up here, and NOTIFY is allowed
2285
+ * in a rule action.
2286
+ */
2287
+
2281
2288
if (walker ((Node * ) query -> targetList , context ))
2282
2289
return true;
2283
2290
if (walker ((Node * ) query -> withCheckOptions , context ))
@@ -2296,6 +2303,54 @@ query_tree_walker(Query *query,
2296
2303
return true;
2297
2304
if (walker (query -> limitCount , context ))
2298
2305
return true;
2306
+
2307
+ /*
2308
+ * Most callers aren't interested in SortGroupClause nodes since those
2309
+ * don't contain actual expressions. However they do contain OIDs which
2310
+ * may be needed by dependency walkers etc.
2311
+ */
2312
+ if ((flags & QTW_EXAMINE_SORTGROUP ))
2313
+ {
2314
+ if (walker ((Node * ) query -> groupClause , context ))
2315
+ return true;
2316
+ if (walker ((Node * ) query -> windowClause , context ))
2317
+ return true;
2318
+ if (walker ((Node * ) query -> sortClause , context ))
2319
+ return true;
2320
+ if (walker ((Node * ) query -> distinctClause , context ))
2321
+ return true;
2322
+ }
2323
+ else
2324
+ {
2325
+ /*
2326
+ * But we need to walk the expressions under WindowClause nodes even
2327
+ * if we're not interested in SortGroupClause nodes.
2328
+ */
2329
+ ListCell * lc ;
2330
+
2331
+ foreach (lc , query -> windowClause )
2332
+ {
2333
+ WindowClause * wc = lfirst_node (WindowClause , lc );
2334
+
2335
+ if (walker (wc -> startOffset , context ))
2336
+ return true;
2337
+ if (walker (wc -> endOffset , context ))
2338
+ return true;
2339
+ }
2340
+ }
2341
+
2342
+ /*
2343
+ * groupingSets and rowMarks are not walked:
2344
+ *
2345
+ * groupingSets contain only ressortgrouprefs (integers) which are
2346
+ * meaningless without the corresponding groupClause or tlist.
2347
+ * Accordingly, any walker that needs to care about them needs to handle
2348
+ * them itself in its Query processing.
2349
+ *
2350
+ * rowMarks is not walked because it contains only rangetable indexes (and
2351
+ * flags etc.) and therefore should be handled at Query level similarly.
2352
+ */
2353
+
2299
2354
if (!(flags & QTW_IGNORE_CTE_SUBQUERIES ))
2300
2355
{
2301
2356
if (walker ((Node * ) query -> cteList , context ))
@@ -3153,6 +3208,56 @@ query_tree_mutator(Query *query,
3153
3208
MUTATE (query -> havingQual , query -> havingQual , Node * );
3154
3209
MUTATE (query -> limitOffset , query -> limitOffset , Node * );
3155
3210
MUTATE (query -> limitCount , query -> limitCount , Node * );
3211
+
3212
+ /*
3213
+ * Most callers aren't interested in SortGroupClause nodes since those
3214
+ * don't contain actual expressions. However they do contain OIDs, which
3215
+ * may be of interest to some mutators.
3216
+ */
3217
+
3218
+ if ((flags & QTW_EXAMINE_SORTGROUP ))
3219
+ {
3220
+ MUTATE (query -> groupClause , query -> groupClause , List * );
3221
+ MUTATE (query -> windowClause , query -> windowClause , List * );
3222
+ MUTATE (query -> sortClause , query -> sortClause , List * );
3223
+ MUTATE (query -> distinctClause , query -> distinctClause , List * );
3224
+ }
3225
+ else
3226
+ {
3227
+ /*
3228
+ * But we need to mutate the expressions under WindowClause nodes even
3229
+ * if we're not interested in SortGroupClause nodes.
3230
+ */
3231
+ List * resultlist ;
3232
+ ListCell * temp ;
3233
+
3234
+ resultlist = NIL ;
3235
+ foreach (temp , query -> windowClause )
3236
+ {
3237
+ WindowClause * wc = lfirst_node (WindowClause , temp );
3238
+ WindowClause * newnode ;
3239
+
3240
+ FLATCOPY (newnode , wc , WindowClause );
3241
+ MUTATE (newnode -> startOffset , wc -> startOffset , Node * );
3242
+ MUTATE (newnode -> endOffset , wc -> endOffset , Node * );
3243
+
3244
+ resultlist = lappend (resultlist , (Node * ) newnode );
3245
+ }
3246
+ query -> windowClause = resultlist ;
3247
+ }
3248
+
3249
+ /*
3250
+ * groupingSets and rowMarks are not mutated:
3251
+ *
3252
+ * groupingSets contain only ressortgroup refs (integers) which are
3253
+ * meaningless without the groupClause or tlist. Accordingly, any mutator
3254
+ * that needs to care about them needs to handle them itself in its Query
3255
+ * processing.
3256
+ *
3257
+ * rowMarks contains only rangetable indexes (and flags etc.) and
3258
+ * therefore should be handled at Query level similarly.
3259
+ */
3260
+
3156
3261
if (!(flags & QTW_IGNORE_CTE_SUBQUERIES ))
3157
3262
MUTATE (query -> cteList , query -> cteList , List * );
3158
3263
else /* else copy CTE list as-is */
0 commit comments