Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 732758d

Browse files
committed
Fix breakage of MV column name list usage.
Per bug report from Tomonari Katsumata. Back-patch to 9.3.
1 parent dddc344 commit 732758d

File tree

3 files changed

+50
-7
lines changed

3 files changed

+50
-7
lines changed

src/backend/rewrite/rewriteDefine.c

Lines changed: 14 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@
4444

4545

4646
static void checkRuleResultList(List *targetList, TupleDesc resultDesc,
47-
bool isSelect);
47+
bool isSelect, bool requireColumnNameMatch);
4848
static bool setRuleCheckAsUser_walker(Node *node, Oid *context);
4949
static void setRuleCheckAsUser_Query(Query *qry, Oid userid);
5050

@@ -355,7 +355,9 @@ DefineQueryRewrite(char *rulename,
355355
*/
356356
checkRuleResultList(query->targetList,
357357
RelationGetDescr(event_relation),
358-
true);
358+
true,
359+
event_relation->rd_rel->relkind !=
360+
RELKIND_MATVIEW);
359361

360362
/*
361363
* ... there must not be another ON SELECT rule already ...
@@ -484,7 +486,7 @@ DefineQueryRewrite(char *rulename,
484486
errmsg("RETURNING lists are not supported in non-INSTEAD rules")));
485487
checkRuleResultList(query->returningList,
486488
RelationGetDescr(event_relation),
487-
false);
489+
false, false);
488490
}
489491
}
490492

@@ -613,15 +615,20 @@ DefineQueryRewrite(char *rulename,
613615
* Verify that targetList produces output compatible with a tupledesc
614616
*
615617
* The targetList might be either a SELECT targetlist, or a RETURNING list;
616-
* isSelect tells which. (This is mostly used for choosing error messages,
617-
* but also we don't enforce column name matching for RETURNING.)
618+
* isSelect tells which. This is used for choosing error messages.
619+
*
620+
* A SELECT targetlist may optionally require that column names match.
618621
*/
619622
static void
620-
checkRuleResultList(List *targetList, TupleDesc resultDesc, bool isSelect)
623+
checkRuleResultList(List *targetList, TupleDesc resultDesc, bool isSelect,
624+
bool requireColumnNameMatch)
621625
{
622626
ListCell *tllist;
623627
int i;
624628

629+
/* Only a SELECT may require a column name match. */
630+
Assert(isSelect || !requireColumnNameMatch);
631+
625632
i = 0;
626633
foreach(tllist, targetList)
627634
{
@@ -657,7 +664,7 @@ checkRuleResultList(List *targetList, TupleDesc resultDesc, bool isSelect)
657664
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
658665
errmsg("cannot convert relation containing dropped columns to view")));
659666

660-
if (isSelect && strcmp(tle->resname, attname) != 0)
667+
if (requireColumnNameMatch && strcmp(tle->resname, attname) != 0)
661668
ereport(ERROR,
662669
(errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
663670
errmsg("SELECT rule's target entry %d has different column name from \"%s\"", i, attname)));

src/test/regress/expected/matview.out

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -450,3 +450,26 @@ SELECT * FROM boxmv ORDER BY id;
450450

451451
DROP TABLE boxes CASCADE;
452452
NOTICE: drop cascades to materialized view boxmv
453+
-- make sure that column names are handled correctly
454+
CREATE TABLE v (i int, j int);
455+
CREATE MATERIALIZED VIEW mv_v (ii) AS SELECT i, j AS jj FROM v;
456+
ALTER TABLE v RENAME COLUMN i TO x;
457+
INSERT INTO v values (1, 2);
458+
CREATE UNIQUE INDEX mv_v_ii ON mv_v (ii);
459+
REFRESH MATERIALIZED VIEW mv_v;
460+
UPDATE v SET j = 3 WHERE x = 1;
461+
REFRESH MATERIALIZED VIEW CONCURRENTLY mv_v;
462+
SELECT * FROM v;
463+
x | j
464+
---+---
465+
1 | 3
466+
(1 row)
467+
468+
SELECT * FROM mv_v;
469+
ii | jj
470+
----+----
471+
1 | 3
472+
(1 row)
473+
474+
DROP TABLE v CASCADE;
475+
NOTICE: drop cascades to materialized view mv_v

src/test/regress/sql/matview.sql

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -173,3 +173,16 @@ UPDATE boxes SET b = '(2,2),(1,1)' WHERE id = 2;
173173
REFRESH MATERIALIZED VIEW CONCURRENTLY boxmv;
174174
SELECT * FROM boxmv ORDER BY id;
175175
DROP TABLE boxes CASCADE;
176+
177+
-- make sure that column names are handled correctly
178+
CREATE TABLE v (i int, j int);
179+
CREATE MATERIALIZED VIEW mv_v (ii) AS SELECT i, j AS jj FROM v;
180+
ALTER TABLE v RENAME COLUMN i TO x;
181+
INSERT INTO v values (1, 2);
182+
CREATE UNIQUE INDEX mv_v_ii ON mv_v (ii);
183+
REFRESH MATERIALIZED VIEW mv_v;
184+
UPDATE v SET j = 3 WHERE x = 1;
185+
REFRESH MATERIALIZED VIEW CONCURRENTLY mv_v;
186+
SELECT * FROM v;
187+
SELECT * FROM mv_v;
188+
DROP TABLE v CASCADE;

0 commit comments

Comments
 (0)