views:

729

answers:

1

I am told by someone that when calling Oracle from ADO.net, when calling multiple inserts in a loop, where each insert causes a trigger to fire that includes within it's PL-Sql a Commit statement, that it is impossible to stop that commit from actually commiting the transaction.

i.e., I want my ADO.Net code to begin a transaction before the loop starts, and, when the loop exits, only commit all the inserts if and only if every insert in the loop was successful. My source is telling me that the way Oracle works, if these triggers include COmmit statements, then this is impossible..

As this seems to be an very common requirement, and I know it is possible in SQL Server, this does not seem right to me.

Is this correct?

+6  A: 

Your informant is wrong, if he is talking about Oracle database triggers:

1) You cannot put a COMMIT in an Oracle trigger that is not autonomous:

SQL> create trigger this_wont_work
  2  after insert on emp
  3  begin
  4    commit;
  5  end;
  6  /

Trigger created.

SQL> insert into emp (empno) values (123)
  2  /
insert into emp (empno) values (123)
            *
ERROR at line 1:
ORA-04092: cannot COMMIT in a trigger
ORA-06512: at "TONY.THIS_WONT_WORK", line 2
ORA-04088: error during execution of trigger 'TONY.THIS_WONT_WORK'

2) If the trigger is autonomous (i.e. has PRAGMA AUTONOMOUS_TRANSACTION in its declaration section) then it can only commit any changes it (the trigger) makes.

There is no danger whatsoever of a trigger committing work you did outside of that trigger.

Note: the use of autonomous transactions in triggers is dangerous except for certain cases, because actions performed by the autonomous trigger will be committed even if the triggering statement is rolled back. This can easily lead to data corruption if mis-used.

Tony Andrews
Yes, I discovered that. So again, what I want to do, is inhibit the trigger commit until my ADO.Net Client code externally tells the database to commit. Then I want the database to commit all pending ops since I began the transaction at the beginning of the loop, including all trigger operatiuons
Charles Bretana
Charles, what you want is exactly what will happen, unless the triggers are autonomous. If they are autonomous, then you have no control over when they are committed, and there's presumably a reason somebody did it that way.
Dave Costa
So does your trigger include a COMMIT and a PRAGMA AUTONOMOUS_TRANSACTION? If so, why since you don't want it to?!
Tony Andrews
You can't stop or delay an autonomous transaction... it is, after all, autonomous. It's meant to happen regardless of the calling txn.
Tony, I'd edit this if I could but you don't mean Oracle Database Triggers, you mean TABLE triggers. I think Database triggers can include commit.
Tony, on further thought, his source may actually be saying the same as you: IF the triggers contain COMMITs, THEN they must be autonomous, and THEREFORE they are independent of his transaction. The question becomes, is this the correct business logic? If not, why were they implemented this way?
Dave Costa
@Mark: All triggers are "database triggers". Per documentation: "Use the CREATE TRIGGER statement to create and enable a database trigger". DDL and event triggers can be ON DATABASE, which I think is what you are referring to. These would be "database DDL" or "database event" triggers.
Dave Costa
I'm not referring to the denotation, but to the connotation. "Database Trigger" is Connoted to mean DDL and Event triggers. The answer is more clear with the change not withstanding an entry in documentation.
What sticks out in this thread for me is Dave Costas comment that "IF the triggers contain COMMITs, THEN they must be autonomous.." if this is so, then I'm screwed, unless I can change the code in these triggers... and to answer another question, there is NO reason for Commits to be in there!
Charles Bretana
Yes, I'm afraid that if you can't change those triggers then they will autonomously commit their own work, as their developer specifically designed them to do. If this is incorrect then the triggers have a bug and must be fixed!
Tony Andrews
... I know that inexperienced developers often throw an autonomous transaction into their triggers because it magically "solves" a "table is mutating" error - but only at the expense of unwanted and usually data-corrupting behaviour.
Tony Andrews