2012-02-23 73 views
6

在SQL数据库引擎内如何实现触发器?我不是指SQL语言级别的触发器定义,而是指Oracle,SQL Server,MySQL等内部的底层实现。数据库引擎如何可扩展地管理数百或数千的触发器?他们是否像使用观察者/听众模式一样使用发布 - 订阅模型?任何有关该主题相关文献的指针也将被赞赏。数据库触发器在SQL数据库引擎中如何实现?

我没有谷歌的“数据库触发器实现”,但我发现的所有信息都是有关SQL触发器定义的信息,这又不是我想要的。

+0

我认为这应该是[dba.se] ..;但我会一直关注它,因为我实际上不知道。 – Ben 2012-02-23 23:42:46

回答

3

触发器是回调函数,因此实现可以像C中的函数指针一样简单。但通常,用户不需要在C中的RDBMS中编写用户定义的过程代码。您需要支持其他一些“更高级别”的语言。所以相关的编程模式是DSL。触发器(可伸缩性)本身的数量本身并不成问题,因为每个表通常只有一个,最多两个,而DML事件仅触发这些事件。实施挑战在其他地方:在一致性和并发语义领域。

+0

我正试图在自己的系统中实现类似触发器的机制。是的,我知道“用户不需要在RDBMS中编写用户定义的程序代码”。我并不是将自己局限于“每桌只有一个,最多两个”的假设。我正在研究一个可能有成千上万个触发器的高端案例。 – stackoverflowuser2010 2012-02-24 19:39:44

+1

触发事件的数量非常有限:插入,更新,删除 - 我没有考虑其他任何事情。在一些奇怪的球场景中,一个触发器可以调用数千个程序 - 但在这里,我完全不了解你的需求。 – 2012-02-27 17:10:47

1

首先,触发器是在数据库中发生特定事件(例如特定表上的INSERT/UPDATE/DELETE)时运行的代码段。触发器隐式执行BEFORE或AFER DML语句,触发器不能像存储过程那样显式执行。

还有两种类型的触发器 - STATEMENT LEVEL触发器和ROW LEVEL触发器。

STATEMENT LEVEL触发器在执行语句之前或之后触发。

ROW LEVEL触发器在操作受到操作影响的每个单独行之前或之后触发。

因此,我们有12种类型的触发器:

1. BEFORE INSERT STATEMENT 
2. BEFORE INSERT ROW 
3. AFTER INSERT STATEMENT 
4. AFTER INSERT ROW 
5. BEFORE UPDATE STATEMENT 
6. BEFORE UPDATE ROW 
7. AFTER UPDATE STATEMENT 
8. AFTER UPDATE ROW 
9. BEFORE DELETE STATEMENT 
10. BEFORE DELETE ROW 
11. AFTER DELETE STATEMENT 
12. AFTER DELETE ROW 

多个触发器可以被编码为他们所提到的执行优先顺序的事件。

每当我们在数据库上运行DML查询(INSERT/UPDATE/DELETE)时,该查询就会在事务中运行。因此,当一个查询运行 -

  1. 锁定表
  2. 的DBMS检查运行前的语句是要执行
  3. 执行实际的SQL语句行由行触发器。
  4. 寻找EACH ROW的BEFORE触发器。如果找到,执行。
  5. 检查错误。如果有的话,回滚语句或其触发器所做的更改。
  6. 找到并执行任何AFTER EACH ROW触发器。
  7. 找到并执行任何AFTER STATEMENT触发器。

不同的DBMS以不同方式管理事务。有关详细信息,请参阅其文档。

许多DBMS只保留文本格式的触发器,而不像编译的存储过程。

从触发器体内调用存储过程是最好的实践,因为存储过程的执行速度比触发器快得多。