diff options
author | Pavan Deolasee | 2018-07-17 04:47:40 +0000 |
---|---|---|
committer | Pavan Deolasee | 2018-07-27 08:00:57 +0000 |
commit | b6f3f378007a40b27c6b2a7eba8fe738a2c57fef (patch) | |
tree | 296965be88144b5a4abd4e94facffeaad2e2d92f | |
parent | d5481c454e5b915fcc5e08acbc13405c836f5cd6 (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.c | 36 | ||||
-rw-r--r-- | src/test/regress/expected/matview.out | 8 | ||||
-rw-r--r-- | src/test/regress/sql/matview.sql | 10 |
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; |