Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ON RULES, PROCEDURES, CACHING and VIEWS IN DATA BASE SYSTEMS #20

Open
mrdrivingduck opened this issue Apr 19, 2023 · 2 comments
Open

ON RULES, PROCEDURES, CACHING and VIEWS IN DATA BASE SYSTEMS #20

mrdrivingduck opened this issue Apr 19, 2023 · 2 comments

Comments

@mrdrivingduck
Copy link
Owner

ERL-M90-36.pdf

一篇古早的论文,讲解了一个简单的 规则系统 的实现,可以被用于支持视图。这也是 PostgreSQL 规则系统 的理论模型。

@mrdrivingduck
Copy link
Owner Author

Grammar

在语法上,规则系统包含:

  • 规则名称
  • 规则触发事件(或者可以被认为是时机,增/删/改/查)
  • 规则操作对象(看起来是一个查询 body,可以带过滤条件)
  • 规则动作
DEFINE RULE rule-name [AS EXCEPTION TO rule-name]
ON event TO object [[FROM clause] WHERE clause]
THEN DO [instead] action

规则系统提供了两个元组变量可供引用:

  • CURRENT:表示符合条件的原元组,用于查询、更新、删除
  • NEW:表示规则将要插入的新元组:用于更新、插入

然后给了一些语法上的例子:

规则 1:在更新表中 name=Joesalary 列时触发,将待更新的元组(NEW) 的 salary 列赋值给 name=Sam 的元组。业务上,这意味着在更新 Joe 的薪水时,总是顺带更新 Sam 的薪水为相同的值。

define rule example_1
on replace to EMP.salary where EMP.name = ‘‘Joe’’
then replace EMP (salary = NEW.salary) where EMP.name = ‘‘Sam’’

规则 2:在查询表中 name=Joe 的列的 salary 时,把当前的 salary 值更新到 name=Billsalary 列上。在业务上,含义是每当访问 Joe 的薪水时,都保证 Bill 的薪水和 Joe 一致。

define rule example_2
on retrieve to EMP.salary where EMP.name = ‘‘Joe’’
then replace EMP (salary = CURRENT.salary) where EMP.name = ‘‘Bill’’

更多例子不赘述。这也是 NEWCURRENT 的使用方法。

规则 8:一个使用规则系统实现的视图。当查询 TOY_EMP 表时,转而查询 EMP 表中的符合条件的某几列。这个 TOY_EMP 在本质上就是一个视图。

define rule example_8
on retrieve to TOY_EMP
then do instead retrieve (EMP-OID = EMP.OID, EMP.name, EMP.age, EMP.salary)
where EMP.dept = ‘‘toy’’

@mrdrivingduck
Copy link
Owner Author

mrdrivingduck commented Apr 19, 2023

Implementation

文中给出了两种实现规则系统的方法:

  1. 在执行器内,处理每一条元组的时候,实现规则
  2. 实现查询重写,在 Parser 和 Optimizer 之前实现这个模块

方法 1 于 1995 年在 Postgre95 出现前从 Berkeley Postgres 项目中移除(原因是?),方法 2 被实现并保留到了现在。其基本算法是替换规则中出现的 CURRENTNEW 引用,并替换所有的元组使用和过滤条件。然后不断进行重写,直到没有更多规则可以被应用为止。

这也是目前 PostgreSQL 中 Query Rewriter 的的大致处理流程:将语法树中的视图节点直接替换为一个子查询节点,子查询的内容就是视图定义。在 PostgreSQL 中创建一个视图,在背地里实际上就是创建了一条规则:

  • SELECT event 上触发
  • 规则行为是 INSTEAD,即使用规则动作得到的结果替换规则结果
  • 规则动作即查询视图定义

Rules ON SELECT are applied to all queries as the last step, even if the command given is an INSERT, UPDATE or DELETE. And they have different semantics from rules on the other command types in that they modify the query tree in place instead of creating a new one. So SELECT rules are described first.

Currently, there can be only one action in an ON SELECT rule, and it must be an unconditional SELECT action that is INSTEAD. This restriction was required to make rules safe enough to open them for ordinary users, and it restricts ON SELECT rules to act like views.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

1 participant