CREATE TRIGGER x AFTER INSERT ON itemtype
FOR EACH ROW
DECLARE
minn itemtype.PRICE%type;
BEGIN
select MIN(itemtype.PRICE) into minn from itemtype;
IF (:new.PRICE > minn*4) then RAISERROR('Custom text');
END IF;
END;
/
I'm trying to create a trigger that raises an error when I try to insert a new entry into the itemtype with itemtype.PRICE column value is greater than 4 times the current low priced item on the table.
I get these compilation errors when I try to create the trigger.
LINE/COL ERROR
-------- --------------------------------------------------------------
5/31 PL/SQL: Statement ignored
5/31 PLS-00201: identifier 'RAISERROR' must be declared
I have also tried
CREATE TRIGGER x AFTER INSERT ON itemtype
FOR EACH ROW
DECLARE
minn itemtype.PRICE%type;
BEGIN
select MIN(itemtype.PRICE) into minn from itemtype;
if (:new.PRICE > minn*4) then raise_application_error(-20010,'Too Expensive');
END IF;
END;
/
which complies, but when i try to insert a new entry into the table I get theses errors saying my trigger fails.
SQL> insert into itemtype(ITEMNUM,NAME,PICTURE,PRICE,BELONGSTO ) VALUES ('A11','The who knows','',10.99,'P');
insert into itemtype(ITEMNUM,NAME,PICTURE,PRICE,BELONGSTO ) VALUES ('A11','The who knows','',10.99,'P')
*
ERROR at line 1:
ORA-04091: table USERNAME.ITEMTYPE is mutating, trigger/function may not see it
ORA-06512: at "USERNAME.X", line 5
ORA-04088: error during execution of trigger 'USERNAME.X'
Try use PRAGMA AUTONOMOUS_TRANSACTION in trigger.
Look my answer on this question:
SQL trigger on delete mutating table
Related
enter image description here CREATE OR REPLACE TRIGGER weekd_tri
BEFORE INSERT OR UPDATE ON payment
FOR EACH ROW
BEGIN
IF TO_CHAR(SYSDATE, 'D') = '1' THEN
RAISE_APPLICATION_ERROR(-20000, 'Cannot make a payment on weekends');
END IF;
END;
error msg
ORA-06512: at "SCOTT.WEEKD_TRI", line 3
ORA-04088: error during execution of trigger 'SCOTT,WEEKD_TRI
can you tell me why i'm getting this error and how to solve this error
*
*this trigger should not accept payment by customer when made on Sat/Sun so i wrote this trigger but when I stried to insert data on Sun it did Fire a triger ORA - 20000 Cannot make a payment on weekends and I was not able to update the values but apart from that I got the other two Erros ORA-06512 & ORA:04088 **
As from your screenshot I see there are 3 error message lines
ORA-20000 - which is the real error message that has been caused from your logic
ORA-6512 - service message to identify the line of code error occured
ORA-4088 - another service message to identify trigger name where error occured
So, the reason why you're getting ora-4088 is raise_application_error command you're using for exception firing. It is just a part of service message for developers
There's no "error", except the one you created yourself, intentionally.
Which day is it today?
SQL> select to_char(sysdate, 'D') from dual;
T
-
1 --> OK, that's the value you're checking in a trigger
SQL>
Sample table:
SQL> create table payment (id number);
Table created.
Trigger:
SQL> create or replace trigger weekd_tri
2 before insert or update on payment
3 for each row
4 begin
5 if to_char(sysdate, 'D') = '1' then
6 raise_application_error(-20000, 'Cannot make a payment on weekends');
7 end if;
8 end;
9 /
Trigger created.
Testing:
SQL> insert into payment (id) values (1);
insert into payment (id) values (1)
*
ERROR at line 1:
ORA-20000: Cannot make a payment on weekends
ORA-06512: at "SCOTT.WEEKD_TRI", line 3
ORA-04088: error during execution of trigger 'SCOTT.WEEKD_TRI'
Right; that's EXACTLY what you wanted to do: IF concluded that today really is '1' and raised an error.
If it were e.g. '2' you checked, today you'd be able to insert a row:
SQL> create or replace trigger weekd_tri
2 before insert or update on payment
3 for each row
4 begin
5 if to_char(sysdate, 'D') = '2' then
6 raise_application_error(-20000, 'Cannot make a payment on weekends');
7 end if;
8 end;
9 /
Trigger created.
SQL> insert into payment (id) values (2);
1 row created.
SQL>
I am new with mysql triggers, I have 2 tables in a database, one is called tasks and the other is task_rules.
Once a new task_rule is inserted, I want to compare the field time (which is a time object) to the current time.
if it is greater than the current time, I want to add a new row in tasks and set rid (in tasks) to id of the newly added rule, and the time field in tasks to the time field of the newly added row.
I am getting many syntax errors and i didnt know how to create this trigger.
BEGIN
DECLARE #time TIME
DECLARE #freq VARCHAR(400)
#time = NEW.time
#freq = NEW.frequency
IF (#time > NOW()) AND (#freq == 'daily') THEN
INSERT INTO task_rules ('rid', 'time') VALUES (NEW.id, #time)
END IF
END
Im doing it using phpmyadmin
1) user defined variable (those preceded with #) should not be declared see How to declare a variable in MySQL? 2) to assign a value to a variable you have to use the SET statement 3) every statement must be terminated - if you are using phpmyadmin and the default terminator is set to ; change it and terminate your statements in the trigger with ; see - https://dev.mysql.com/doc/refman/8.0/en/stored-programs-defining.html 4) null safe equals in mysql is not == from memory this should be <=> see https://dev.mysql.com/doc/refman/8.0/en/comparison-operators.html 5) you should probably set delimiters before and after the trigger 6) column names should be escaped with back ticks not single quotes. 7) for each row clause missing before begin statement.
try this
drop trigger if exists t;
delimiter $$
create trigger t after insert on task
for each row
BEGIN
DECLARE vtime TIME;
DECLARE vfreq VARCHAR(400);
set time = NEW.time;
set freq = NEW.frequency;
IF (vtime > NOW()) AND (vfreq <=> 'daily') THEN
INSERT INTO task_rules (`rid`, `time`) VALUES (NEW.id, vtime);
END IF;
END $$
delimiter ;
And do review https://dev.mysql.com/doc/refman/8.0/en/trigger-syntax.html
I have this trigger in mysql which works fine:
CREATE TRIGGER ins_trainee AFTER INSERT ON trainee
FOR EACH ROW UPDATE training_activities SET NO_of_Trainees =
( SELECT COUNT(SN)
FROM trainee
WHERE trainee.training_type = training_activities.SN
)
And I tried converting to oracle like this:
CREATE OR REPLACE TRIGGER ins_trainee
AFTER INSERT ON trainee
FOR EACH ROW
BEGIN
UPDATE training_activities SET NO_of_Trainees =
SELECT COUNT(SN)
FROM trainee
WHERE trainee.training_type = training_activities.SN;
END;
/
But I get warning: trigger created with compilation errors
And show errors gives:
2/1 PL/SQL: SQL Statemnet Ignored
2/49 PL/SQL: ORA-00936: missing expression
I am trying to convert this tsql to mysql but showing error need help
CREATE PROCEDURE FormAdd
#formName varchar(MAX)
AS
IF NOT EXISTS(SELECT * FROM tbl_Form WHERE formName=#formName)
BEGIN
INSERT INTO tbl_Form
(formName)
VALUES
(#formName)
SELECT ##identity
END
ELSE
BEGIN
SELECT '-1'
END
mysql
CREATE PROCEDURE FormAdd
(p_formName varchar(500) )
begin
INSERT INTO tbl_Form (formName)
VALUES (p_formName)
where NOT EXISTS(SELECT * FROM tbl_Form WHERE formName=p_formName) ;
SELECT Last_insert_id() as returnvalue ;
SELECT '-1' ;
end
Your attempt was syntactically invalid because logically, an INSERT statement cannot contain a WHERE clause since it does not act on existing rows.
If the purpose is to insert only if the value for p_formname is not already present, then an appropriate step would be to define a unique index on that column first. Then, construct your procedure to attempt the insert and inspect the ROW_COUNT() value to see if one was inserted and act accordingly, returning -1 if not to adapt your existing T-SQL procedure.
First create the unique index on p_formname:
ALTER TABLE tbl_Form ADD UNIQUE KEY `idx_formName` (`formName`);
Then your procedure should use INSERT INTO...ON DUPLICATE KEY UPDATE to attempt to insert the row. Per the documentation, the value of ROW_COUNT() will be 0 if a new row was not inserted or 1 if it was.
CREATE PROCEDURE FormAdd (p_formName varchar(500))
BEGIN
/* Attempt the insert, overwrite with the same value if necessary */
INSERT INTO tbl_Form (formName) VALUES (p_formName) ON DUPLICATE KEY UPDATE formName = p_formName;
/* Return the LAST_INSERT_ID() for a new row and -1 otherwise */
SELECT
CASE
WHEN ROW_COUNT() = 1 THEN LAST_INSERT_ID()
ELSE -1
END AS returnValue;
END
I have created a mysql trigger to update on insert a value from another table:
DROP TRIGGER IF EXISTS `CourseCode`//
CREATE TRIGGER `CourseCode` BEFORE INSERT ON `race`
FOR EACH ROW BEGIN
SET NEW.Course_Code = (
SELECT
course_code
from
tb_course
where
tb_course.course_name = NEW.course_name
)
END
//
This works perfectly. It returns the 4 character code for the course_name based on the tb_course table.
What I'm trying to do is the exact same thing in another table, I copy and paste the trigger and rename the trigger and the table (field names and types are also identical) it but it won't work:
DROP TRIGGER IF EXISTS `CourseCode2`//
CREATE TRIGGER `CourseCode2` BEFORE INSERT ON `fields`
FOR EACH ROW
BEGIN
SET NEW.Course_Code = (
SELECT
course_code
from
tb_course
where
tb_course.course_name = NEW.course_name
)
END
//
However this results in null values. I've tried replacing New.Course_name with a string (i.e. tb_course.course_name="String") and that updates that static value fine so the trigger appears to be working but either it isn't matching the select statement in this table for or it's not setting the Course_Code field...
Is there any sort of debugging you can suggest to figure this out? It's driving me nuts and I don't know what to do to diagnose the problem.
Cheers
I have no idea what is wrong with the second trigger.
However, the 'debugging' part i can maybe help with.
A search of the 'net' will return various software (paid for) that will allow single step debugging. Rather than pay for stuff, all i want is 'print' statements from inside stored function procedures and triggers.
a quick search lead me to someone who has done all the work already.
Debugging Stored Procedures in MySql
I have just set it up in MySql and tried it and it works fine.
Here is some sample code, based on your trigger and the output i got.
DELIMITER $$
USE `testmysql`$$
DROP TRIGGER /*!50032 IF EXISTS */ `CourseCode`$$
CREATE
/*!50017 DEFINER = 'test'#'localhost' */
TRIGGER `CourseCode` BEFORE INSERT ON `race`
FOR EACH ROW BEGIN
DECLARE v_course_code INT;
DECLARE v_course_title VARCHAR(255);
CALL procLog("line 12: Entering CourseCode");
SELECT
course_code, course_title
INTO
v_course_code, v_course_title
FROM
tb_course
WHERE
tb_course.course_name = NEW.course_name;
SET NEW.course_code = v_course_code;
CALL procLog(CONCAT("line_22: ", v_course_title, " code: ", NEW.course_code));
CALL procLog("line 24: Exiting CourseCode");
END;
$$
DELIMITER ;
Query:
CALL setupProcLog();
INSERT INTO `race` (course_name, race_info)
VALUES ('learn_it_02', 'this is another test');
CALL cleanup('query end');
procLog output:
entrytime connection_id msg
2014-02-23 12:32:21 5 line 12: Entering CourseCode
2014-02-23 12:32:21 5 line_22: Learn It Course 02 code: 2
2014-02-23 12:32:21 5 line 24: Exiting CourseCode
2014-02-23 12:32:21 5 cleanup() query end
Ok, a little clumsy maybe but it will help with debugging 'stored' programs.
I will be using it from now on.