假设我们有以下表结构:
documents docmentStatusHistory status
+---------+ +--------------------+ +----------+
| docId | | docStatusHistoryId | | statusId |
+---------+ +--------------------+ +----------+
| ... | | docId | | ... |
+---------+ | statusId | +----------+
| ... |
+--------------------+
可能很明显,但值得一提的是,文档的当前状态是最后输入的状态历史记录。
该系统的性能缓慢但肯定会下降,我建议将上述结构更改为:
documents docmentStatusHistory status
+--------------+ +--------------------+ +----------+
| docId | | docStatusHistoryId | | statusId |
+--------------+ +--------------------+ +----------+
| currStatusId | | docId | | ... |
| ... | | statusId | +----------+
+--------------+ | ... |
+--------------------+
这样,我们就可以将文档的当前状态放在应有的位置。
由于遗留应用程序的构建方式,我无法更改遗留应用程序上的代码来更新文档表上的当前状态。
在这种情况下,我不得不为我的规则打开一个例外,以不惜一切代价避免触发器,仅仅是因为我无权访问遗留应用程序代码。
我创建了一个触发器,每次将新状态添加到状态历史记录时,它都会更新文档的当前状态,它就像一个魅力。
然而,在一个晦涩且很少使用的情况下,需要删除最后的状态历史,而不是简单地添加一个新的。因此,我创建了以下触发器:
create or replace trigger trgD_History
after delete on documentStatusHistory
for each row
currentStatusId number;
begin
select statusId
into currentStatusId
from documentStatusHistory
where docStatusHistoryId = (select max(docStatusHistoryId)
from documentStatusHistory
where docId = :old.docId);
update documentos
set currStatusId = currentStatusId
where docId = :old.docId;
end;
这就是我得到臭名昭著的错误的地方ORA-04091
。
我了解为什么会收到此错误,即使我将触发器配置为AFTER触发器。
问题是我看不到解决此错误的方法。我在网上搜索了一段时间,到目前为止找不到任何有用的东西。
随着时间的推移,我们正在使用 Oracle 9i。