Trigger to prevent Any Deleting from Table - sql

a trigger for this new rental history table that prevents deletions from the table.
CREATE OR REPLACE TRIGGER RENTALHIS_DEL
BEFORE DELETE ON RENTALHISTORY
BEGIN
dbms_output.put_line( 'Records can not be deleted');
END;
DELETE FROM RENTALHISTORY WHERE RENTALID = 1;
-- It is deleting before it says it can not delete
1 rows deleted.
Records can not be deleted

dbms_output.put_line( 'Records can not be deleted');
The above just prints the text and trigger completes successfully and then delete happens anyway. What you wanna do instead is to raise an error to prevent the program from completing.
Use standard procedure raise_application_error to stop the program and raise error:
CREATE OR REPLACE TRIGGER RENTALHIS_DEL
BEFORE DELETE ON RENTALHISTORY
BEGIN
raise_application_error(-20001,'Records can not be deleted');
END;
/

You want to raise an error, not print a message. The delete happens anyway:
CREATE OR REPLACE TRIGGER RENTALHIS_DEL
BEFORE DELETE ON RENTALHISTORY
BEGIN
RAISE_APPLICATION_ERROR (-20000, 'Deletion not supported on this table');
END;
Alternatively, you could use an instead of trigger to prevent the delete from taking place:
CREATE OR REPLACE TRIGGER RENTALHIS_DEL
INSTEAD OF DELETE ON RENTALHISTORY
BEGIN
dbms_output.put_line( 'Records cannot be deleted');
END;

