i have this homework to do and im into a problem creating triggers,
i have to make an update trigger so i have this table
+----+------+
| id | name |
+----+------+
| 1 | x |
+----+------+
| 2 | y |
+----+------+
| 3 | z |
+----+------+
so, the trigger i was thinking to do is this one
DELIMITER ||
CREATE TRIGGER updateID AFTER DELETE
ON personalData FOR EACH ROW
BEGIN
UPDATE personalData
SET id = id - 1
WHERE id > old.id;
END ||
DELIMITER ;
the idea is if some user is deleted the id would be updated, as an expample
if x is deleted the table would be
+----+------+
| id | name |
+----+------+
| 1 | y |
+----+------+
| 2 | z |
+----+------+
when i try to create the trigger the following error shows:
Error Code: 2014. Commands out of sync; you can't run this command now
I was searching for info, but i cant see whats wrong
Related
The goal here is to update and concatenate a text field from one table to another based on conditions. When a text col gets updated with some text from a user form, run After update trigger.
The trigger runs but updates all the columns not just the one that has changed.Trying to understand how to just update the correct row only.
Here's what i have so far-
SQLFiddle
| ID | SUBID | SWNOTES |
|----|-------|---------| Table 1
| 1 | 40 | test |
| 2 | 60 | |
| ID | SUBID | CONTENT | SWFLAG |
|----|-------|---------|--------|
| 1 | 40 | hello | 0 | Table 2
| 2 | 60 | nothing | 0 |
CREATE TRIGGER `updatecontentnotes` AFTER UPDATE ON `tab1`
FOR EACH ROW
BEGIN
IF New.swnotes <> OLD.swnotes
THEN
Update `tab2`
Inner Join `tab1` ON `tab2`.`subid` = `tab1`.`subid`
Set `tab2`.`swflag` = '1',`tab2`.`content` = CONCAT(`tab2`.`content`, `tab1`.`swnotes`)
Where `tab2`.`subid` = `tab1`.`subid` AND `tab2`.`swflag` = '0';
END IF;
END//
And if I update the table with say:
Update `tab1`
set `swnotes` = "new"
where `subid` = '60'
I get :
| ID | SUBID | CONTENT | SWFLAG |
|----|-------|------------|--------|
| 1 | 40 | hellotest | 1 |
| 2 | 60 | nothingnew | 1 |
Now I know it is doing what I am telling it to do. I want to update just the row that is updated. Thanks for any help on this.
Since the contents of your trigger will run for every row on tab1, you need to be more restrictive in your WHERE clause so that it will only affect the rows that have been updated. Right now it updates every row on tab2
Try adding this to your trigger SQL:
From:
Where `tab2`.`subid` = `tab1`.`subid` AND `tab2`.`swflag` = '0';
To:
Where `tab2`.`subid` = `tab1`.`subid` AND `tab2`.`swflag` = '0' AND `tab2`.`id` = OLD.id;
This produces the results that I think you are looking for:
| ID | SUBID | CONTENT | SWFLAG |
|----|-------|------------|--------|
| 1 | 40 | hello | 0 |
| 2 | 60 | nothingnew | 1 |
The updated SQLFiddle is here:
http://sqlfiddle.com/#!2/9fa2d2/1/0
i am new to this and want some help.i have table with name "abc" with following entries
+------+--------+------+
| Id | Name | City |
+------+--------+------+
| 101 | john | abc |
| 102 | Miller | cbz |
+------+--------+------+
and another table "xyz"
+------+--------+------+
| Id | Name | City |
+------+--------+------+
| 102 | Miller | cbz |
+------+--------+------+
i applied trigger on table "abc" which will update the table "xyz" with recently inserted values and will delete all previous entries...
for example, when i fire insert query on "abc" table i get ,"abc" as follow
insert into abc Values(103,'Joseph','xyz');
i get output for table "abc" as,
+------+--------+------+
| Id | Name | City |
+------+--------+------+
| 101 | john | abc |
| 102 | Miller | cbz |
| 103 | Joseph | xyz |
+------+--------+------+
and table "xyz" as,
+------+--------+------+
| Id | Name | City |
+------+--------+------+
| 103 | Joseph | xyz |
+------+--------+------+
now my question is how to acheive this using only one table(i dont want to use two table as this is not my requirement).
like following ..
insert into xyz values(104,'Ridhit','pqr');
+------+--------+------+
| Id | Name | City |
+------+--------+------+
| 104 | Ridhit | pqr |
+------+--------+------+
Please help.Trigger i used is
DELIMITER !!
create trigger OnlyOne BEFORE INSERT on abc
for each row
BEGIN
DECLARE a1 INT;
Select count(1) INTO a1 from xyz;
IF a1>0 THEN
delete from xyz limit 1;
insert into xyz(Id,Name,City) values (new.Id,new.Name,new.City);
ELSE
insert into xyz(Id,Name,City) values (new.Id,new.Name,new.City);
END IF;
END;
!!
DELIMITER ;
Do this on application level, but you better make sure you use transactions. You probably don't want to have an empty table, when the operation crashes in the middle.
You may also consider to have following approach.
Instead of deleting/updating whenever an insert occurs, add a column like created with default value of current timestamp to your table so that it looks something like this:
CREATE TABLE abc(
id int auto_increment primary key,
name varchar(50),
city varchar(50),
created timestamp default current_timestamp
);
To get the latest entry you just do
SELECT * FROM abc ORDER BY created DESC LIMIT 1;
Or you put this in a view
CREATE VIEW just_latest_entry_from_abc AS
SELECT * FROM abc ORDER BY created DESC LIMIT 1;
Then you just do
SELECT * FROM just_latest_entry_from_abc;
When table size matters, create a cronjob or a scheduled event to delete older entries on a regular basis.
I'm currently working with a client that wants their database to duplicate info into a second table in a different format when it is initially inserted.
Basically like the following:
Table 1
| ID | NAME | EMAIL | password |
--------------------------------------
| 1 | david | x#x.co | asx234 |
| 2 | anthony | y#x.co | 24gss3 |
| 3 | jillian | z#x.co | hdfg5d |
Every time a row gets inserted into table 1 they also want to take that information from table 1 and add it to Table 2
Table 2
| ID | NAME | EMAIL | password | signature | level | lastenter | register_date |
-----------------------------------------------------------------------------------------------
| 1 | david | x#x.co | asx234 | text | 3 | 0000-00-00 | Date of insert |
| 2 | anthony | y#x.co | 24gss3 | text | 3 | 0000-00-00 | Date of insert |
| 3 | jillian | z#x.co | hdfg5d | text | 3 | 0000-00-00 | Date of insert |
How do I set up a trigger to insert the data into Table 2 whenever a row is inserted into table 1?
Thanks!
Some thoughts below, but the trigger would look something like this:
DELIMITER $$
DROP TRIGGER IF EXISTS trgMyNewTrigger $$
CREATE TRIGGER trgMyNewTrigger AFTER INSERT ON Table1
FOR EACH ROW
BEGIN
INSERT into Table2 (ID,NAME,EMAIL,`password`,signature,`level`,lastenter,register_date) VALUES (
new.ID, new.NAME, new.EMAIL, new.password, 'text', 3, '0000-00-00', CURDATE() );
END $$
DELIMITER ;
This is not a great solution. Triggers in general can cause some nasty issues and limit your capabilities down the road. It would be better to reconsider the design of the table to be inclusive of the data you need, have the application perform the extra step or use some sort of ETL process to get the data at set intervals.
I will all assume the clear text passwords are for the example.
Basically I have two tables A and B. These are linked by unique ID's where the entries in B point to one entry in A. The entries in A and B also have a 'status' field denoting if the entry is active or not...
My questions is therefore; is it possible to link the status field of the entries in B and have them update, every time the 'status' field in A (pointed to by the unique ID) is updated? I could do this fairly easy with an SQL command however I'm wondering if there is a more automatic solution. Example:
table A
|------ID------|----status----|
| 1 | on |
| 2 | on |
|---------------|----------------|
table B
|-----eID------|------ID------|----status----|
| 1 | 1 | on |
| 2 | 1 | on |
| 3 | 2 | on |
|---------------|---------------|----------------|
I then run:
UPDATE `A` SET `status` = 'off' WHERE `ID` = 1;
And the result would be:
table A
|------ID------|----status----|
| 1 | off |
| 2 | on |
|---------------|---------------|
table B
|-----eID------|------ID------|----status----|
| 1 | 1 | off |
| 2 | 1 | off |
| 3 | 2 | on |
|---------------|---------------|----------------|
Is that possible?
Many Regards,
Andreas
i hope this trigger code can help u.
CREATE TRIGGER `abc` AFTER UPDATE ON `tablea` FOR EACH ROW BEGIN UPDATE tableb SET STATUS = new.status WHERE id = new.id;
END
I have a database in MySQL. Here is SQL query to create it http://paste.org.ru/?xzctqi
Here is main table books. All I need to do is when I add some book, I choose publisher ID for it. After adding books, I need loop through all records in this table and increment column publisher_books_amount for all rows, which has same publisher as in currently added row.
+----+-------+--------+------------------------+-----------+
| id | title | author | publisher_books_amount | publisher |
+----+-------+--------+------------------------+-----------+
| 1 | Book1 | 1 | 0 | 1 |
| 2 | Book2 | 2 | 0 | 1 |
| 3 | Book3 | 1 | 0 | 2 |
| 4 | Book4 | 3 | 0 | 3 |
| 5 | Book1 | 3 | 0 | 1 |
+----+-------+--------+------------------------+-----------+
I've created trigger
DROP TRIGGER IF EXISTS `insert_trigger`;
DELIMITER |
CREATE TRIGGER `insert_trigger` AFTER INSERT ON books
FOR EACH ROW
BEGIN
UPDATE books SET publisher_books_amount = (publisher_books_amount + 1)
WHERE publisher = NEW.publisher;
END;
|
DELIMITER ;
But when I'm trying to add book, MySQL provides me with an error.
Can't update table 'books' in stored function/trigger because it is
already used by statement which invoked this stored function/trigger.
Don't ask me why do I have denormalized DB. I just need structure described above.
BTW I need to create same triggers after deleting and updating rows. If there are some problems with that, could you help me with it too?
Sincerely, Dmitriy.
Update inside a loop is not allowed, because it goes to infinite loop.
Try your triiger without update,with only set value this=this.