SQL insert, delete, update - mysql

So i see that SQL has some tables which hold the newly inserted and deleted data from tables one may refer. I didn't notice such a table for updated data. I am currently working with triggers and i need to apply a trigger to an update. How do i do that?
USE [examene]
GO
/****** Object: Trigger [dbo].[trig1] Script Date: 6/8/2013 6:48:26 AM ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
ALTER trigger [dbo].[trig1] on [dbo].[participari]
after insert,update,delete
as
begin
if (exists (select * from deleted))
rollback
if (exists (select * from inserted,proiecte
where inserted.idpr = proiecte.idpr
and deadline<dela union
select * from inserted,proiecte
where inserted.idpr = proiecte.idpr and inserted.panala>proiecte.deadline))
rollback
end
this is my trigger so far

There is no such thing as updated virtual table. When update occurs old values might be found in deleted and new values in inserted
Use the inserted and deleted Tables
The deleted table stores copies of the affected rows during DELETE and
UPDATE statements. During the execution of a DELETE or UPDATE
statement, rows are deleted from the trigger table and transferred to
the deleted table.
The deleted table and the trigger table ordinarily
have no rows in common. The inserted table stores copies of the
affected rows during INSERT and UPDATE statements. During an insert or
update transaction, new rows are added to both the inserted table and
the trigger table. The rows in the inserted table are copies of the
new rows in the trigger table.
An update transaction is similar to a delete operation followed by an
insert operation; the old rows are copied to the deleted table first,
and then the new rows are copied to the trigger table and to the
inserted table.

Related

MySQL: is a TRIGGER ON DELETE triggered by DROP PARTITION?

In my MySQL base, with engine=innodb and 1 file by partition, I have:
Table 1 partitioned by date
Table 2 that counts the entries of table 1 by date
Table 1 is filled by a software, and Table 2 is filled by triggers on Table 1, as below:
CREATE TRIGGER tgi_table1 AFTER INSERT ON table1 FOR EACH ROW INSERT INTO table2 values ( NEW.date, 1 ) ON DUPLICATE KEY UPDATE count = count+1;
CREATE TRIGGER tgd_table1 AFTER DELETE ON table1 FOR EACH ROW UPDATE table2 SET count = count-1;
Also, there is a script that runs periodically and execute DROP PARTITION on the old partitions of table1.
My question is: will these DROP PARTITION activate the trigger tgd_table1?
Thank you.
No, it wont use DELETE query for deleting records. It is dropping the data in a different way. Here is the explanation from mysql docs:
DELETE: The trigger activates whenever a row is deleted from the table; for example, through DELETE and REPLACE statements. DROP TABLE and TRUNCATE TABLE statements on the table do not activate this trigger, because they do not use DELETE. Dropping a partition does not activate DELETE triggers, either.

Simple Update trigger + simple row insert

Total novice at triggers... all the docs don't bother with beginner stuff.
I just want to update the row(s) that has/have been updated. My trigger below updates the entire table. The trigger below just tests two columns for changes.
How do I restrict this update trigger to the update only the updated rows and not the entire table?
ALTER TRIGGER [dbo].[geog_update] ON [dbo].[Site]
FOR UPDATE
AS
SET NOCOUNT ON
IF (UPDATE(Latitude) OR UPDATE(Longitude))
BEGIN
UPDATE Site
SET geog = geography::Point([Latitude], [Longitude], 4326)
WHERE Latitude is not null and Longitude is not null
END
Can I use the same trigger for inserted rows by just using FOR UPDATE, INSERT? Probably not since the IF checks for UPDATE() on a column, unless INSERT implies UPDATE.
Ok first, you never under any circumstances design a trigger to update only one row in SQL Server. You design it to update the rows that were inserted, deleted or updated. Triggers operate on batches and you cannot assume that you will never change more than one record in code that hits the database.
You do that by joining to one of two pseudotables that are available only in triggers, inserted or deleted. Inserted contains the new records or the values after an update, delted contains the values for the records deleted or the values before an update occurred.
You could try something like:
ALTER TRIGGER [dbo].[geog_update] ON [dbo].[Site]
FOR UPDATE
AS
SET NOCOUNT ON
UPDATE S
SET geog = geography::Point(i.[Latitude], i.[Longitude], 4326)
FROM Site s
JOIN Inserted I on s.id = i.id
WHERE Latitude is not null and Longitude is not null
Here is the final UPDATE trigger. I made an INSERT trigger that is almost identical.
CREATE TRIGGER [dbo].[geog_update] ON [dbo].[Site]
FOR UPDATE
AS
SET NOCOUNT ON
IF (UPDATE(Latitude) OR UPDATE(Longitude))
BEGIN
UPDATE t1
SET t1.geog = geography::Point(t1.Latitude, t1.Longitude, 4326)
FROM Site AS t1 INNER JOIN Inserted AS t2 ON t1.Site_ID = t2.Site_ID
WHERE (t1.Latitude IS NOT NULL)
AND (t1.Longitude IS NOT NULL)
AND (t1.Record_Archive_Date IS NULL)
END

MySQL Trigger - Using logical inserted table to insert into another table

I am currently in the process of writing my first trigger in MySQL within PHPmyadmin. I would like it so that when an item in one table is updated, a row in another table is inserted. Several columns of the row that is to be inserted in the second table are determined by the values being updated in the first table.
Therefore, I need to INSERT a new row in table B when an update occurs on table A. And some of the values of the columns in table B are to be defined by the values in the updated table A row which caused the trigger to run.
Please find the trigger below.
CREATE TRIGGER `before_categoryiteminstance_update` BEFORE UPDATE ON `TABLEA`
FOR EACH ROW BEGIN
declare f_guidcategoryiteminstance int;
declare f_guidcategory int;
INSERT INTO TABLEB
SET
f_guidcategoryiteminstance =(SELECT guidcategoryiteminstance FROM inserted),
f_guidcategory =(SELECT guidcategory FROM inserted),
guiduser= f_guidcategory,
guidcategoryinstance= f_guidcategoryiteminstance,
number= number +1,
dateofaction= NOW(); END
The trigger can be added to the DB fine. However, when I attempt to update a row on table A (which should cause the trigger to run), I get an error stating that the table Inserted does not exist. However, I was under the impression that Inserted should be a logical table that contains the results of the initial part of the trigger. Is this only the case if the trigger is being run on an insert and not an update? If so, is there an equivalent for an update trigger?

INSTEAD OF UPDATE,DELETE,INSERT : determine each command

I need determine each of this this 3 commands in trigger [UPDATE,DELETE,INSERT].For last 2 I do next:
IF EXISTS (SELECT * FROM inserted)
BEGIN
END
ELSE IF EXISTS (SELECT * FROM deleted)
BEGIN
END
How can I get updating rows?
Thanks.
Not exactly sure what you're trying to accomplish, but you can test if it's an UPDATE if both inserted (values after update) and deleted (values before update) exist. From the documentation:
The deleted table stores copies of the affected rows during DELETE
and UPDATE statements. During the execution of a DELETE or UPDATE
statement, rows are deleted from the trigger table and transferred to
the deleted table. The deleted table and the trigger table ordinarily
have no rows in common.
The inserted table stores copies of the affected rows during
INSERT and UPDATE statements. During an insert or update
transaction, new rows are added to both the inserted table and the
trigger table. The rows in the inserted table are copies of the new
rows in the trigger table.
Thus, if inserted exists but not deleted, it's an INSERT; if deleted exists but not inserted, it's a DELETE; if they both exist, it's an UPDATE.

Move data from one table to another using on update trigger

I am new to DB development. Please help me create a trigger for moving data from one table to another.
I have two tables, one contains "Transaction Status" from where I want to move records on transaction status change into another table having completed transactions. So the value in one table will get deleted and will get inserted into another table.
Please correct me in the following trigger:
create trigger transaction_state after update on test_archive for each row begin
insert into test_me(select * from test_archive where new.Transaction_status = 2);
delete from test_archive where new.Transaction_status = 2;
end;
Why do I feel like I am helping you with homework? Your trigger, as written, will probably move ALL rows when someone updates a row to Transaction_Status=2. Since you didn't join the NEW table to the test_archive table, your WHERE clauses will be true for all rows.
if you really want all rows with Transaction_status=2 moved from test_archive to test_me, then get rid of the FOR EACH and the references to the NEW table.
create trigger transaction_state after update on test_archive
begin
insert into test_me
select * from test_archive where Transaction_status = 2;
delete from test_archive where Transaction_status = 2;
end;