You can make use of commit after your delete statement and rollback after that to reach to the previous stage using Pragma.
CREATE OR REPLACE TRIGGER
RENTALHIS_DEL
AFTER DELETE ON RENTALHISTORY
DECLARE
PRAGMA
AUTONOMOUS_TRANSACTION;
BEGIN
RAISE_APPLICATION_ERROR
(-20000, 'Deletion getting rolled
back');
ROLLBACK;
END;

Related

Multiple WHEN Statements in Oracle SQL

Can I get some help on below SQL trigger. Something is wrong with using multiple "WHEN" statements.
create or replace TRIGGER TRANS_TASKS_TRIG02
BEFORE INSERT OR UPDATE ON "TASKS"
REFERENCING FOR EACH ROW
WHEN(NEW.STATUS='WIP') BEGIN
IF INSERTING OR UPDATING THEN
:NEW.UPDATED_DATE := NEW_TIME(SYSDATE, 'GMT', 'PDT' );
END IF;
WHEN(NEW.STATUS<>'WIP') BEGIN
IF INSERTING OR UPDATING THEN
:NEW.UPDATED_DATE := NULL;
END IF;
END;
According to Oracle's documentation, you can't have multiple when clauses in a trigger.
You could create to separate triggers:
create or replace TRIGGER TRANS_TASKS_TRIG02_WIP
BEFORE INSERT OR UPDATE ON "TASKS"
REFERENCING FOR EACH ROW
WHEN(NEW.STATUS='WIP') BEGIN
IF INSERTING OR UPDATING THEN
:NEW.UPDATED_DATE := NEW_TIME(SYSDATE, 'GMT', 'PDT' );
END IF;
END;
create or replace TRIGGER TRANS_TASKS_TRIG02_WIP
BEFORE INSERT OR UPDATE ON "TASKS"
REFERENCING FOR EACH ROW
WHEN(NEW.STATUS<>'WIP') BEGIN
IF INSERTING OR UPDATING THEN
:NEW.UPDATED_DATE := NULL;
END IF;
END;
Or have a single trigger with an if statement in it. Note that the if inserting or updating condition is redundant, since the trigger is invoked only before insert or update:
create or replace TRIGGER TRANS_TASKS_TRIG02
BEFORE INSERT OR UPDATE ON "TASKS"
REFERENCING FOR EACH ROW
BEGIN
IF :NEW.STATUS='WIP' THEN
:NEW.UPDATED_DATE := NEW_TIME(SYSDATE, 'GMT', 'PDT' );
ELSIF :NEW.STATUS<>'WIP' THEN
:NEW.UPDATED_DATE := NULL;
END IF;
END;
/

Postgres trigger check amount before delete

I am trying to create a postgres before trigger to check the amount of records that are going to be deleted before it actually does. For example to not delete more than 5 records
You could achieve that with an AFTER DELETE statement-level trigger. Inside the trigger function you can count the number of affected rows and throw an exception if the count is too high. The exception will force a rollback of the transaction that initiated the delete.
create function prevent_delete()
returns trigger
as
$BODY$
declare
l_count integer;
begin
select count(*)
into l_count
from old_table;
if l_count > 5 then
raise exception 'Too many rows would be deleted';
end if;
return null;
end;
$BODY$
LANGUAGE plpgsql;
And then create the trigger:
create trigger prevent_mass_delete
after delete on the_table
referencing old table as old_table
for each statement
execute procedure prevent_delete();

Oracle 12c AFTER INSERT OR UPDATE TRIGGER

I Have a following trigger, which updates but and rolling back automatically, I'm not finding what is the cause, kindly help.
FYI: updating table UDF_DATA has a foreign key reference to CCEX.CUSTOMER triggering table.
CREATE OR REPLACE TRIGGER TR_CUSTOMER_PM
AFTER INSERT OR UPDATE ON CCEX.CUSTOMER FOR EACH ROW
DECLARE
i_subscriber_id Number :=3080;
user_xcep EXCEPTION;
PRAGMA EXCEPTION_INIT( user_xcep, -20001 );
pragma autonomous_transaction;
i_syscode ccex.customer.cust_system_code%type;
BEGIN
IF :new.cust_account_number like 'TID%' THEN
i_syscode:= :new.cust_system_code;
update udf_data set value = 'Term'
where subscriber_id = i_subscriber_id
and cust_system_code = i_syscode
and entity_id = '1488_OTA'
and udf_id = '3994_OTA'
and name = 'Primary Manager';
END IF;
EXCEPTION
when others then
raise user_xcep;
END;
/
Since the trigger is in autonomous_transaction mode, it should close the transaction.
Please add commit just before the exception line.

SQL trigger to show salary change

I am trying to create a simple trigger in sql developer to display the change in salary when it is changed
CREATE OR REPLACE TRIGGER salary_changes
BEFORE DELETE OR INSERT OR UPDATE ON FACULTY
FOR EACH ROW
DECLARE
sal_diff NUMBER;
BEGIN
sal_diff := :NEW.F_SALARY - :OLD.F_SALARY;
DBMS_OUTPUT.PUT_LINE('Difference: ' || sal_diff);
END;
when I attempt to run the trigger it prompts be to enter binds for NEW and OLD and when i try run an update to see if it works it states the trigger failed. So how am i using the old and new tags incorrectly? or is that not the issue
There are several issues with your code.
You need to create a after trigger instead of the before trigger.
You are trying to write a trigger that performs an operation for
insert,delete or update. So you should do the conditional checks
(such as if inserting,deleting or updating) clause.
Also, when you do delete, there is no new value, but just the old
value.
I would change your trigger as below..
CREATE OR REPLACE TRIGGER salary_changes
AFTER DELETE OR INSERT OR UPDATE ON FACULTY
FOR EACH ROW
DECLARE
sal_diff NUMBER;
BEGIN
If (INSERTING or UPDATING) then
sal_diff := :NEW.F_SALARY - :OLD.F_SALARY;
DBMS_OUTPUT.PUT_LINE('Difference: ' || sal_diff);
END IF;
IF DELETING THEN
DBMS_OUTPUT.PUT_LINE('The deleted value is:' || :OLD.F_SALARY);
END IF;
END;

How to create a trigger that fires after an update in PL/SQL

I will like to create a trigger, that when Movie_Qty in the Fin_Movie table is updated to a 0, the message "(Movie Title) is no longer available"
This is what I have so far:
CREATE TRIGGER movie_trg
AFTER UPDATE OF movie_qty
ON fin_movie
FOR EACH ROW
WHEN (new.movie_qty = 0)
BEGIN
DBMS_OUTPUT.PUT_LINE(' will no longer be available');
END;
It compiles, but I dont know how display the movie_title before in the output.
Thank you
CREATE OR REPLACE
TRIGGER SAL_TRG1 AFTER UPDATE ON EMPC
FOR EACH ROW
begin
if (:new.salary =0) then
raise_application_error (-20110,'invalid length');
end if;
end;