Ik execute a query that inserts some values in de table, if a combination of ID, Year, rownum (unique index) exists that i do a regular ON DUPLICATE KEY UPDATE and so the row is updated. The query looks like this:
INSERT INTO data_advertenties_prijzen (`ID`, `year`, `rownum`, `status_prijs`,
`datum_dag`, `timestamp_dag`)
VALUES (100,2014,1,1,'2014-01-01',1388534400),
(100,2014,2,1,'2014-07-16',1405468800),
(100,2014,3,1,'2014-07-26',1406332800)
ON DUPLICATE KEY UPDATE
status_prijs = VALUES(status_prijs),
datum_dag = VALUES(datum_dag),
timestamp_dag = VALUES(timestamp_dag)
Nothing difficults there, but….
I also want to do a ON DUPLICATE IGNORE for 1 value in the same query. I Also want to insert one row for 2015. For example: (100,2015,1,1,'2015-01-01',1405468800)…
If there is already a row with ID=100, Year=2015 And rownum=1 the insert of that row must be ignored.
How to do that?
You could change the values conditionally in the ON DUPLICATE clause.
I did this experiment to make sure it works:
INSERT INTO data_advertenties_prijzen VALUES (100, 2014, 1, 7, now(), 1406332800)
ON DUPLICATE KEY UPDATE
status_prijs = IF((id,year,rownum)=(100,2015,1), status_prijs, VALUES(status_prijs)),
datum_dag = IF((id,year,rownum)=(100,2015,1), datum_dag, VALUES(datum_dag)),
timestamp_dag = IF((id,year,rownum)=(100,2015,1), timestamp_dag, VALUES(timestamp_dag));
So if I try to insert a specific trio of id/year/rownum, it just uses the existing value, else if it's some other id/year/rownum, it uses the VALUES I specify in the INSERT.
Unfortunately, you must repeat the expression for each column you want to update.
Related
I would like to do something like this (the updated value should be different than the inserted value):
"INSERT INTO notification_chat_counts (uid,group_id,count)
VALUES
(",$uid,",",$groupId,",1)
ON DUPLICATE KEY UPDATE
(count = count +1)"
Of course it is possible. Even the MySQL manual has example of inserting different value that the values which would got updated:
INSERT INTO table (a,b,c) VALUES (1,2,3) ON DUPLICATE KEY UPDATE c=c+1;
For your example, the correct query syntax would be:
$query = "INSERT INTO notification_chat_counts (uid,group_id,count)
VALUES (",$uid,",",$groupId,",1)
ON DUPLICATE KEY UPDATE count=count+1"
However for this statement to work you must have an UNIQUE type index defined for this table, so that MySQL can decide if such row already exists in the table or not.
Also remember that inserting values into SQL query like this is dangerous and not recommended. You should use prepared statements for that.
Structure table:
id (int primary key)
name (varchar 100)
date(datetime)
For insert I use query:
INSERT INTO table (name, date) VALUES ('t1','$date');
For delete row I use query:
DELETE FROM table WHERE name = 't1';
I would like want how make 1 query: first insert, if row with it name already exist, than delete row, and insert again.
Tell me please how to make it?
Create a UNIQUE index over your name column:
ALTER TABLE `table` ADD UNIQUE (name);
If you genuinely want to "delete row and insert again", then you can use REPLACE instead of INSERT. As documented:
REPLACE works exactly like INSERT, except that if an old row in the table has the same value as a new row for a PRIMARY KEY or a UNIQUE index, the old row is deleted before the new row is inserted.
Therefore, in your case:
REPLACE INTO `table` (name, date) VALUES ('t1','$date');
However, if instead of deleting the existing record and then inserting a new one you merely want to update the existing record, you can use INSERT ... ON DUPLICATE KEY UPDATE:
INSERT INTO `table` (name, date) VALUES ('t1','$date')
ON DUPLICATE KEY UPDATE date = VALUES(date);
The most material difference is in the treatment of columns for which you do not provide explicit values (such as id in your example): REPLACE will result in the new record having the default value, whereas INSERT ... ON DUPLICATE KEY UPDATE will result in the old value being retained.
What you want to do is use MySQL's on duplicate update feature.
Can be used like this :
INSERT INTO table (name, date) VALUES ('t1','$date')
ON DUPLICATE KEY UPDATE name=VALUES(name),dateVALUES(date);
Of course for that to happen a dupliate violation must occur.
insert into table (name, date) values('t1','$date') on duplicate key update name=values(name), date=values(date)
Are you looking for an update query?
Update will set a value on an already existing row.
UPDATE table SET date = '$newdate' WHERE name = 't1';
The best way to do this is using the mysql methods together with your query.
If you make the 'name' field unique:
id (int primary key)
name (varchar 100) NOT NULL UNIQUE
date(datetime)
And alter the query to:
INSERT INTO table
(name, date) VALUES ('t1','$date')
ON DUPLICATE KEY UPDATE date = "$date"
I have a MySQL query that is meant to update two columns by increments of 1, or create them if they do not exist.
My current table has four columns: id, username, playtime, and deathtime.
As it stands now, this is the query I use:
INSERT INTO `playTime` (`username`, `playtime`, `deathtime`)
VALUES ('Rogue', 1, 1)
ON DUPLICATE KEY UPDATE `playtime`=`playtime`+1
AND `deathtime`=`deathtime`+1
(The username is dynamic in application, but one is provided for the example).
My issue, however, is that on a duplicate key it doesn't increment the values, rather it sets both values to 0. Through numerous tests of tweaking the query, I have found that it is the AND clause that causes the query to "reset" the values. For instance, this query will increment the playtime column correctly:
INSERT INTO `playTime` (`username`, `playtime`, `deathtime`)
VALUES ('Rogue', 1, 1)
ON DUPLICATE KEY UPDATE `playtime`=`playtime`+1
And if you swap "playtime" with "deathtime", then it increments the other column correctly. Why is this?
Use a comma to delimit statements here.
INSERT INTO `playTime` (`username`, `playtime`, `deathtime`)
VALUES ('Rogue', 1, 1)
ON DUPLICATE KEY UPDATE `playtime`=`playtime`+1, `deathtime`=`deathtime`+1
The example can be seen in the documentation here: http://dev.mysql.com/doc/refman/5.0/en/insert-on-duplicate.html
Try this.. a comma, instead of AND
INSERT INTO `playTime` (`username`, `playtime`, `deathtime`)
VALUES ('Rogue', 1, 1)
ON DUPLICATE KEY UPDATE `playtime`=`playtime`+1 ,
`deathtime`=`deathtime`+1
Consider this statement:
INSERT INTO table (a,b,c) VALUES (1,2,3) ON DUPLICATE KEY UPDATE d=d+1;
I need the value of d.
Is it possible to obtain it without performing a further SELECT?
There is a unique index on a,b,c. Would this index be used for better performance? This table will have a large number of rows.
Assuming you will be running both queries using the same connection, You can use the LAST_INSERT_ID(expr) function to set the current value of d, and check the value of LAST_INSERT_ID() together with the ROW_COUNT() function to find out if the record was inserted or updated:
INSERT INTO table (a,b,c)
VALUES (1,2,3)
ON DUPLICATE KEY UPDATE d = LAST_INSERT_ID(d + 1);
SELECT IF(ROW_COUNT() = 2, LAST_INSERT_ID(), 0 /*default value*/) ;
You can also use session variables:
INSERT INTO table (a,b,c)
VALUES (1,2,3)
ON DUPLICATE KEY UPDATE d = #tmp := (d + 1);
SELECT IF(ROW_COUNT() = 2, #tmp, 0 /*default value*/) ;
I have a table with columns record_id (auto inc), sender, sent_time and status.
In case there isn't any record of a particular sender, for example "sender1", I have to INSERT a new record otherwise I have to UPDATE the existing record which belongs to "user1".
So if there isn't any record already stored, I would execute
# record_id is AUTO_INCREMENT field
INSERT INTO messages (sender, sent_time, status)
VALUES (#sender, time, #status)
Otherwise I would execute UPDATE statement.
Anyway.. does anyone know how to combine these two statements in order to insert a new record if there isn't any record where the field sender value is "user1" otherwise update the existing record?
MySQL supports the insert-on-duplicate syntax, f.e.:
INSERT INTO table (key,col1) VALUES (1,2)
ON DUPLICATE KEY UPDATE col1 = 2;
If you have solid constraints on the table, then you can also use the REPLACE INTO for that. Here's a cite from MySQL:
REPLACE works exactly like INSERT, except that if an old row in the table has the same value as a new row for a PRIMARY KEY or a UNIQUE index, the old row is deleted before the new row is inserted.
The syntax is basically the same as INSERT INTO, just replace INSERT by REPLACE.
INSERT INTO messages (sender, sent_time, status) VALUES (#sender, time, #status)
would then be
REPLACE INTO messages (sender, sent_time, status) VALUES (#sender, time, #status)
Note that this is a MySQL-specific command which doesn't occur in other DB's, so keep portability in mind.
As others have mentioned, you should use "insert...on duplicate key update", sometimes referred to as an "upsert". However, in your specific case you don't want to use a static value in the update, but rather the values you pass in to the values clause of the insert statement.
Specifically, I think you want to update two columns if the row already exists:
1) sent_time
2) status
In order to do this, you would use an "upsert" statement like this (using your example):
INSERT INTO messages (sender, sent_time, status)
VALUES (#sender, time, #status)
ON DUPLICATE KEY UPDATE
sent_time = values(sent_time),
status = values(status);
Check out "Insert on Duplicate Key Update".
INSERT INTO table (a,b,c) VALUES (1,2,3)
ON DUPLICATE KEY UPDATE c=c+1;
UPDATE table SET c=c+1 WHERE a=1;
One options is using on duplicate update syntax
http://dev.mysql.com/doc/refman/5.1/en/insert-on-duplicate.html
Other options is doing select to figure out if record exists and then doind inser/update accordingly. Mind that if you're withing transaction select will not explicitly terminate the transaction so it's safe using it.
use merge statement :
merge into T1
using T2
on (T1.ID = T2.ID)
when matched
then update set
T1.Name = T2.Name
when not matched
then insert values (T2.ID,T2.Name);