I started by googling, and found this article which talks about mutex tables.
I have a table with ~14 million records. If I want to add more data in the same format, is there a way to ensure the record I want to insert does not already exist without using a pair of queries (ie, one query to check and one to insert is the result set is empty)?
Does a unique
constraint on a field guarantee the insert
will fail if it's already there?
It seems that with merely a constraint, when I issue the insert via php, the script croaks.
If the record exists, it will be overwritten; if it does not yet exist, it will be created.
Alternatively, the outer
SELECT
statement can refer toDUAL
in order to handle the case where the table is initially empty:use
INSERT IGNORE INTO table
see http://bogdan.org.ua/2007/10/18/mysql-insert-if-not-exists-syntax.html
there's also
INSERT … ON DUPLICATE KEY UPDATE
syntax, you can find explanations on dev.mysql.comPost from bogdan.org.ua according to Google's webcache:
Here is a PHP function that will insert a row only if all the specified columns values don't already exist in the table.
If one of the columns differ, the row will be added.
If the table is empty, the row will be added.
If a row exists where all the specified columns have the specified values, the row won't be added.
Example usage :
Any simple constraint should do the job, if an exception is acceptable. Examples :
Sorry is this seems deceptively simple. I know it looks bad confronted to the link you share with us. ;-(
But I neverleless give this answer, because it seem to fill your need. (If not, it may trigger your updating your requirements, which would be "a Good Thing"(TM) also).
Edited: If an insert would break the database unique constraint, an exception is throw at the database level, relayed by the driver. It will certainly stop your script, with a failure. It must be possible in PHP to adress that case ...
There are several answers that cover how to solve this if you have a
UNIQUE
index that you can check against withON DUPLICATE KEY
orINSERT IGNORE
. That is not always the case, and asUNIQUE
has a length constraint (1000 bytes) you might not be able to change that. For example, I had to work with metadata in WordPress (wp_postmeta
).I finally solved it with two queries:
Query 1 is a regular
UPDATE
query with no effect when the dataset in question is not there. Query 2 is anINSERT
which depends on aNOT EXISTS
, i.e. theINSERT
is only executed when the dataset doesn't exist.