BEFORE UPDATE Trigger
Hi,
I'm looking for a solution to find out which columns are set in the update-statement inside a before update trigger. Can someone give me a hint?!
What I want to do:
I want to ensure that an update-statement for a special table always include attribute "XXX". To declare this attribute as "not null" is useless, because it is set correctly at insert. To compare the new value against the old value in a before update trigger isn't possible because the new value can be the same as the old value.
I'm using Oracle 8i.
There is no need to use two triggers and a temporary table where a simple insert from the before trigger will do the job.
You can just insert the :old.column values straigth into a history table within the before update trigger though I would prefer to use an after update trigger. Nevertheless, both the insert into history and the update will be part of one transaction so the two action will commit or rollback together:
UT1 > create or replace trigger marktest_bu
2 before update on marktest
3 for each row
4 begin
5 insert into marktest_hist
6 values (:old.fld1, :old.fld2, :old.fld3, :old.fld4);
7 end;
8 /
Trigger created.
UT1 > select * from marktest_hist;
no rows selected
UT1 > update marktest set fld1 = 'trigtest2'
2 where fld1 = 'trigtest';
1 row updated.
UT1 > select * from marktest_hist;
FLD1 FLD2 FLD3 FLD4
trigtest 9 28-MAY-04 trigtest
IMHO -- Mark D Powell --
Similar Messages
-
Mutating error : row level BEFORE UPDATE trigger
Hi,
I had an issue on mutating terror(was trying to write a row level BEFORE update trigger), however i got it resolved after refering tom kytes web site. I thought i would share it with everyone, might be helpful for a few... Thanks!
I will be more than happy to learn on further better ways of resolving this issue.
Below I have posted the trigger that was causing this error and the work around for that issue, I created a package and three other triggers to replace row level BEFORE update trigger:
++trigger that was causing this issue:++
CREATE OR REPLACE TRIGGER C_F_BI
BEFORE INSERT ON CONTACT_FUNCTION FOR EACH ROW
declare
cursor function_code_cur ( cur_contact_id CONTACT.Contact_Id%type,
cur_function_type_code CONTACT_FUNCTION.Function_Type_Code%type)
is
select
cft.function_type_code,
cft.multiples_permitted
from
CONTACT_FUNCTION cf,
CONTACT c,
CONTACT_FUNCTION_TYPE cft
where
c.acct_id = (select acct_id from contact where contact_id = cur_contact_id)
and c.contact_id = cf.contact_id
and cf.function_type_code = cft.function_type_code
and cft.function_type_code = cur_function_type_code;
v_function_type_code contact_function_type.function_type_code%type;
v_multiples_permitted contact_function_type.multiples_permitted%type;
E_Multiples_Not_Permitted Exception;
begin
if not function_code_cur%isopen then
open function_code_cur(:new.contact_Id,:new.function_type_code);
end if;
loop
fetch function_code_cur into v_function_type_code, v_multiples_permitted;
exit when not function_code_cur%found;
end loop;
** if the fetch returns a v_multiples_permitted of 'Y' or no record is found, then it is
** ok to add the record. Otherwise raise an error because that function_type is already
** being used at the current acct.
if v_multiples_permitted = 'N' then
raise E_Multiples_Not_Permitted;
end if;
close function_code_cur;
EXCEPTION
when E_Multiples_Not_Permitted then
raise_application_error( -20001,'Multiples not allowed for function type ' ||
v_function_type_code || '. sqlerrm - ' || sqlerrm );
when others then
raise;
end;
++solution for above issue :++
create or replace package state_pkg
is
type ridArray_rec is record(rid rowid, cont_id number, cont_fn_type varchar2(20));
type ridArray is table of ridArray_rec index by binary_integer;
newRows ridArray;
empty ridArray;
end state_pkg;
create or replace trigger contact_function_bu1
before update on contact_function
begin
state_pkg.newRows := state_pkg.empty;
end;
create or replace trigger contact_function_bu2
before update ON CONTACT_FUNCTION FOR EACH ROW
DECLARE
I NUMBER:=0;
begin
I := state_pkg.newRows.count+1;
state_pkg.newRows( I ).rid := :new.rowid;
state_pkg.newRows( I ).cont_id := :new.contact_id;
state_pkg.newRows( I ).cont_fn_type := :new.function_type_code;
end;
create or replace trigger contact_function_bu
after update ON CONTACT_FUNCTION
declare
cursor function_code_cur ( cur_contact_id CONTACT.Contact_Id%type,
cur_function_type_code CONTACT_FUNCTION.Function_Type_Code%type,
rid2 rowid)
is
select
cft.function_type_code,
cft.multiples_permitted
from
CONTACT_FUNCTION cf,
CONTACT c,
CONTACT_FUNCTION_TYPE cft
where
c.acct_id = (select acct_id from contact where contact_id = cur_contact_id)
and c.contact_id = cf.contact_id
and cf.function_type_code = cft.function_type_code
and cft.function_type_code = cur_function_type_code
and cf.rowid = rid2;
v_function_type_code contact_function_type.function_type_code%type;
v_multiples_permitted contact_function_type.multiples_permitted%type;
E_Multiples_Not_Permitted Exception;
begin
for i in 1 .. state_pkg.newRows.count loop
if not function_code_cur%isopen then
open function_code_cur(state_pkg.newRows(i).cont_id, state_pkg.newRows(i).cont_fn_type, state_pkg.newRows(i).rid);
end if;
loop
fetch function_code_cur into v_function_type_code, v_multiples_permitted;
exit when not function_code_cur%found;
end loop;
** if the fetch returns a v_multiples_permitted of 'Y' or no record is found, then it is
** ok to add the record. Otherwise raise an error because that function_type is already
** being used at the current acct.
if v_multiples_permitted = 'N' then
raise E_Multiples_Not_Permitted;
end if;
close function_code_cur;
end loop;
EXCEPTION
when E_Multiples_Not_Permitted then
raise_application_error( -20001,'Multiples not allowed for function type ' ||
v_function_type_code || '. sqlerrm - ' || sqlerrm );
when others then
raise;
end;
/It seems you could have solved the issue otherwise:
CREATE OR REPLACE TRIGGER c_f_bi
BEFORE INSERT
ON contact_function
FOR EACH ROW
DECLARE
v_function_type_code contact_function_type.function_type_code%TYPE;
v_multiples_permitted contact_function_type.multiples_permitted%TYPE;
e_multiples_not_permitted EXCEPTION;
BEGIN
BEGIN
SELECT cft.function_type_code, cft.multiples_permitted
INTO v_function_type_code, v_multiples_permitted
FROM contact c, contact_function_type cft
WHERE c.acct_id = (SELECT acct_id
FROM contact
WHERE contact_id = :NEW.contact_id)
AND c.contact_id = :NEW.contact_id
AND cft.function_type_code = :NEW.function_type_code;
EXCEPTION
WHEN NO_DATA_FOUND
THEN
v_function_type_code := :NEW.function_type_code;
v_multiples_permitted := '?';
END;
** if the query returns a v_multiples_permitted of 'Y' or no record is found, then it is
** ok to add the record. Otherwise raise an error because that function_type is already
** being used at the current acct.
IF v_multiples_permitted = 'N'
THEN
RAISE e_multiples_not_permitted;
END IF;
EXCEPTION
WHEN e_multiples_not_permitted
THEN
raise_application_error (-20001,
'Multiples not allowed for function type '
|| v_function_type_code
|| '. sqlerrm - '
|| SQLERRM
WHEN OTHERS
THEN
RAISE;
END;
/:p -
Slow update on 11g in conjuction with before update trigger
Hello,
I have strange problem - when on table exists before update trigger(in its body is nothing important, maybe problem is on other triggers aswell), then repeating update on this table is slower and slower on 11g, on 10g it is ok. Problem is on windows and linux platform aswell.
I created some scripts to simulate this behavior, in table is 60 000 row. In one loop I update all 60 000 rows from table and measure time.
Can someone tell me where problem is and if it is possible to manage it with some settings or anyway ? In our application it is big problem, similar operation takes days ......
thanks tomas
times for 10g:
Trigger disabled
Loop 1 - 6,13 secs
Loop 2 - 2,92 secs
Loop 3 - 3,19 secs
Loop 4 - 2,95 secs
Loop 5 - 3,39 secs
Trigger enabled
Loop 1 - 4,83 secs
Loop 2 - 3,78 secs
Loop 3 - 4,75 secs
Loop 4 - 3,91 secs
Loop 5 - 3,81 secs
times for 11g:
Trigger disabled
Loop 1 - 2,27 secs
Loop 2 - 2,4 secs
Loop 3 - 2,3 secs
Loop 4 - 2,42 secs
Loop 5 - 2,36 secs
Trigger enabled
Loop 1 - 8,01 secs
Loop 2 - 17,22 secs
Loop 3 - 29,21 secs
Loop 4 - 58,43 secs
Loop 5 - 115,59 secs
script for create test table
CREATE TABLE SD3Test
(MPID INTEGER NOT NULL ENABLE,
ROWCOUNT NUMBER(10,0),
CLOSEDROWCOUNT NUMBER(10,0),
AMOUNT NUMBER(18,2) DEFAULT 0 NOT NULL ENABLE,
LOCALAMOUNT NUMBER(18,2) DEFAULT 0 NOT NULL ENABLE,
CLOSED CHAR(1 BYTE) DEFAULT 'N' NOT NULL ENABLE);
ALTER TABLE SD3Test ADD CONSTRAINT SD3TestPK PRIMARY KEY (MPID);
--fill test data
DECLARE mCnt INTEGER;
BEGIN
mCnt := 0;
FOR mCnt IN 1..60000 loop
INSERT INTO SD3Test (MPID, Amount, LocalAmount, RowCount, ClosedRowCount)
VALUES(mCnt, 0, 0, 0, 0);
END loop;
END;
--create trigger
CREATE OR REPLACE TRIGGER SD3TestAU
BEFORE UPDATE ON SD3Test FOR EACH ROW
DECLARE
mInt INTEGER;
BEGIN
/*original code of our trigger, but performance problem is
not depend on it, just depend on existence of this trigger
IF ((:new.RowCount=:new.ClosedRowCount) and (:new.RowCount>0)) THEN
:new.Closed:='A';
ELSE
:new.Closed:='N';
end if;
mInt := 1;
END;
/ script for run test
--test for updates with trigger disabled and enabled
set serveroutput on;
DECLARE
mCnt INTEGER;
mLoop INTEGER;
mDisEna INTEGER;
mStart NUMBER;
mStop NUMBER;
BEGIN
--2 loops - first with disabled trigger, second with enabled trigger
FOR mDisEna IN 1..2 loop
IF mDisEna = 1 THEN
execute immediate 'ALTER TRIGGER SD3TestAU disable';
dbms_output.put_line('Trigger disabled');
ELSE
execute immediate 'ALTER TRIGGER SD3TestAU enable';
dbms_output.put_line('Trigger enabled');
END IF;
-- 3 inner loops for measure time
FOR mLoop IN 1..3 loop
--update on all records in table
mStart := dbms_utility.get_time;
FOR mCnt IN 1..60000 loop
UPDATE SD3Test
SET
ROWCOUNT = ROWCOUNT+1,
CLOSEDROWCOUNT = CLOSEDROWCOUNT+1,
AMOUNT = AMOUNT + mCnt,
LOCALAMOUNT = LOCALAMOUNT + mCnt
WHERE
MPID = mCnt;
END loop;
mStop := dbms_utility.get_time;
dbms_output.put_line('Loop ' || mLoop || ' - ' || round((mStop - mStart)/100,2) || ' secs');
END loop;
END loop;
END;
/Hello,
Your case has been reported as a bug #7173924 (TRIGGER IS MUCH SLOWER IN 11G) few days ago.
Still on analyze.
Nicolas. -
Before Update Trigger has mutating problem
I'm getting a mutating problem with this updating trigger. I'm not sure how to deal with it. Here is my code:
CREATE OR REPLACE TRIGGER WTL_SMP_TRG2
BEFORE UPDATE ON WTL_SAMPLES
FOR EACH ROW
DECLARE
sampleCount NUMBER(1) := 0;
dupLabSampleID NUMBER(8) := 0;
BEGIN
SELECT COUNT(sample_ID)
INTO sampleCount
FROM wtl_samples
WHERE jb_job_id = :new.jb_job_id
AND lab_no = :new.lab_no
AND sample_ID != :old.sample_ID;
IF sampleCount > 0 THEN
SELECT sample_ID
INTO dupLabSampleID
FROM wtl_samples
WHERE jb_job_id = :new.jb_job_id
AND lab_no = :new.lab_no
AND sample_ID != :old.sample_ID;
RAISE_APPLICATION_ERROR(-20501, 'Update failed, Lab Number ' || :new.lab_no || ' is used by SampleID: ' || dupLabSampleID);
END IF;
--EXCEPTION
-- WHEN OTHERS THEN
-- RAISE_APPLICATION_ERROR(-20901, 'Error in WTL_SMP_TRG2.');
END WTL_SMP_TRG2;
any help appreciated
adamI guess I couldve done that, but was using design editor and didn't know how to put a unique constraint in. Is the problem only because I'm referencing the :old.sample_ID, or the :new values as well? If it's just the :old value I could write a before update statement trigger to place the sample_id into a package varaible and then call that variable up in the row level trigger.... i've tried this, but don't know how to pull the sample_id value i need in the before statement trigger... i'll supply the code i've done so far...
CREATE OR REPLACE TRIGGER WTL_SMP_TRG2_INIT
BEFORE UPDATE ON WTL_SAMPLES
DECLARE
BEGIN
wtl_trg_custom_pkg.oldSampleID := sample_id; /* Doesn't know sample_id...? */
END WTL_SMP_TRG2_INIT; -
Before Update Trigger compilation problem
Hello experts! I have a compilation problem for a trigger I am trying to create.
As a matter of fact it should update INT_INITIAL with the old value of INT_LOCK.
The compilation fails and the debugger raises an ORA 01747 error (invalid declaration for user table, user column etc.)
Do you have an idea what is wrong with my code?
create or replace
TRIGGER TRIGGER_INT_INITIAL
BEFORE UPDATE ON TBL_MATRIX_INTERMEDIATE_RESULT
FOR EACH ROW
Begin
IF NVL(:new.INT_INITIAL, 0) != :old.INT_LOCK THEN
UPDATE TBL_MATRIX_INTERMEDIATE_RESULT set
:NEW.INT_INITIAL = :old.INT_LOCK;
END IF;
END;Regards,
SebHi Seb,
You don't need to use UPDATE stmt here as you are updating the same table on which your trigger is fired. So it may cause mutating table error too.
when you use :new.colname it will immediately take care of the new value to be inserted in the respective column.
So no need to write Update stmt.
Hence remove,
UPDATE TBL_MATRIX_INTERMEDIATE_RESULT set And use := is an assignment operator whereas = is to equate..
:=Twinkle -
Help discovering what's wrong w/ my before update trigger
Let me prefix this w/ the fact that I'm an idiot, so be kind.
I have one trigger that is not working (seemingly), and I am about googled out so I thought I'd ask and see if anyone couldn't provide thoughts, insults, suggestions or what have you.
Database being used is 10g XE and updates are being done transactionally.
I have a table that stores (among other things) the status of a particular type of (app specific) transaction. When that status changes to a particular value, I have a trigger that updates another table with the date that this status change took place.
<pre>Table: XTransaction
id (pk)
statusid (int)
...</pre>
and here is what my trigger looks like:
<pre>create or replace trigger x_transaction_update before update on xtransaction
for each row
declare
begin
if( :old.statusid = 1) then -- this is here because I got an error when I tried to use a when clause above
begin
-- I log before the update w/ some other info to tell whether I've been to this spot or not
update sometable set when_it_happened = sysdate where xtransid = :old.id;
-- I log after the update too
exception
when others then
-- I log sqlerrm
end;
end;
end if;
end;</pre>
here's what I've been able to gather through testing & viewing logs from the trigger:
1. there's no exception being logged,
2. the pre/post update logs with all the correct data (proving that the trigger is fired),
3. when I update xtransaction from visual studio (through the oracle addin which lets you run queries against the database), the status is changed, the trigger is fired, and the other table is updated.
4. when the application that normally updates the xtransaction table runs, xtransaction is updated, the trigger is fired, and sometable is not updated.
so I have absolutely no clue where to go with this one. Usually I could fire up sql server's query analyser and watch what's coming through, and I've tried to use toad's commercial tool to do this, but to no avail. I've tried changing it to an after update, but had the same results. I wrote this some months ago, and it was working then, but not now.MadHatter wrote:
@Centinul
the only difference between what I posted and the actual trigger are table / column names, and a sproc I wrote for the logging in place of the comments I have:
log_msg('update sometable set arrival = sysdate where transid = ' || :old.id);I know this doesn't answer the question you have now, you should seriously consider removing the WHEN OTHERS clause altogether OR ensure that there is a RAISE or RAISE_APPLICATION_ERROR there.
This trigger isn't syntactically correct either:
create or replace trigger x_transaction_update before update on xtransaction
for each row
declare
begin
if( :old.statusid = 1) then -- this is here because I got an error when I tried to use a when clause above
begin
-- I log before the update w/ some other info to tell whether I've been to this spot or not
update sometable set when_it_happened = sysdate where xtransid = :old.id;
-- I log after the update too
exception
when others then
-- I log sqlerrm
end;
end; /* Extra END here.... */
end if;
end;Edited by: Centinul on Oct 30, 2009 1:23 PM -
Halting the update from a BEFORE UPDATE trigger
Hello,
I'm writing a trigger which is set to fire before update. One of the possible scenarios requires that the row being updated is not updated but instead deleted. Is it possible to send a DELETE query and then stop the update process so it doesn't spit out an error? I haven't tested this yet, but I'm quite sure it will give an error if it's trying to update a row which has just been deleted.
Thanks,
PavelHi,
Personally, I don't like implement some business logic into trigger... so, why run an update whenever you need a delete ?
I would modify the original code to delete in this case instead of update.
My 2 cents,
Nicolas.
SQL> create table pavel (id number, txt varchar2(10));
Table created.
SQL> insert into pavel values (1, 'This one');
1 row created.
SQL> ed
Wrote file afiedt.buf
1 create or replace trigger pavel_trg
2 before update on pavel
3 for each row
4 begin
5 delete from pavel where id = :old.id;
6* end;
SQL> /
Trigger created.
SQL> update pavel set txt = 'Two';
update pavel set txt = 'Two'
ERROR at line 1:
ORA-04091: table SCOTT.PAVEL is mutating, trigger/function may not see it
ORA-06512: at "SCOTT.PAVEL_TRG", line 2
ORA-04088: error during execution of trigger 'SCOTT.PAVEL_TRG'Message was edited by:
N. Gasparotto -
Before update trigger on a view
Hello,
is not possible to write a before update or insert trigger based on a view?
create or replace trigger trg_bef_upd_vwangajatiabsente
before update on vw_angajati_absente
referencing old as old new as new
for each row
begin
if :old.motivabila='N' and :new.motivabila='D' then raise_application_error(-20433, 'Nu se poate modifica o absenta nemotivabila!');
end;is it possible to solve these situations? :)
Regards,Roger22 wrote:
regarding to 2)
in my trigger i must raise_application_error? if i don't raise then i need to issue update statements..... ?If you have an INSTEAD OF trigger that just has a body similar to the body you posted above, that would mean that update statements either
- Raise an error
- Do nothing (i.e. do not update any data in any table)
That is a syntactically valid state-- Oracle will certainly allow you to have an INSTEAD OF UPDATE trigger that effectively throws away update statements. It's just that it would be rather rare that this would be the desired behavior. Presumably, if you're going through the effort of writing the trigger, you want certain update statements to succeed and, thus, to update data. If that is the case, your trigger would have to have UPDATE statements that update the proper row(s) in the proper base table(s).
An INSTEAD OF UPDATE trigger is literally that. You are replacing, in its entirety, the update statement against the view with the code in your trigger. So your trigger would need to issue the base table updates that Oracle would have had there not been a trigger on the view.
Justin -
After/before update trigger
Hi All
Does any onoe know
what 's the difference between after update/insert trigger and before update/insert trigger
on database tables.Hi
The basic diffrence is
Before Update triggers before the table is updated and
After update triggers after the table is updated but
before the implicit commit fires.
therefore when you raise the application error a
implicit Rollback happens and the record is not commited.
Regards
Shajesh Nair
Deloitte.
[email protected] -
After Update Trigger executes twice when single row is uptd thro proc
We have the below trigger in our db. When a single record is updated using a procedure the trigger is executed twice and it inserts two records in other table.
But when i issue an update statement using any sql client tool it is executing only once and inserts only one record in other table.
Can any one please help me to find the reason?
Trigger:*
create or replace TRIGGER CX_HEADER_ESCL_T1 AFTER UPDATE OF STATUS ON CX_HEADER
FOR EACH ROW
DECLARE
"b1-CTRIYJ" boolean := FALSE;
BEGIN
IF UPDATING('STATUS') AND(:NEW.status = 'SUCCESS') THEN
"b1-CTRIYJ" := TRUE;
END IF;
IF "b1-CTRIYJ" = TRUE THEN
INSERT
INTO siebel.s_escl_req(req_id, created, bt_row_id, rule_id, tbl_name, created_by, group_id)
VALUES('11111111', CURRENT_DATE, :NEW.row_id, '1-CTRIYJ', 'CX_HEADER', :NEW.last_upd_by, '1-2CU3');
"b1-CTRIYJ" := FALSE;
END IF;
END;
Procedure:
CREATE OR REPLACE
PROCEDURE CLOSE_BATCH
(ChildRecordCount IN NUMBER, HeaderId IN VARCHAR2, CompletionStatus OUT VARCHAR2) AS
CafeChildCount NUMBER;
BEGIN
select count(*) into CafeChildCount from SIEBEL.CX_CHILD where HEADER_ID=HeaderId;
IF ChildRecordCount = CafeChildCount THEN
update SIEBEL.CX_HEADER set STATUS ='SUCCESS', MODIFICATION_NUM = MODIFICATION_NUM+1 where HEADER_ID=HeaderId;
CompletionStatus := 'SUCCESS';
ELSE
update SIEBEL.CX_CHILD set STATUS='FAILED' where HEADER_ID=HeaderId;
update SIEBEL.CX_HEADER set STATUS='FAILED' where HEADER_ID=HeaderId;
CompletionStatus := 'FAILED';
END IF;
commit;
/*CompletionStatus := 'SUCCESS';*/
EXCEPTION
WHEN OTHERS THEN
CompletionStatus := SQLCODE;
rollback;
END;Your problem seems not be related to the trigger restart issue I have already mentioned because you are using a AFTER UPDATE trigger and not a BEFORE UPDATE trigger:
>
BEFORE Triggers Fired Multiple Times
If an UPDATE or DELETE statement detects a conflict with a concurrent UPDATE, then Oracle Database performs a transparent ROLLBACK to SAVEPOINT and restarts the update. This can occur many times before the statement completes successfully. Each time the statement is restarted, the BEFORE statement trigger is fired again. The rollback to savepoint does not undo changes to any package variables referenced in the trigger. Your package should include a counter variable to detect this situation.
>
If you are sure that you update a single row and that your trigger fires twice and if you can easiily reproduce the issue, I recommend that you contact Oracle Support and create a Service Request for your issue that could be an Oracle bug. -
Update Trigger: New Value
Hi, I am in a strange situation, hope some one can help me. I have a BEFORE UPDATE trigger in which I have a condtion like.
IF :new.col1 is NULL THEN
:new.col1 := 'AA';
END IF;
My aim is if col1 set to NULL or col1 is not included in update statement then value 'AA' should be assigned to col1.
This works fine in following cases
1) If UPDATE statement set col1 to NULL explicitly
2) If :old.col1 is NULL and col1 is not included in update statement
But not working when
3) :old.col1 IS NOT NULL and col1 is not included update statement.
I want value 'AA' should assigned to col1 in case 3 also. Is there any way ?
Thanks.I don't think that this can be done through the trigger alone, because the trigger cannot distinguish between the two cases where ...
i) col1 is not mentioned in the update, and ...
ii) col1 is mentioned but is updated from a non-null value to the same value. -
Help on creating update trigger(urgent)
Hii all,
I have a situation like this
I have 10 different tables like a,b,c,d,e,f
But i have same columns in all tables
like
updated_by,
updated_date
I need to create a procedure and call that procedure in update triggers for all tables
Can anybody help
In creating Procedure and trigger
ThanksThere is nothing wrong with the trigger, but the procedure is another story. You cannot do DML on the table that is firing the trigger inside the trigger, that is the mutating table error.
I am not really sure why you are doing the DML anyway. you have defined a BEFORE UPDATE trigger on k_constituent, and the procedure checks for the existence of a row in the same table where the currt_user_id field is the same as the id of the user making the update. Without knowing anything about the application, this implies one of two things to me. Either you are trying to make sure the row to be updated does exist, or, this is some kind of security check.
If it is the first, then it is unneccessary, since the before update trigger will only fire if the row to be updated exists viz.
SQL> CREATE OR REPLACE TRIGGER jt_bu
2 BEFORE UPDATE ON JTEST
3 FOR EACH ROW
4
5 BEGIN
6 :new.updby := USER;
7 :new.updon := SYSDATE;
8 DBMS_OUTPUT.Put_Line('Trigger fired ok');
9 END;
10 /
Trigger created.
SQL> SELECT * FROM jtest;
ID DESCR UPDBY UPDON
1 YES OPS$ORACLE 24-APR-03
2 NEWDES OPS$ORACLE 23-APR-03
3 ORACLE OPS$ORACLE 23-APR-03
SQL> UPDATE jtest SET descr = 'NO' WHERE id = 1;
Trigger fired ok
1 row updated.
SQL> UPDATE jtest SET descr = 'NO' WHERE id = 5;
0 rows updated.If you are doing this for security, then you are way too late. The user should not be in the database doing updates if they are not a valid user (whatever valid user means to you).
As a side note, you do realize that if there is more than one record in k_constituent with currt_user_id = updating user, then the procedure will not set update_date and update_by?
TTFN
John -
Oracle version 9.2.0.1.
I've got a "before" update trigger that fires whenever I change an existing value in the table but it doesn't fire when I delete a value or add a value that had previously been empty. It feels like I'm missing something that's probably pretty basic - many thanks for anyone who can point me in the right direction.Something like
CREATE OR REPLACE TRIGGER <trigger_name>
BEFORE INSERT OR DELETE OR UPDATE ON <table_name>
<trigger_body>Regards
Peter -
I am getting a trigger error when updating a table. Here is the trigger :
CREATE OR REPLACE TRIGGER "SCHEMA"."UPD_SOMETABLE" AFTER
UPDATE ON "SCHEMA"."UPD_SOMETABLE" REFERENCING OLD AS OLD NEW AS NEW FOR EACH ROW BEGIN
UPDATE "SCHEMA"."UPD_SOMETABLE" SET "DATE_UPDATED" = SYSDATE
END;
ALTER TRIGGER "SCHEMA"."UPD_SOMETABLE" ENABLE;
The error :
SQL Error: ORA-04098: trigger 'SCHEMA.UPD_SOMETABLE' is invalid and failed re-validation
04098. 00000 - "trigger '%s.%s' is invalid and failed re-validation"
*Cause: A trigger was attempted to be retrieved for execution and was
found to be invalid. This also means that compilation/authorization
failed for the trigger.
*Action: Options are to resolve the compilation/authorization errors,
disable the trigger, or drop the trigger.The syntax error is the lack of a semicolon after SYSDATE. There is also an error that the table name and trigger name are the same but I'm guessing that's something you did in sanitizing the code before posting it
Once you fix the syntax error, however, you're very likely to get a runtime mutating table error.
If your intention is to set the DATE_UPDATED column to SYSDATE for each row that is updated, you'd need to use a before update trigger, you'd adjust the :new.date_updated, and you'd fix the syntax error. Something like
CREATE OR REPLACE TRIGGER trigger_name
BEFORE UPDATE ON table_name
FOR EACH ROW
BEGIN
:new.date_updated := sysdate;
END;If you are trying to do something other than what I guessed above, please let us know what you are trying to get the trigger to do.
Justin -
Hello,
I'm building an interface to a 3rd party system and I'm pushing data to an interface table. And I was wondering if anyone could help me on this problem that I'm having. I have a table, call it Table "A", and this is the table that the user enters data into via a Portal Form. Then I have created a procedure that extracts the data in table A to the interface table. However, once the data is in the interface table, I don't what the user to be able to update the record in table A. How do I handle this situation? Can it be something on the Portal Form or does it have to be something on the back-end, say a before update trigger? Any help would be appriciated!!
Thanks,
MartinThanks for posting your question under the correct topic :)
As I've answered you [here |http://forums.oracle.com/forums/thread.jspa?threadID=922047&tstart=0] :
You should use :OLD value to catch value that was before update
Please refer to documentation for "step by step" explanation
http://download.oracle.com/docs/cd/B19306_01/server.102/b14200/statements_7004.htm#sthref7885
Kamran Agayev A. (10g OCP)
http://kamranagayev.wordpress.com
[Step by Step install Oracle on Linux and Automate the installation using Shell Script |http://kamranagayev.wordpress.com/2009/05/01/step-by-step-installing-oracle-database-10g-release-2-on-linux-centos-and-automate-the-installation-using-linux-shell-script/]
Maybe you are looking for
-
Router works for OS X, Not Windows XP
I have a Linksys BEFW11S4 ver. 4 wireless router with the lastest firmware. I also have an Apple Macbook running Boot Camp with Windows XP Pro. I can connect and use the router on OS X just fine but I am unable to connect under Windows XP. It just ke
-
How to retrive new logical column based on flag values in table.
Hi, i have two tables in rpd 1.file table contains the coulmns------->date,file_count,record_count,cldm_stg,cmsa_stg,archive_stg 2.rejection table columns---------> are same as above both have same common columns.my requirement is publish a dashboard
-
Hi experts, I want to create a generic data source related to purchasing for these fields.Anyone please provide me exact tables of these fields 1.MWSKZ Tax code 2.KBETR Condition amount 3.KWERT Condition Value 4.SORT1 Search Term 5.SO
-
When the magnifier in Ancestry's document viewer is used (for example to view one small part of a Census image at a larger magnification), it is impossible to remove the cursor from the image without CTRL-ALT-DEL, which releases it instantly. Findmyp
-
Can I buy an unlock iphone 5 in US now? If I can, how many business days can I get it? Thank you!