I am trying to convert a complex oracle sql procedure to mysql. The procedure contains of many differenct selects, cursors etc. I already wrote a version of it in mysql, but it does not work and only gives some error messages. I hope on could help me.
Tables
CREATE TABLE IF NOT EXISTS `NutritionalInformation`
(
`idNuIn` INT NOT NULL PRIMARY KEY AUTO_INCREMENT,
`calories` FLOAT NULL,
`saturatedFat` FLOAT NULL,
`transFat` FLOAT NULL,
`carbohydrates` FLOAT NULL,
`sugar` FLOAT NULL,
`protein` FLOAT NULL,
`salt` FLOAT NULL
);
CREATE TABLE IF NOT EXISTS `Inventory`
(
`idInventory` INT NOT NULL,
`idIngredient` INT NOT NULL,
`idStore` INT NOT NULL,
`expiryDate` DATE NULL,
`deliveryDate` DATE NOT NULL,
`amount` INT NOT NULL,
`isAccessible` INT NOT NULL,
CONSTRAINT `fk_Inventory_Ingredient`
FOREIGN KEY (`idIngredient`)
REFERENCES `Ingredient` (`idIngredient`),
CONSTRAINT `fk_Inventory_StoreA`
FOREIGN KEY (`idStore`)
REFERENCES `WaffleStore` (`idStore`),
CONSTRAINT pk_Inventory
PRIMARY KEY (idInventory)
);
CREATE TABLE IF NOT EXISTS `Inventory`
(
`idInventory` INT NOT NULL,
`idIngredient` INT NOT NULL,
`idStore` INT NOT NULL,
`expiryDate` DATE NULL,
`deliveryDate` DATE NOT NULL,
`amount` INT NOT NULL,
`isAccessible` INT NOT NULL,
PRIMARY KEY (`idIngredient`, `idStore`),
CONSTRAINT `fk_Inventory_Ingredient`
FOREIGN KEY (`idIngredient`)
REFERENCES `Ingredient` (`idIngredient`),
CONSTRAINT `fk_Inventory_StoreA`
FOREIGN KEY (`idStore`)
REFERENCES `WaffleStore` (`idStore`)
);
CREATE TABLE IF NOT EXISTS `Product`
(
`idProduct` INT NOT NULL PRIMARY KEY AUTO_INCREMENT,
`idNuIn` INT NOT NULL,
`price` FLOAT NOT NULL,
`name` VARCHAR(255) NOT NULL,
CONSTRAINT `fk_Product_NutritionalInformation1`
FOREIGN KEY (`idNuIn`)
REFERENCES `NutritionalInformation` (`idNuIn`)
);
CREATE TABLE IF NOT EXISTS `Waffle`
(
`idWaffle` INT NOT NULL PRIMARY KEY AUTO_INCREMENT,
`creatorName` VARCHAR(255) NULL,
`creationDate` DATE NOT NULL,
`processingTimeSec` INT,
`healty` VARCHAR(255),
CONSTRAINT `fk_Waffle_Product1`
FOREIGN KEY (`idWaffle`)
REFERENCES `Product` (`idProduct`)
);
CREATE TABLE IF NOT EXISTS `WaffleIngredient`
(
`idIngredient` INT NOT NULL,
`idWaffle` INT NOT NULL,
`amount` INT NOT NULL,
PRIMARY KEY (`idIngredient`, `idWaffle`),
CONSTRAINT `fk_WaffleRecept_Ingredient1`
FOREIGN KEY (`idIngredient`)
REFERENCES `Ingredient` (`idIngredient`),
CONSTRAINT `fk_WaffleRecept_Waffle1`
FOREIGN KEY (`idWaffle`)
REFERENCES `Waffle` (`idWaffle`)
);
CREATE TABLE IF NOT EXISTS `WaffleStore`
(
`idStore` INT NOT NULL PRIMARY KEY AUTO_INCREMENT,
`name` VARCHAR(255) NULL,
`areaCode` VARCHAR(15) NULL,
`location` VARCHAR(255) NULL,
`streetName` VARCHAR(255) NULL,
`houseNumber` VARCHAR(45) NULL
);
Example Inserts
INSERT INTO NutritionalInformation (idNuIn, calories, saturatedFat, transFat, carbohydrates, sugar, protein, salt)
VALUES (4, 60, 0, 0, 0, 0, 0, 0);
INSERT INTO NutritionalInformation (idNuIn, calories, saturatedFat, transFat, carbohydrates, sugar, protein, salt)
VALUES (5, 350, 3, 3, 5, 5, 3, 1);
INSERT INTO INGREDIENT (idIngredient, idNuIn, name, unit, price, processingTimeSec)
VALUES (3, 4, 'Apfel', 'g', 0.5, 3);
INSERT INTO PRODUCT (idProduct, idNuIn, price, name)
VALUES (4, 5, 3.5, 'ApfelWaffel');
INSERT INTO WAFFLE (idWaffle, creatorName, creationDate, processingTimeSec, healty)
VALUES (4, 'Berndt', '2020-12-01', NULL, NULL);
INSERT INTO WAFFLEINGREDIENT(idIngredient, idWaffle, amount)
VALUES (3, 4, 2);
INSERT INTO WaffleStore (idStore, name, areaCode, location, streetName, houseNumber)
VALUES (1, 'Waffle GMBH', '50000', 'TEST', 'TEST', '38');
INSERT INTO INVENTORY(idInventory, idIngredient, idStore, expiryDate, deliveryDate, amount, isAccessible)
VALUES (2, 3, 1, '3032-12-30', '3032-12-30', 100, 1);
INSERT INTO WaffleOrder(idOrder, idStore, totalAmount, paymentStatus, orderDate)
VALUES (1, 1, 2, 0, '2020-12-30');
Oracle SQL PROCEDURE
CREATE OR REPLACE PROCEDURE OnInventoryAdd (
s_idProduct IN INT,
s_idOrder IN INT,
s_extenal_amount IN INT
)
IS
v_store INT;
v_waffle_id INT;
v_cursor_ingredientid INT;
v_cursor_amount INT;
v_cursor_expiryDate DATE;
v_cursor_deliveryDate DATE;
v_operator VARCHAR(3) := 'add';
CURSOR v_Ingredient_Cursor_On_Insert(w_Id INT) IS
SELECT idIngredient, amount FROM WAFFLEINGREDIENT WHERE idWaffle = w_Id;
CURSOR v_Ingredient_Cursor_On_Delete(i_id INT) IS
SELECT expiryDate, deliveryDate FROM Inventory WHERE idIngredient = i_id;
BEGIN
SELECT idStore INTO v_store FROM WAFFLEORDER WHERE idOrder = s_idOrder;
SELECT w.idWaffle INTO v_waffle_id FROM Waffle w WHERE w.idProduct = s_idProduct;
-- If more than one waffle is bought
FOR x IN 1..s_extenal_amount LOOP
-- Get all ingredient information of waffle
OPEN v_Ingredient_Cursor_On_Insert(v_waffle_id);
LOOP
FETCH v_Ingredient_Cursor_On_Insert INTO v_cursor_ingredientId, v_cursor_amount;
EXIT WHEN v_Ingredient_Cursor_On_Insert%NOTFOUND;
-- Get all old expirydate and deliverydate information
OPEN v_Ingredient_Cursor_On_Delete(v_cursor_ingredientId);
LOOP
FETCH v_Ingredient_Cursor_On_Delete INTO v_cursor_expiryDate, v_cursor_deliveryDate;
EXIT WHEN v_Ingredient_Cursor_On_Delete%NOTFOUND;
END LOOP;
CLOSE v_Ingredient_Cursor_On_Delete;
END LOOP;
CLOSE v_Ingredient_Cursor_On_Insert;
-- Update the Inventory
InventoryUpdate(v_store, v_cursor_ingredientId, v_cursor_amount, v_operator, v_cursor_expiryDate, v_cursor_deliveryDate);
END LOOP;
END;
/
Current Version
DROP PROCEDURE IF EXISTS `OnInventoryAdd`;
DELIMITER //
CREATE PROCEDURE `OnInventoryAdd` (
s_idProduct INT,
s_idOrder INT,
s_extenal_amount INT
)
BEGIN
DECLARE loop_counter INT DEFAULT s_extenal_amount;
DECLARE v_store INT;
DECLARE v_waffle_id INT;
DECLARE v_cursor_ingredientid INT;
DECLARE v_cursor_amount INT;
DECLARE v_cursor_expiryDate DATE;
DECLARE v_cursor_deliveryDate DATE;
DECLARE v_operator VARCHAR(3) DEFAULT 'add';
DECLARE v_c_insert_done, v_c_delete_done BOOLEAN DEFAULT FALSE;
DECLARE v_Ingredient_Cursor_On_Insert CURSOR FOR
SELECT idIngredient, amount FROM WAFFLEINGREDIENT WHERE idWaffle = v_waffle_id;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET v_c_insert_done = TRUE;
SELECT idStore INTO v_store FROM WAFFLEORDER WHERE idOrder = s_idOrder;
SELECT idWaffle INTO v_waffle_id FROM Waffle WHERE idWaffle = s_idProduct;
WHILE loop_counter > 0 DO
SET loop_counter = loop_counter - 1;
OPEN v_Ingredient_Cursor_On_Insert;
curr_insert_loop: LOOP
FETCH FROM v_Ingredient_Cursor_On_Insert INTO v_cursor_ingredientId, v_cursor_amount;
IF v_c_insert_done THEN
CLOSE v_Ingredient_Cursor_On_Insert;
LEAVE curr_insert_loop;
END IF;
BLOCK2 : BEGIN
DECLARE v_Ingredient_Cursor_On_Delete CURSOR FOR
SELECT expiryDate, deliveryDate FROM Inventory WHERE idIngredient = v_cursor_ingredientid;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET v_c_delete_done = TRUE;
OPEN v_Ingredient_Cursor_On_Delete;
curr_delete_loop : LOOP
FETCH FROM v_Ingredient_Cursor_On_Delete INTO v_cursor_expiryDate, v_cursor_deliveryDate;
IF v_c_delete_done THEN
CLOSE v_Ingredient_Cursor_On_Delete;
LEAVE curr_delete_loop;
END IF;
END LOOP curr_delete_loop;
END BLOCK2;
END LOOP curr_insert_loop;
CALL InventoryUpdate(v_store, v_cursor_ingredientId, v_cursor_amount, v_operator, v_cursor_expiryDate, v_cursor_deliveryDate);
END WHILE;
END //
DELIMITER ;
Error
4 row(s) affected, 2 warning(s): 1264 Out of range value for column 'expiryDateOnInsert' at row 2 1264 Out of range value for column 'deliveryDateOnInsert' at row 1
Even tho I wrote the Oracle Procedure, I have zero clue how to write the same behavior in MYSQL and more over how to fix this error. If there is a alternative to do the same without cursors, then it would be fine too
Ok, I've managed to convert the oracle procedure into mysql stored procedure, here is the working code:
Code
CREATE PROCEDURE `OnInventoryAdd` (
s_idProduct INT,
s_idOrder INT,
s_extenal_amount INT
)
BEGIN
DECLARE loop_counter INT DEFAULT s_extenal_amount;
DECLARE done1, done2 BOOLEAN DEFAULT FALSE;
DECLARE v_store INT;
DECLARE v_waffle_id INT;
DECLARE v_operator VARCHAR(3) DEFAULT 'add';
DECLARE v_cursor_ingredientid INT;
DECLARE v_cursor_amount INT;
DECLARE v_cursor_expiryDate DATE;
DECLARE v_cursor_deliveryDate DATE;
DECLARE v_Ingredient_Cursor_On_Insert CURSOR FOR
SELECT idIngredient, amount FROM WAFFLEINGREDIENT WHERE idWaffle = v_waffle_id;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET done1 = TRUE;
SELECT idStore INTO v_store FROM WAFFLEORDER WHERE idOrder = s_idOrder;
SELECT idWaffle INTO v_waffle_id FROM Waffle WHERE idWaffle = s_idProduct;
REPEAT
OPEN v_Ingredient_Cursor_On_Insert;
loop1 : LOOP
FETCH FROM v_Ingredient_Cursor_On_Insert INTO v_cursor_ingredientId, v_cursor_amount;
IF done1 THEN
CLOSE v_Ingredient_Cursor_On_Insert;
LEAVE loop1;
END IF;
BLOCK1 : BEGIN
DECLARE v_Ingredient_Cursor_On_Delete CURSOR FOR
SELECT expiryDate, deliveryDate FROM Inventory WHERE idIngredient = v_cursor_ingredientid;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET done2 = TRUE;
OPEN v_Ingredient_Cursor_On_Delete;
loop2 : LOOP
FETCH FROM v_Ingredient_Cursor_On_Delete INTO v_cursor_expiryDate, v_cursor_deliveryDate;
IF done2 THEN
SET done2 = FALSE; -- This was the solution
LEAVE loop2;
END IF;
END LOOP loop2;
END BLOCK1;
END LOOP loop1;
CALL InventoryUpdate(v_store, v_cursor_ingredientId, v_cursor_amount, v_operator, v_cursor_expiryDate, v_cursor_deliveryDate);
SET loop_counter = loop_counter - 1;
UNTIL loop_counter = 0
END REPEAT;
END //
DELIMITER ;
I have a problem and I don't know how to solve it.
I need to create a procedure with cursor to insert into Vizite: dataora (i need a function), Medici_Idm,Pacienti_Idm,Cabinete_Idm from temporary table.My procedure doesn't work, i also use for select tables: Medici, Pacineti,Cabinete to extract id.
Table 1:
CREATE TABLE IF NOT EXISTS Vizite (
Idv INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
DataOra DATETIME,
Medici_Idm INT NOT NULL,
Pacienti_Idp INT NOT NULL,
Cabinete_Idc INT NOT NULL,
FOREIGN KEY (Medici_Idm) REFERENCES Medici(Idm),
FOREIGN KEY (Pacienti_Idp) REFERENCES Pacienti(Idp),
FOREIGN KEY (Cabinete_Idc) REFERENCES Cabinete(Idc)
) Engine=INNODB;
Table 2:
CREATE TEMPORARY TABLE IF NOT EXISTS TempVizite (
Idt INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
DataVizita VARCHAR(250),
OraIntrare TIME,
NumePacient VARCHAR(250),
PrenumePacient VARCHAR(250),
NumeMedic VARCHAR(250),
PrenumeMedic VARCHAR(250),
Cabinet VARCHAR (250));
the procedure:
DELIMITER /
CREATE PROCEDURE VARIANTA3()
BEGIN
DECLARE M_I,P_I,C_I VARCHAR(100);
DECLARE I_V INT;
DECLARE D DATE;
DECLARE O TIME;
DECLARE CURS1 CURSOR FOR -- declaram cursorul
SELECT IDT,DATAVIZITA,ORAINTRARE,NUMEMEDIC,NUMEPACIENT,CABINET FROM TEMPVIZITE;
DECLARE EXIT HANDLER FOR 1329 BEGIN END; -- declaram handler specific erorii de terminarea cursorului
OPEN CURS1;
BUCLA: LOOP
FETCH CURS1 INTO M_I,P_I,C_I,I_V,D,O;
INSERT IGNORE INTO VIZITE VALUES(I_V,#DATAORA,M_I,P_I,C_I);
SELECT TIMESTAMP(DATAVIZITA,ORAINTRARE) INTO #DATAORA;
SELECT IDM FROM MEDICI WHERE NUME = NUMEMEDIC INTO M_I;
SELECT IDP FROM PACIENTI WHERE NUME = NUMEPACIENT INTO P_I;
SELECT IDC FROM CABINETE WHERE NUME = CABIENT INTO C_I;
END LOOP;
CLOSE CURS1;
END /
DELIMITER ;
I'm having difficulty with developing the logic in MySQL. I don't know how to INSERT multiple records from a Table AFTER UPDATE.
CREATE TABLE primeira(
ID int PRIMARY KEY AUTO_INCREMENT,
nome varchar(30) NOT NULL,
valor int DEFAULT 0
);
CREATE TABLE segunda(
ID int PRIMARY KEY AUTO_INCREMENT,
ID_primeira int,
ultimo_valor int DEFAULT 0,
credito int NOT NULL,
limite int DEFAULT 0,
FOREIGN KEY(ID_primeira) references primeira(ID)
);
CREATE TABLE terceira(
ID int PRIMARY KEY AUTO_INCREMENT,
ID_segunda int,
`data` TIMESTAMP DEFAULT CURRENT_TIMESTAMP NOT NULL,
estado boolean DEFAULT false,
FOREIGN KEY(ID_segunda) references segunda(ID)
);
CREATE TRIGGER tr_segundaLimite_INS
BEFORE INSERT ON segunda FOR EACH ROW
SET NEW.limite = New.ultimo_valor + New.credito;
DELIMITER //
CREATE TRIGGER tr_primeira_UPD
AFTER UPDATE ON primeira FOR EACH ROW
IF (SELECT limite FROM segunda WHERE segunda.ID_primeira = New.ID AND
(limite - NEW.valor)< 50) THEN
INSERT INTO terceira(ID_segunda)
VALUES ((SELECT ID FROM segunda WHERE segunda.ID_primeira = New.ID
AND (limite - NEW.valor)< 50));
END IF;
END
//
DELIMITER ;
I'm going to use procedures with functions to SELECT the data. The problem with this TRIGGER is that it's not working when there are multiple matching records.
The error that I am getting is-
subquery returns more than 1 row.
The objective is: After an update of the primeira.valor, the trigger would subtract segunda.limite - New.valor. If this difference is < 50 then all the matching segunda.ID would be registered at terceira.ID_segunda on terceira table.
I'm using data below:
INSERT INTO primeira(nome,valor)
VALUES
('Burro',800),
('Chiconizio',300),
('Xerosque',400),
('Shrek',600);
INSERT INTO segunda(ID_primeira,ultimo_valor,credito)
VALUES
(1,600,800),
(1,700,400),
(1,800,500),
(2,150,200),
(2,200,180),
(2,250,300);
UPDATE primeira
SET Valor = 330
WHERE ID = 2;
You need CURSOR for this. You can try the following trigger code. I hope this will fix your issue.
DELIMITER //
CREATE TRIGGER tr_primeira_UPD
AFTER UPDATE ON primeira FOR EACH ROW
BEGIN
DECLARE v_limite_diff INT;
DECLARE v_seg_id INT;
DECLARE done INT DEFAULT FALSE;
DECLARE c1 CURSOR FOR SELECT (s.limite - NEW.valor), s.id
FROM segunda s WHERE s.ID_primeira = New.ID;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = TRUE;
OPEN c1;
my_loop: LOOP
FETCH c1 INTO v_limite_diff, v_seg_id;
IF done THEN
LEAVE my_loop;
END IF;
IF( v_limite_diff < 50 ) THEN
INSERT INTO terceira(ID_segunda) VALUES(v_seg_id);
END IF;
END LOOP;
END//
DELIMITER ;
I'm working on an Android program that introduces in a table approximately 15000 integer values(somewhere between 350-500 lines with 32 columns). In the DB I also have other similar values. This 15000 values that I'm talking about represent a processed image, so basically I want to compare the similarity of two images. Now, when I try to compare the values of two images(I'm comparing value by value and count the equal ones), only the data writing process takes about 7 minutes, which is way too long(I want to be able to write and compare at least 5 images in that time). I know that usually you don't work with this kind of things directly in the DB, but do you think that there is anything that I can do, or is it necessary to do this comparison on the server? The values returned by the descriptor came as line elements separated by ',' and each line is separated by ';'. I take each returned element and save it in a tables column. Here is my code:
Split function:
CREATE DEFINER=`root`#`localhost` FUNCTION `strSplit`(textIn longtext, delim varchar(12), count int) RETURNS int(11)
BEGIN
declare splitString INT(11);
SET splitString = replace(substring(substring_index(textIn, delim, count), length(substring_index(textIn, delim, count - 1)) + 1), delim, '');
RETURN splitString;
END
The function that creates the table:
CREATE TABLE IF NOT EXISTS `myguide`.`objectlocation` (
`ObjectLocationId` INT(11) NOT NULL AUTO_INCREMENT,
`ValueObject` LONGTEXT NOT NULL,
`DescriptorSize` INT(11) NOT NULL,
`DescriptionObject` VARCHAR(45) NOT NULL,
`DataInsert` DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP,
`InsertBy` VARCHAR(45) NULL DEFAULT NULL,
PRIMARY KEY (`ObjectLocationId`))
ENGINE = InnoDB
AUTO_INCREMENT = 2
DEFAULT CHARACTER SET = utf8
And this is the code that does the insert part:
CREATE DEFINER=`root`#`localhost` PROCEDURE `myguide_sp_info_imageId`(descriptorIn longtext, sizeDescriptor INT)
BEGIN
declare sizeImagesTable INT DEFAULT (select count(*) from objectLocation);
declare descriptorSizeImage INT;
declare descriptor INT;
declare sizeDescriptorImage INT DEFAULT sizeDescriptor;
declare contorInsertImage INT default 1;
declare descriptorForSplit longtext;
declare descriptorImageSaved longtext;
declare descriptorForSplitImageSaved longtext;
/* check if table exist, drop*/
DROP TEMPORARY TABLE IF EXISTS backupObjectLocation;
/* Create temporar table for store info about objectLocation*/
CREATE TEMPORARY TABLE backupObjectLocation (
id INT NOT NULL PRIMARY KEY AUTO_INCREMENT,
idImage int NOT NULL,
descriptorSaved longtext not null,
sizeDescriptorSaved float not null
);
/* check if table exist, drop*/
DROP TEMPORARY TABLE IF EXISTS processImage;
/* Create temporar table for store info about objectLocation*/
CREATE TEMPORARY TABLE processImage (
id INT NOT NULL PRIMARY KEY AUTO_INCREMENT,
descriptorSaved varchar(255) ,
descriptorReceived varchar(255)
);
SET descriptorImageSaved = RTRIM(descriptorIn);
SET descriptorForSplit = REPLACE(descriptorImageSaved, ';', ',');
INSERT INTO backupObjectLocation (idImage, descriptorSaved, sizeDescriptorSaved)
SELECT ObjectLocationId, ValueObject, DescriptorSize FROM objectLocation;
loop_insertDescriptorImage: LOOP
if contorInsertImage > sizeDescriptorImage then
leave loop_insertDescriptorImage;
end if;
SET descriptor = strSplit(descriptorForSplit, ',', contorInsertImage);
INSERT INTO processImage (descriptorReceived) VALUES (descriptor);
SET contorInsertImage = contorInsertImage + 1;
ITERATE loop_insertDescriptorImage;
end LOOP;
loop_table: LOOP
if sizeImagesTable > 1 then
leave loop_table;
end if;
SET descriptorSizeImage = (SELECT sizeDescriptorSaved from backupObjectLocation where id = sizeImagesTable);
loop_image: LOOP
if descriptorSizeImage > 1 then
leave loop_image;
end if;
SET descriptorImageSaved = (SELECT descriptorSaved from backupObjectLocation where id = sizeImagesTable);
SET descriptorForSplitImageSaved = REPLACE(descriptorImageSaved, ';', ',');
SET descriptorSizeImage = descriptorSizeImage + 1;
ITERATE loop_image;
end LOOP;
SET sizeImagesTable = sizeImagesTable + 1;
ITERATE loop_table;
end LOOP;
select descriptorImageSaved;
select * from backupObjectLocation;
select * from processImage;
END
Please help me find a solution.
I am constantly getting a Error code 1062: Duplicate Entry.
The first row insert, but then it fails on the same ID.
So everytime I hit execute it will increment: 1466, 1467, 1468, 1469.
And each time there is the same record entered, so I am assuming the autoincrement is only working for the first iteration.
Table:
'entity':
CREATE TABLE `entity` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) NOT NULL,
`reg_num` varchar(45) NOT NULL,
`enterprise_id` int(11) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1474 DEFAULT CHARSET=latin1 COMMENT=\'Comment'
Stored procedure:
DELIMITER $$
CREATE DEFINER=`root`#`localhost` PROCEDURE `tp_to_entityPROC`()
DETERMINISTIC
COMMENT 'stored'
BEGIN
DECLARE done BOOLEAN DEFAULT 0;
DECLARE Tid INT;
DECLARE Tt_name TEXT;
DECLARE allt CURSOR FOR
SELECT training_provider_id, training_provider_name
FROM training_providers;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET done=1;
OPEN allt;
read_loop: LOOP
IF done THEN
LEAVE read_loop;
END IF;
FETCH allt INTO Tid, Tt_name;
SET #id = 0;
SET #t_name = 0;
SET #id = Tid;
SET #t_name = Tt_name;
SET #empty = '';
if (#id != 0) THEN
INSERT INTO entity (name)
VALUES (#t_name);
SET #my_id = LAST_INSERT_ID();
IF #my_id != 0 THEN
UPDATE training_awarded_providers
SET training_awarded_provider_id = #my_id
WHERE training_awarded_provider_id = #id;
END IF;
END IF;
END LOOP;
CLOSE allt;
END
Not sure about the exact error of duplicate entry but your posted code is not going to work.
Your Table schema
CREATE TABLE `entity` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) NOT NULL,
`reg_num` varchar(45) NOT NULL <-- Here it's non null column
In your store procedure you are trying to insert null to reg_num column which will never succeed
if (#id != 0) THEN
INSERT INTO entity (name)
VALUES (#t_name);