创建而不是插入触发器

时间:2017-10-08 22:30:57

标签: sql oracle

我是Oracle的初学者。我正在尝试创建一个INSTEAD OF触发器来强制执行一个规则,即教师不应该在一个月内工作超过60小时

这是我到目前为止所拥有的

    CREATE TRIGGER limit_hour
    INSTEAD OF INSERT ON SESSIONHOURS 
    DECLARE
    totalHours NUMBER := 60;
    monthOnly DATE;
    totalSession NUMBER;
    FOR EACH ROW
    BEGIN
      INSERT INTO SESSIONHOURS(SESSIONDATEKEY, TUTORKEY, TOTALSESSION)
      SELECT EXTRACT (MONTH FROM DATE S.SESSIONDATEKEY), S.TOTALSESSION
      INTO monthOnly, totalSession
    FROM SESSIONHOURS S
    END;

错误“不适当的INTO”不断弹出。此外,我需要为提取的月份分配每个会话的总和(每个30分钟),然后将其与“totalHour”进行比较。如何为日期值分配时间值?任何建议将不胜感激

2 个答案:

答案 0 :(得分:0)

您的INSERT语句编写不正确。它应该是:

INSERT INTO SESSIONHOURS(SESSIONDATEKEY, TOTALSESSION)
  SELECT EXTRACT (MONTH FROM DATE S.SESSIONDATEKEY), S.TOTALSESSION
    FROM SESSIONHOURS S

这不会解决你的总时数"问题,但它会处理您报告的错误。

祝你好运。

答案 1 :(得分:0)

在我看来,BEFORE INSERT触发器更合适,而不是使用INSTEAD OF触发器。 INSTEAD OF触发器通常用于将不可插入视图上的INSERT映射到INSERT到所需的表中。另一方面,BEFORE INSERT触发器在每行插入表之前触发,允许检查行中的值的一致性等。这样的触发器可以如下使用:

(arrays) => "?" + arrays.filter(({length}) => length > 1).map(([tax, ...cats]) => `${tax}=${cats.join(",")}`).join("&")

在处理INSESS进入SESSIONHOURS之前将触发此触发器。它查询数据库以确定其密钥位于INSERT语句(CREATE TRIGGER SESSIONHOURS_BI BEFORE INSERT INTO SESSIONHOURS FOR EACH ROW DECLARE nTotal_tutor_hours NUMBER; BEGIN SELECT SUM(HOURS) INTO nTotal_tutor_hours FROM SESSIONHOURS s WHERE s.TUTORKEY = :new.TUTORKEY; IF nTotal_tutor_hours + :new.HOURS > 60 THEN RAISE_APPLICATION_ERROR(-20001, 'Addition of ' || :new.HOURS || ' for tutor ' || :new.TUTORKEY || ' exceeds monthly limit of 60'); END IF; END SESSIONHOURS_BI; )中的教师的总工作小时数。如果工作总时数加上新记录中的小时数超过60,则会引发异常,从而导致INSERT中止。否则触发器正常返回,INSERT继续。

然而 - 即使这样也行不通。问题是触发器是在SESSIONHOURS表上定义的,而在触发器内部,SESSIONHOURS表上有一个SELECT。这将导致数据库抛出可怕的:new.TUTORKEY异常,并附有解释性文本ORA-04091。有几种方法可以解决这个问题,其中最好的方法是遵循一个简单的规则:

***永远不要*在触发器中实施商业逻辑!!!!

诸如“导师可能不会超过60小时工作”的规则是一项商业规则。这应该在您的应用程序逻辑中实现,而不是在触发器中实现。在数据库中创建过程或函数以执行INSERT INTO SESSIONHOURS和任何所需的验证逻辑,并在每次需要将数据插入SESSIONHOURS时调用该过程。不要尝试将验证逻辑置于触发器中 - 您会发现它非常困难,并且会导致永无止境的调试会话as noted here

祝你好运。