summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPavan Deolasee2018-07-17 04:47:40 +0000
committerPavan Deolasee2018-07-27 08:00:57 +0000
commitb6f3f378007a40b27c6b2a7eba8fe738a2c57fef (patch)
tree296965be88144b5a4abd4e94facffeaad2e2d92f
parentd5481c454e5b915fcc5e08acbc13405c836f5cd6 (diff)
Fix handling of REFRESH MATERIALIZED VIEW CONCURRENTLY
We create a coordinator-only LOCAL temporary table for REFRESH MATERIALIZED VIEW CONCURRENTLY. Since this table does not exist on the remote nodes, we must not use explicit "ANALYZE <temptable>". Instead, just analyze it locally like we were doing at other places. Restore the matview test case to use REFRESH MATERIALIZED VIEW CONCURRENTLY now that the underlying bug is fixed.
-rw-r--r--src/backend/commands/matview.c36
-rw-r--r--src/test/regress/expected/matview.out8
-rw-r--r--src/test/regress/sql/matview.sql10
3 files changed, 38 insertions, 16 deletions
diff --git a/src/backend/commands/matview.c b/src/backend/commands/matview.c
index bfe549766c..685c227c96 100644
--- a/src/backend/commands/matview.c
+++ b/src/backend/commands/matview.c
@@ -624,6 +624,8 @@ refresh_by_match_merge(Oid matviewOid, Oid tempOid, Oid relowner,
char *matviewname;
char *tempname;
char *diffname;
+ char *qualified_diffname;
+ char *tempschema;
TupleDesc tupdesc;
bool foundUniqueIndex;
List *indexoidlist;
@@ -636,9 +638,11 @@ refresh_by_match_merge(Oid matviewOid, Oid tempOid, Oid relowner,
matviewname = quote_qualified_identifier(get_namespace_name(RelationGetNamespace(matviewRel)),
RelationGetRelationName(matviewRel));
tempRel = heap_open(tempOid, NoLock);
- tempname = quote_qualified_identifier(get_namespace_name(RelationGetNamespace(tempRel)),
+ tempschema = get_namespace_name(RelationGetNamespace(tempRel));
+ tempname = quote_qualified_identifier(tempschema,
RelationGetRelationName(tempRel));
- diffname = make_temptable_name_n(tempname, 2);
+ diffname = make_temptable_name_n(RelationGetRelationName(tempRel), 2);
+ qualified_diffname = quote_qualified_identifier(tempschema, diffname);
relnatts = matviewRel->rd_rel->relnatts;
usedForQual = (bool *) palloc0(sizeof(bool) * relnatts);
@@ -728,7 +732,8 @@ refresh_by_match_merge(Oid matviewOid, Oid tempOid, Oid relowner,
#endif
"SELECT mv.ctid AS tid, newdata "
"FROM %s mv FULL JOIN %s newdata ON (",
- diffname, matviewname, tempname);
+ qualified_diffname,
+ matviewname, tempname);
/*
* Get the list of index OIDs for the table from the relcache, and look up
@@ -830,11 +835,25 @@ refresh_by_match_merge(Oid matviewOid, Oid tempOid, Oid relowner,
* must keep it around because its type is referenced from the diff table.
*/
+#ifndef PGXC
/* Analyze the diff table. */
resetStringInfo(&querybuf);
- appendStringInfo(&querybuf, "ANALYZE %s", diffname);
+ appendStringInfo(&querybuf, "ANALYZE %s", qualified_diffname);
if (SPI_exec(querybuf.data, 0) != SPI_OK_UTILITY)
elog(ERROR, "SPI_exec failed: %s", querybuf.data);
+#else
+ {
+ /*
+ * Don't want to send down the ANALYZE on the remote nodes because the
+ * temporary table was not created there to start with. See above.
+ */
+ VacuumStmt *stmt = makeNode(VacuumStmt);
+ RangeVar *rv = makeRangeVar(tempschema, diffname, -1);
+ stmt->relation = rv;
+ stmt->options = VACOPT_ANALYZE;
+ ExecVacuum(stmt, true);
+ }
+#endif
OpenMatViewIncrementalMaintenance();
@@ -845,7 +864,8 @@ refresh_by_match_merge(Oid matviewOid, Oid tempOid, Oid relowner,
"(SELECT diff.tid FROM %s diff "
"WHERE diff.tid IS NOT NULL "
"AND diff.newdata IS NULL)",
- matviewname, diffname);
+ matviewname,
+ qualified_diffname);
if (SPI_exec(querybuf.data, 0) != SPI_OK_DELETE)
elog(ERROR, "SPI_exec failed: %s", querybuf.data);
@@ -854,7 +874,8 @@ refresh_by_match_merge(Oid matviewOid, Oid tempOid, Oid relowner,
appendStringInfo(&querybuf,
"INSERT INTO %s SELECT (diff.newdata).* "
"FROM %s diff WHERE tid IS NULL",
- matviewname, diffname);
+ matviewname,
+ qualified_diffname);
if (SPI_exec(querybuf.data, 0) != SPI_OK_INSERT)
elog(ERROR, "SPI_exec failed: %s", querybuf.data);
@@ -865,7 +886,8 @@ refresh_by_match_merge(Oid matviewOid, Oid tempOid, Oid relowner,
/* Clean up temp tables. */
resetStringInfo(&querybuf);
- appendStringInfo(&querybuf, "DROP TABLE %s, %s", diffname, tempname);
+ appendStringInfo(&querybuf, "DROP TABLE %s, %s",
+ qualified_diffname, tempname);
if (SPI_exec(querybuf.data, 0) != SPI_OK_UTILITY)
elog(ERROR, "SPI_exec failed: %s", querybuf.data);
diff --git a/src/test/regress/expected/matview.out b/src/test/regress/expected/matview.out
index bc5387f1cf..16ba1eeb49 100644
--- a/src/test/regress/expected/matview.out
+++ b/src/test/regress/expected/matview.out
@@ -411,7 +411,7 @@ CREATE UNIQUE INDEX on mvtest_mv (c);
INSERT INTO mvtest_foo VALUES(2, 3, 4);
INSERT INTO mvtest_foo VALUES(3, 4, 5);
REFRESH MATERIALIZED VIEW mvtest_mv;
-REFRESH MATERIALIZED VIEW mvtest_mv;
+REFRESH MATERIALIZED VIEW CONCURRENTLY mvtest_mv;
DROP TABLE mvtest_foo CASCADE;
NOTICE: drop cascades to materialized view mvtest_mv
-- allow subquery to reference unpopulated matview if WITH NO DATA is specified
@@ -429,7 +429,7 @@ INSERT INTO mvtest_boxes (b) VALUES
CREATE MATERIALIZED VIEW mvtest_boxmv AS SELECT * FROM mvtest_boxes;
CREATE UNIQUE INDEX mvtest_boxmv_id ON mvtest_boxmv (id);
UPDATE mvtest_boxes SET b = '(2,2),(1,1)' WHERE id = 2;
-REFRESH MATERIALIZED VIEW mvtest_boxmv;
+REFRESH MATERIALIZED VIEW CONCURRENTLY mvtest_boxmv;
SELECT * FROM mvtest_boxmv ORDER BY id;
id | b
----+-----------------------------
@@ -455,7 +455,7 @@ INSERT INTO mvtest_v values (1, 2);
CREATE UNIQUE INDEX mvtest_mv_v_ii ON mvtest_mv_v (ii);
REFRESH MATERIALIZED VIEW mvtest_mv_v;
UPDATE mvtest_v SET j = 3 WHERE x = 1;
-REFRESH MATERIALIZED VIEW mvtest_mv_v;
+REFRESH MATERIALIZED VIEW CONCURRENTLY mvtest_mv_v;
REFRESH MATERIALIZED VIEW mvtest_mv_v_2;
REFRESH MATERIALIZED VIEW mvtest_mv_v_3;
REFRESH MATERIALIZED VIEW mvtest_mv_v_4;
@@ -575,7 +575,7 @@ NOTICE: relation "mvtest_mv_foo" already exists, skipping
CREATE UNIQUE INDEX ON mvtest_mv_foo (i);
RESET ROLE;
REFRESH MATERIALIZED VIEW mvtest_mv_foo;
-REFRESH MATERIALIZED VIEW mvtest_mv_foo;
+REFRESH MATERIALIZED VIEW CONCURRENTLY mvtest_mv_foo;
DROP OWNED BY regress_user_mvtest CASCADE;
DROP ROLE regress_user_mvtest;
-- make sure that create WITH NO DATA works via SPI
diff --git a/src/test/regress/sql/matview.sql b/src/test/regress/sql/matview.sql
index 3e2a4126fb..d96175aa26 100644
--- a/src/test/regress/sql/matview.sql
+++ b/src/test/regress/sql/matview.sql
@@ -59,7 +59,7 @@ INSERT INTO mvtest_t VALUES (6, 'z', 13);
-- confirm pre- and post-refresh contents of fairly simple materialized views
SELECT * FROM mvtest_tm ORDER BY type;
SELECT * FROM mvtest_tvm ORDER BY type;
-REFRESH MATERIALIZED VIEW mvtest_tm;
+REFRESH MATERIALIZED VIEW CONCURRENTLY mvtest_tm;
REFRESH MATERIALIZED VIEW mvtest_tvm;
SELECT * FROM mvtest_tm ORDER BY type;
SELECT * FROM mvtest_tvm ORDER BY type;
@@ -140,7 +140,7 @@ CREATE UNIQUE INDEX on mvtest_mv (c);
INSERT INTO mvtest_foo VALUES(2, 3, 4);
INSERT INTO mvtest_foo VALUES(3, 4, 5);
REFRESH MATERIALIZED VIEW mvtest_mv;
-REFRESH MATERIALIZED VIEW mvtest_mv;
+REFRESH MATERIALIZED VIEW CONCURRENTLY mvtest_mv;
DROP TABLE mvtest_foo CASCADE;
-- allow subquery to reference unpopulated matview if WITH NO DATA is specified
@@ -158,7 +158,7 @@ INSERT INTO mvtest_boxes (b) VALUES
CREATE MATERIALIZED VIEW mvtest_boxmv AS SELECT * FROM mvtest_boxes;
CREATE UNIQUE INDEX mvtest_boxmv_id ON mvtest_boxmv (id);
UPDATE mvtest_boxes SET b = '(2,2),(1,1)' WHERE id = 2;
-REFRESH MATERIALIZED VIEW mvtest_boxmv;
+REFRESH MATERIALIZED VIEW CONCURRENTLY mvtest_boxmv;
SELECT * FROM mvtest_boxmv ORDER BY id;
DROP TABLE mvtest_boxes CASCADE;
@@ -175,7 +175,7 @@ INSERT INTO mvtest_v values (1, 2);
CREATE UNIQUE INDEX mvtest_mv_v_ii ON mvtest_mv_v (ii);
REFRESH MATERIALIZED VIEW mvtest_mv_v;
UPDATE mvtest_v SET j = 3 WHERE x = 1;
-REFRESH MATERIALIZED VIEW mvtest_mv_v;
+REFRESH MATERIALIZED VIEW CONCURRENTLY mvtest_mv_v;
REFRESH MATERIALIZED VIEW mvtest_mv_v_2;
REFRESH MATERIALIZED VIEW mvtest_mv_v_3;
REFRESH MATERIALIZED VIEW mvtest_mv_v_4;
@@ -219,7 +219,7 @@ CREATE MATERIALIZED VIEW IF NOT EXISTS mvtest_mv_foo AS SELECT * FROM mvtest_foo
CREATE UNIQUE INDEX ON mvtest_mv_foo (i);
RESET ROLE;
REFRESH MATERIALIZED VIEW mvtest_mv_foo;
-REFRESH MATERIALIZED VIEW mvtest_mv_foo;
+REFRESH MATERIALIZED VIEW CONCURRENTLY mvtest_mv_foo;
DROP OWNED BY regress_user_mvtest CASCADE;
DROP ROLE regress_user_mvtest;