I'm looking for something can help me to get the id of the ticket created at the first row.
I know i can simplify this by using different prepared query but I want not (try and see if it possible by this way and if it's not using the multiple queries way.
I know LAST_INSERT_ID() in mysql but I'm a little worried about inserting several lines at the same time....
During my research I also see someone directy SELECT the specified ID but it's a big cost of ressources.
I also see ##INSERTED and i didn't see a big difference between them, so i had the same problem...
The code :
CREATE PROCEDURE `Create_Ticket`(IN idU bigint(16),IN type VARCHAR(45),IN pseudo VARCHAR(45), IN lienacc VARCHAR(100), IN liengame VARCHAR(100), IN content VARCHAR(500))
BEGIN
INSERT INTO `dbOneT`.`Ticket` (`FaceitGame`,`Status`,`Ouverture` )
VALUES ( liengame , 0 , NOW());
INSERT INTO `dbOneT`.`Users_has_Ticket` (`Users_id`, `Ticket_id`)
VALUES ( idU, `Ticket`.`idTicket` );
INSERT INTO `dbOneT`.`Accuse` (`Pseudo`,`LienFaceit`)
VALUES (pseudo, lienacc);
INSERT INTO `dbOneT`.`Ticket_has_Accuse` (`Ticket_id_A`, `Accusé_id`)
VALUES (`Ticket`.`idTicket`, `Accuse`.`idAccuse`);
END
I'm running MariaDB 10.3.27
The "computer" is a raspberry pi 4B with 8go ram
On Raspberry Pi OS (A debian)
thanks for your help and have a nice day
Tom
CREATE PROCEDURE `Create_Ticket`(IN idU bigint(16),IN type VARCHAR(45),IN pseudo VARCHAR(45), IN lienacc VARCHAR(100), IN liengame VARCHAR(100), IN content VARCHAR(500))
BEGIN
-- declare variables for inserted PK AI values
DECLARE _idTicket INT;
DECLARE _idAccuse INT;
INSERT INTO `dbOneT`.`Ticket` (`FaceitGame`,`Status`,`Ouverture` )
VALUES ( liengame , 0 , NOW());
-- save assignerd AI value to the variable
SET _idTicket := LAST_INSERT_ID();
INSERT INTO `dbOneT`.`Users_has_Ticket` (`Users_id`, `Ticket_id`)
-- use saved value
VALUES ( idU, _idTicket );
INSERT INTO `dbOneT`.`Accuse` (`Pseudo`,`LienFaceit`)
VALUES (pseudo, lienacc);
-- save assignerd AI value to the variable
SET _idAccuse := LAST_INSERT_ID();
-- use saved values
INSERT INTO `dbOneT`.`Ticket_has_Accuse` (`Ticket_id_A`, `Accusé_id`)
VALUES (_idTicket, _idAccuse);
END
Related
I have this MYSQL Stored procedure that will insert a record and I need the output to give the last_insert_id(). I have tried several different commands, (listed below the procedure) to get this number, but nothing works.
here is the stored procedure:
CREATE DEFINER=`root`#`%` PROCEDURE `TestInsert`(IN v_area_id INT, IN v_regid INT, IN v_event INT, IN v_familyid INT, IN v_memberid INT, IN v_amount DECIMAL(12,2),
IN v_desc varchar(255), OUT auto_id INTEGER )
BEGIN
DECLARE auto_id INT DEFAULT 0;
INSERT INTO stripe (area_id, regid, event, familyid, memberid, totalamt, charge_description)
values (v_area_id, v_regid, v_event, v_familyid, v_memberid, v_amount, v_desc);
SET #auto_id = LAST_INSERT_ID();
END
I have tried these different commands to get a result:
SET auto_id := last_insert_id();
SELECT last_insert_id() INTO #auto_id; (also without the #)
Using or not using the "DECLARE auto_id INT DEFAULT 0;" makes no difference.
Also found some other commands here stack overflow, which I don't remember now.
the Insert works fine, just can't get the id.
I'm using Navicat command console.
I'm in my first databases class and I'm trying to write a conditional block for a mysql procedure.
This is the procedure:
delimiter //
CREATE PROCEDURE add_ascent(IN cid INT, IN pid INT)
BEGIN
DECLARE count_ascents INT;
SET count_ascents = 0;
SELECT COUNT(`cid`) INTO count_ascents FROM ascents WHERE `cid`=cid AND `pid`=pid;
IF count_ascents < 1 THEN
INSERT INTO ascents (`cid`, `pid`) VALUES (cid, pid);
UPDATE climbers SET climbers.ascents = climbers.ascents + 1 WHERE climbers.id=cid;
UPDATE problems SET problems.ascents = problems.ascents + 1 WHERE problems.id=pid;
END IF;
END;
//
delimiter ;
The goal of the procedure is to only perform the insert and updates if the (cid, pid) pair is not in the the ascents database. After testing, the program doesn't seem to go into the if block at all.
FYI, you might want to consider using an UPSERT, instead of "select/if/insert". For example, mySQL offers INSERT ON DUPLICATE KEY UPDATE.
Here, I suggest:
giving your parameters a DIFFERENT name than the column name, for example iCid and iPid, then
Typing SELECT COUNT(cid) INTO count_ascents FROM ascents WHERE cid=iCid AND pid=iPid and checking the result.
I got a website with a database running on MySQL Community Server (GPL) version 5.5.37
And I want to write a stored precedure to insert an image in table 1 then select the id from that last post to insert that id in table 2.
I started to google and ended up with this:
CREATE PROCEDURE InsertNewMedia(
IN insertLocatie varchar(255),
IN insertNaam varchar(150),
IN insertOmschrijving longtext,
IN insertCategorieID int
)
BEGIN
INSERT INTO MediaDB (idMediaDB, Locatie, Naam, Omschrijving) VALUES (NULL, insertLocatie, insertNaam, insertOmschrijving);
SELECT MAX(idMediaDB) AS Nieuwste FROM MediaDB;
INSERT INTO MediaLink (idMediaLink, OverMijShoots_idOverMijShoots, MediaDB_idMediaDB) VALUES (NULL, insertCategorieID, Nieuwste);
END
I know this is a wrong code but I can't find a good awnser on what I need.
Can anyone help me?
I think you are looking for LAST_INSERT_ID():
delimiter //
CREATE PROCEDURE InsertNewMedia(
IN insertLocatie varchar(255),
IN insertNaam varchar(150),
IN insertOmschrijving longtext,
IN insertCategorieID int
)
BEGIN
INSERT INTO MediaDB(idMediaDB, Locatie, Naam, Omschrijving)
VALUES (NULL, insertLocatie, insertNaam, insertOmschrijving);
INSERT INTO MediaLink (idMediaLink, OverMijShoots_idOverMijShoots, MediaDB_idMediaDB)
VALUES (NULL, insertCategorieID, LAST_INSERT_ID());
END//
delimiter ;
I did a trigger in mysql to shoot alerts always an input value was less than the set value. But now I need it is done in SQL SERVER.
I would be grateful if someone could help me transform mysql trigger to a SQL Server trigger.
Thanks to all at once.
My trigger is:
DELIMITER $$
create TRIGGER alert
AFTER INSERT ON records
FOR EACH ROW
begin
Set #comp=0;
Set #tempmax=0;
Set #tempmin=0;
select lim_inf_temp into #tempmin from sensores where idSensor=NEW.idSensor;
Set #maxidAlarme=0;
if (CAST(NEW.Temperatura AS UNSIGNED)<#tempmin) then
SELECT MAX(idAlarme) into #maxidAlarme FROM alarmes;
SET #maxidAlarme=#maxidAlarme+1;
INSERT INTO alarmes(idAlarme,descricao_alarme, idRegisto) VALUES (#maxidAlarme,"inserted below the normal temperature",New.idRegisto);
INSERT INTO sensores_tem_alarmes(idSensor,idAlarme,dataAlarme) VALUES (NEW.idSensor,#maxidAlarme,NOW());
set #comp=+1;
end if;
set #id_sensores_em_alerta=1;
SELECT MAX(id_sensores_em_alerta) into #id_sensores_em_alerta FROM sensores_em_alerta;
INSERT INTO sensores_em_alerta(id_sensores_em_alerta, idSensor, idAlarme, data_registo, numerosensoresdisparados) VALUES (id_sensores_em_alerta,NEW.idSensor, #maxidAlarme, NOW(), #comp);
end $$;
DELIMITER ;
I've tried to make the trigger in SQL Server, but as the script is different and I'm getting many difficulties to do the right way.
My attempt that was not going at all well:
CREATE TRIGGER Alert ON registos AFTER INSERT AS
BEGIN
DECLARE #comp decimal= 0
DECLARE #tempmax decimal= 0
DECLARE #tempmin decimal= 0
DECLARE #current_max_idAlarme int = (SELECT MAX(IdAlarme) FROM alarmes)
-- Insert into alarmes from the inserted rows if temperature less than tempmin
INSERT alarmes (IdAlarme, descricao_alarme, idRegisto)
SELECT
ROW_NUMBER() OVER (ORDER BY i.idRegisto) + #current_max_idAlarme,
'temp Error',
i.idRegisto
FROM
inserted AS i
WHERE
i.Temperatura < #tempmin
END
But dont do anything.
Dont create data on table alarmes :S
Does anyone could help me please. I would be eternally grateful.
Many Greetings and thank you all.
First of all, MSSQL doesn't have the option FOR EACH ROW, so it treats multiple inserted rows at once as a set. You will therefore have to insert the values into a table variable.
Unfortunately I do not know much MySQL actually, but I believe this is a starting point?
CREATE TRIGGER ALERT
ON records
AFTER INSERT
AS
BEGIN
DECLARE #comp INT;
DECLARE #tempmax INT;
DECLARE TABLE #tempmin (tempmin INT);
INSERT INTO #tempmin
SELECT s.lim_inf_temp FROM sensores s WHERE s.idSensor IN (inserted.idSensor);
--rest of the code
I'm going to post this code against my better judgement - redesign the tables is better than this hack.
This uses a ROW_number() to virtualise a surrogate identity key for the alarmes table. This is a 'bad plan' (tm).
Also the answer is partial - it doesn't do everything your question asked for -- I hope it gets your further along the road. Use it as a guide for how to interact with the virtual INSERTED table. Good luck
CREATE TRIGGER Alert ON records AFTER INSERT AS
BEGIN
DECLARE #comp INT = 0
DECLARE #tempmax INT = 0
DECLARE #tempmin INT = 0
-- get the max current id.
-- note that this is EXTREMELY unsafe as if two pieces of code are executing
-- at the same time then you *will* end up with key conflicts.
-- you could use SERIALIZABLE.... but better would be to redisn the schema
DECLARE #current_max_idAlarme = (SELECT MAX(IdAlarme) FROM alarmes)
-- Insert into alarmes from the inserted rows if temperature less than tempmin
INSERT alarmes (IdAlarme, descricao_alarme, idRegisto)
SELECT
ROW_NUMBER() OVER (ORDER BY i.idRegisto) + #current_max_idAlarme,
'temp Error',
i.idRegisto
FROM
inserted AS i
WHERE
i.Temperatura < #tempmin
END
How do I write a stored procedure to add a person record with multiple addresses?
It is easy if the person has only one address but I'm not sure how to write a stored procedure to add a person with multiple addresses.
Here is the stored procedure to add a person with one address:
DELIMITER $$
CREATE PROCEDURE `log`.`spAddPerson` (
IN personID INT,
IN personName VARCHAR(100),
IN addressLine1 VARCHAR(45),
IN addressLine2 VARCHAR(45),
IN myCity VARCHAR(45),
IN myState VARCHAR(45),
IN myCountry VARCHAR(45)
)
BEGIN
DECLARE EXIT HANDLER FOR SQLEXCEPTION
BEGIN
ROLLBACK;
END;
START TRANSACTION;
INSERT INTO person VALUES(personID,personName);
-- addressid is automatically generated
INSERT INTO address(Line1, Line2,City,State,Country) VALUES
(addressLine1, addressLine2, myCity,myState, myCountry);
INSERT INTO personAddress(personID, last_insert_id());
COMMIT;
END
The above code works fine. However, I do not know how to handle a person with multiple addresses without writing a separate stored procedure. Is there a simple way to do this?
You cannot pass a variable number of variables to a procedure, nor a non-scalar type.
A possible trick would be building a temporary table with the addresses before calling this procedure. Either the temporary table is pre-determined, or pass its name as a VARCHAR parameter(and use it to build dynamic SQL statements). Eg:
CREATE PROCEDURE spAddPerson (tmp_table VARCHAR(10), ...)
BEGIN
...
PREPARE s AS CONCAT(
'INSERT INTO address (line1, ...) VALUES SELECT * FROM ', tmp_table
);
EXECUTE s;
...
END
-- use it like this
CREATE TEMPORARY TABLE tmp_addresses (line1 VARCHAR(255), ...);
INSERT INTO tmp_addresses VALUES ('1 Cherry Lane'), ... ;
CALL spAddPerson ('tmp_addresses', ...);
However, I would rather split the action in two parts. Do you really want to prevent the creation of the person altogether if its address creation fails? And even then, wouldn't you want to advise your user why the transaction failed (user creation or address creation)?
I would rather treat these two exceptions separately at the application level:
issue a "START TRANSATION"
try to insert a person (call stored proc 1)
if it failed, rollback and notify user
for each address
try to insert an address (call stored proc 2)
if it failed, rollback and notify user
issue a "COMMIT"
> DECLARE #LAST_INSERT_ID INT
> DECLARE #EXECUTION_OK char(1)
> SET #EXECUTION_OK = 1
>
> insert into base_table(imgPath,store,apparelType) values (imgPath,store,apparelType)
>
> SELECT #LAST_INSERT_ID = SCOPE_IDENTITY()
>
> insert into data_table(cvID,color) values (#LAST_INSERT_ID, color)
> GO
>
> If exists( Select cvID from data_table where cvID= #LAST_INSERT_ID)
> Begin
> #EXECUTION_OK = 0
> End