数据库 |使用不同类型的视图

PostgreSQL | Using different types of views

  1. 我正在尝试在 PostgreSQL 中创建一个不可更新的视图,但我创建的每个视图在向表中插入一些数据后都会继续更新。我做错了什么?
  2. 物化视图和可更新视图有什么区别?
  3. 如何快速检查视图是否可更新?

以下是我尝试创建的三种视图:

 -- Updatable view
    
CREATE VIEW vip_tickets_for_events AS
    SELECT events.id, events.name, COUNT(tickets.id) as vip_tickets_num FROM events
        JOIN tickets on events.id = tickets.event_id
    WHERE tickets.type = 'VIP'
    GROUP BY events.id, events.name;

 -- Non-updatable view

CREATE VIEW tickets_for_events AS
    SELECT vip_tickets.name, vip_tickets.vip_tickets_num, general_tickets.general_tickets_num
    FROM (SELECT events.name, COUNT(tickets.id) as vip_tickets_num FROM events
            JOIN tickets on events.id = tickets.event_id
        WHERE tickets.type = 'VIP'
        GROUP BY events.name) AS vip_tickets
    JOIN
        (SELECT events.name, COUNT(tickets.id) as general_tickets_num FROM events
            JOIN tickets on events.id = tickets.event_id
        WHERE tickets.type = 'General'
        GROUP BY events.name) AS general_tickets
    ON vip_tickets.name = general_tickets.name;

 -- Materialized view

CREATE MATERIALIZED VIEW average_ticket_prices_for_events AS
    SELECT events.id, events.name, AVG(tickets.price) as average_price FROM events
        JOIN tickets on events.id = tickets.event_id
    GROUP BY events.id, events.name;

I'm trying to create a non-updatable view in PostgreSQL but every view I've created is continue updating after inserting some data in tables.

你在混淆术语。 “updatable视图”是允许数据为inserted/updated/deleted:

的视图
insert into some_view(col1, col2) values('val_1', 100);

这是一个 example 您可以玩的视图

docs 说:

Simple views are automatically updatable: the system will allow INSERT, UPDATE and DELETE statements to be used on the view in the same way as on a regular table.

当视图足够简单时,请参阅该文档。

由于您的所有视图在 FROM 区域中包含超过 1 个 table,因此它们是 non-updatable。换句话说,你将无法 运行 insert/update/delete 直接对抗他们。

当你说“我创建的每个视图在 tables 中插入一些数据后继续更新”时,这对我来说意味着你期望视图在源 table 已更改。

这不适用于常规视图,它会将我们带到您的下一个问题

  1. 实体化视图和 updatable 视图有什么区别?

同样,我忽略了“updatable”这个词,因为它毫无意义。

视图只是一个存储的查询。每当你说

select * from some_view

将执行基础查询。您总能获得实际数据。

物化视图是 table 的快照。它保留上次执行的查询和结果(称为“刷新”)。

因此,如果您几天前创建或刷新了实体化视图,它会显示几天前的数据,无论 table 数据是否已更改。

而且我相信“物化视图”是您想要实现的目标,说“non-updatable 视图”

  1. 如何快速检查视图是否已更新table?
  • 如果您需要检查是否可以 运行 insert/update/delete 反对一个视图,您可以尝试一下或检查它的源代码是否足够 simple
  • 如果您需要检查一个对象是视图还是物化视图,这个查询将帮助您
 select *
   from pg_matviews
  where matviewname = 'test_mview'; -- whether an object is a materialized view (and won't get updated automatically after table data changed)

select *
  from pg_views
 where viewname = 'test_view'; -- whether it is a view (ad will get updated after changes in a source table)