刷新物化视图:并发,事务行为

时间:2013-09-15 10:45:27

标签: postgresql materialized-views postgresql-9.3

关于REFRESH MATERIALIZED VIEW的官方PostgreSQL 9.3文档尚未对其进行详细描述。

来自blog的引用:

  Postgres 9.3中的物化视图有一个严重的限制,包括在刷新时使用独占锁。这基本上阻止了在使用来自其父关系的新数据刷新实体化视图时尝试读取的任何尝试

来自mailing list的帖子的另一个引用:

  

如果我理解正确的事情,那么REFRESH MATERIALIZED VIEW锁定了   具有AccessExclusiveLock的物化视图,即使视图已经存在   包含数据。

我的问题:以下序列是否正确:

  1. 查询正在访问实体化视图
  2. 作业执行REFRESH MATERIALIZED VIEW。它会锁定视图,并等待所有使用matview运行的查询完成
  3. matview正在开始刷新;如果matview上有索引,则会同时更新(因此在一次交易中完成刷新)
  4. 使用matview查询等待刷新完成。如果这需要太长时间,则会出现类似“等待锁定超时错误”的情况。
  5. 刷新完成,锁定被删除
  6. 等待matview的查询继续

2 个答案:

答案 0 :(得分:8)

截至Postgres 9.4发布时,情况并非完全如此。您现在可以使用REFRESH MATERIALIZED VIEW CONCURRENTLY命令同时刷新实例化视图。从功能上来说,这会刷新视图,但是在没有读锁定的情况下会这样做。在计算方面这是一个更昂贵的操作,但是如果锁定对你来说是个问题(因为对我而言,这导致我走这条路),那么这不是一个糟糕的方法。

以下是发布说明中的更多信息:https://wiki.postgresql.org/wiki/What%27s_new_in_PostgreSQL_9.4#REFRESH_MATERIALIZED_VIEW_CONCURRENTLY

答案 1 :(得分:4)

得到答案,因为我还没有玩过mat视图,但基于此:

http://www.postgresql.org/docs/current/static/sql-creatematerializedview.html

他们背后的哲学是将它们视为create table as ...

的更智能变体
  

CREATE MATERIALIZED VIEW与CREATE TABLE AS类似,不同之处在于它还会记住用于初始化视图的查询,以便以后可以根据需要刷新。物化视图具有许多与表相同的属性,但不支持临时物化视图或自动生成OID。

在我阅读refresh materialized view命令或我在其上找到的文档时,它们不会自动更新,我也会像您一样了解流程。

我想,排他锁是因为你不能轻易地知道(除了琐碎的情况)哪些行是脏的,哪些不是。如果开发人员确定了这样做的有效方式,那么物化视图可能会自动同时更新。