how to check if row exist with trigger in mysql? - mysql

I want to check if a row exist with a trigger before insert here is my table and my trigger
Table students: ID | Name
Trigger validation :
CREATE TRIGGER `validation` BEFORE INSERT ON `students`
FOR EACH ROW
begin
declare var_name varchar(255);
declare check_row varchar(255);
set var_name = new.name;
select name into check_row from students where name = var_name;
end

If you are using a stored procedure, you can accomplish this with a handler if the column has a unique key on it
CREATE PROCEDURE `student_create` (IN name_in VARCHAR(64), ...)
BEGIN
SET #name = name_in;
DECLARE EXIT HANDLER FOR SQLSTATE '23000'
SET #name = CONCAT('dupe_',name_in);
INSERT INTO students (name, ...) VALUES (#name, ...);
END$$
If you are really set on using a trigger, all you need is an if
IF (SELECT id FROM students WHERE name = NEW.name) THEN
SET var_name = CONCAT('dupe_',NEW.name);
END IF;
Replace the CONCAT with whatever transformation you want perform on the name

Related

Update the same row after insert Inside the trigger

I have to use a trigger that will update the inserted row. Following is my trigger.
DELIMITER $$
USE `kikan_db`$$
CREATE TRIGGER `t_trigger` AFTER INSERT ON `t_order`
FOR EACH ROW BEGIN
Declare kb_rate int;
Declare kb_amount int;
REPLACE INTO t_order_sales_month
SET order_no = NEW.order_no,
search_sales_month = getSalesMonth(NEW.order_no);
SELECT kickback_rate INTO kb_rate from m_customer where customer_code = New.bill_customer_code;
SET kb_amount := 9999 / kb_rate;
UPDATE `t_order` SET `t_order`.kickback_amount = kb_amount where `t_order`.order_no = NEW.order_no;
END;
$$
DELIMITER ;
Getting error at update.
It is mandatory for me to use AFTER instead of BEFORE type of trigger
Instead of using only after insert/update trigger, (1) you can change the value of virtual new row on before insert/update :
Declare kb_rate int;
Declare kb_amount int;
SELECT kickback_rate INTO kb_rate from m_customer
where customer_code = New.bill_customer_code;
SET kb_amount := 9999 / kb_rate;
SET new.kickback_amount = kb_amount;
(2)And execute the other SQL statements in a after insert/update trigger:
REPLACE INTO t_order_sales_month
SET order_no = NEW.order_no,
search_sales_month = getSalesMonth(NEW.order_no);

How to create dynamic where conditions according to the parameter in stored procedure in mysql?

I have created a stored procedure in which I want to list employees according to the parameter.
The procedure has some parameters, one of them I want to use for the type(eg:branch, department etc) and the other is the id corresponding to that.
I want to create where conditions to variable.
How can I do that?
DELIMITER $$
CREATE PROCEDURE Emp_details(IN div_type VARCHAR(100), IN id INT, OUT emp_name VARCHAR(100))
BEGIN
DECLARE cond VARCHAR(100);
IF div_type = 'branch' THEN
SET cond = 'branch_id='+id;
ELSEIF div_type = 'department' THEN
SET cond = 'department_id='+id;
ELSEIF div_type = 'emp' THEN
SET cond = 'employee_master_id='+id;
ELSE
SET cond = '';
END IF;
SELECT
emp_fullname INTO emp_name
FROM armr_employee_master
WHERE +cond ;
END$$
Just turn the IF into a WHERE:
SELECT emp_fullname
INTO emp_name
FROM armr_employee_master
WHERE id = CASE div_type
WHEN 'branch' THEN branch_id
WHEN 'department' THEN department_id
WHEN 'emp' THEN employee_master_id
END

mysql insert statement as a variable [duplicate]

This question already has answers here:
How To have Dynamic SQL in MySQL Stored Procedure
(3 answers)
Closed 8 years ago.
is it possible to set a variable to an insert statement in a stored procedure?
Something like:
set variable1 = insert into table(field1, field2, field3) values(val1, val2, variable2);
If so, how should it be written?
I keep throwing errors and documentation in the wild is inconclusive.
I was going for brevity but the entire procedure is thus:
-- --------------------------------------------------------------------------------
-- Routine DDL
-- Note: comments before and after the routine body will not be stored by the server
-- --------------------------------------------------------------------------------
DELIMITER $$
CREATE DEFINER=`root`#`localhost` PROCEDURE `new_accession`(in barcode int, in accepted varchar(11), in wt float(11,2), in wtunit varchar(3),in draw date, in chist varchar(256), in ghist varchar(256), in meds varchar(256), in diffdiag varchar(256),in diseasesus varchar(256),in volume int, in facility int, in patient int, in employ int, in compromised int, in receiving int, in test int)
BEGIN
declare accessionId int;
declare accessionTest int;
declare tkInsert varchar(256);
declare hptInsert varchar(256);
declare calInsert varchar(256);
declare pthInsert varchar(256);
declare vitdtkInsert varchar(256);
declare cnpInsert varchar(256);
if wtunit = 'lb' then set wt = convertLbKg(wt);
end if;
INSERT INTO accession(barcode_accession,accepted_accession,weight_accession,req_weight_units,draw_date_accession,cancer_history_accession,general_history_accession,medication_accession,differential_diagnosis_accession,disease_suspect_accession,volume_accession,facility_doctor_index_id_facility_doctor_index,patient_id_patient,employee_id_employee,accession_compromised_id_accession_compromised,receiving_id,accession_typeof_id_accession_typeof)
VALUES (barcode,accepted,wt,wtunit,draw,chist,ghist,meds,diffdiag,diseasesus,volume,facility,patient,employ,compromised,receiving,1);
set accessionId = last_insert_id();
set tkInsert = insert into pending(accession_facility_index,reagent_type,`status`)values(accessionId,1,'Pending');
set hptInsert = insert into pending(accession_facility_index,reagent_type,`status`)values(accessionId,2,'Pending');
set calInsert = insert into pending(accession_facility_index,reagent_type,`status`)values(accessionId,3,'Pending');
set pthInsert = insert into pending(accession_facility_index,reagent_type,`status`)values(accessionId,4,'Pending');
if test = 1 then tkInsert,calInsert;
elseif test =2 the hptInsert,pthInsert;
else pthInsert;
end if;
END
It is not very clear what you want but if your goal is to store insert's outcome (affected rows) you could use ROW_COUNT().
ROW_COUNT() returns the number of rows changed, deleted, or inserted
by the last statement if it was an UPDATE, DELETE, or INSERT.
For other statements, the value may not be meaningful.
For example:
variable1 = (select ROW_COUNT());
I think you're looking for prepared statements.
PREPARE tkInsert FROM CONCAT("insert into pending(accession_facility_index,reagent_type,`status`)values(?, 1,'Pending')";
Then you execute it with:
EXECUTE tkInsert USING accessionId;

How to Insert Data with Mysql Trigger After Insert?

This is the database vehicle table's trigger
DROP TRIGGER IF EXISTS InsertVehTrig;
DELIMITER $$
CREATE TRIGGER InsertVehTrig AFTER INSERT
ON Vehicle FOR EACH ROW
SWL_return:
BEGIN
DECLARE Cph CHAR(50);
DECLARE DevID CHAR(12);
DECLARE VehID BIGINT;
DECLARE TmpID BIGINT;
DECLARE DevCount INT;
SET Cph = rtrim(ltrim(NEW.cph));
SET VehID = NEW.ID;
SET DevID = NEW.DevID;
if(VehID is null) then
select count(id) into #DevCount from vehicle where (cph=#Cph) or (DevID=#DevID);
-- 条件:当前的车牌号 或 设备ID
end if;
if (DevCount > 1) then -- 如果记录数,超过1,则认为有重复
-- Rollback not supported in trigger
SET #SWV_Null_Var = 0;
Leave SWL_return;
else
if (DevCount = 1) then
select ID INTO #TmpID from Vehicle where (Vehicle.cph = #Cph) or (Vehicle.DevID = #DevID);
if (TmpID != VehID) then -- --如果增加的车牌号码与数据库中的在相同的,则不允许增加
-- Rollback not supported in trigger
Leave SWL_return;
SET #SWV_Null_Var = 0;
end if;
end if;
end if;
update vehicle set cph = #Cph where ID = #VehID;
END;
Right now i m trying to insert new data row in the vehicle table, but error with this
ERROR 1442: Can't update table 'vehicle' in stored function/trigger because it is already used by statement which invoked this stored function/trigger.
SQL Statement:
INSERT INTO `gis_server`.`vehicle` (`TrackerNum`, `cph`, `DevID`, `DevType`) VALUES ('1', 'NR09B00555', 'NR09B00555', '2')
those database are designed by 3 party company,
How do i insert data to vehicle table?
You can achieve this by making two changes to your approach:
Firstly, use a BEFORE trigger rather than an AFTER
Secondly, rather than updating the same table, update the NEW table, setting the column value to the new value before the NEW table hits the table targeted by the INSERT.
For example, replace your UPDATE line with the following:
UPDATE NEW SET cph = Cph;
MySQL doesn't allow you to edit the data in the table on which a trigger is created in that trigger, but you can edit the NEW table to modify the values going into that table.

not allowed to return a resultset from a trigger mysql

delimiter $$
CREATE TRIGGER REDUCE_NOTE_COUNT
AFTER DELETE ON iv_notes
FOR EACH ROW BEGIN
DECLARE supplierid int(11);
DECLARE customerid int(11);
SELECT supplierid ,customerid FROM iv_documents WHERE id=OLD.note_documentid;
SET supplierid=supplierid;
SET customerid=customerid;
IF supplierid=OLD.note_companyid THEN
update iv_documents
set supplier_notes=supplier_notes-1
where id=OLD.note_documentid and supplier_notes>0;
END IF;
IF customerid=OLD.note_companyid THEN
update iv_documents set customer_notes=customer_notes-1
where id=OLD.note_documentid
and customer_notes>0 ;
END IF;
END$$
delimiter ;
You cannot execute SELECT statements from trigger. If you want to set variables, then use SELECT INTO statement, e.g. -
DECLARE supplierid_ INT(11);
DECLARE customerid_ INT(11);
SELECT
supplierid, customerid
INTO
supplierid_, customerid_
FROM
iv_documents
WHERE
id = OLD.note_documentid;
IF supplierid_ = OLD.note_companyid THEN
...
Also, rename variables, they have to differ from from field names.