2012-02-08 15 views
17

que tengo una tabla básica con columnas:Demasiados incrementos de automóviles con ON DUPLICATE KEY UPDATE

  • id (primaria con AI)
  • nombre (singular)
  • etc

Si la columna única no existe, INSERTAR la fila; de lo contrario, ACTUALIZAR la fila ....

INSERT INTO pages (name, etc) 
VALUES 
    'bob', 
    'randomness' 
ON DUPLICATE KEY UPDATE 
name = VALUES(name), 
etc = VALUES(etc) 

El problema es que si realiza una ACTUALIZACIÓN, el valor de auto_increment en la columna de ID aumenta. Entonces, si se realizan un montón de ACTUALIZACIONES, el id auto_increment se dispara.

parece ser que era un error: http://bugs.mysql.com/bug.php?id=28781

... pero yo estoy usando InnoDB en MySQL 5.5.8 de alojamiento compartido.

Otras personas que tienen problemas con la de hace años no hay solución: prevent autoincrement on MYSQL duplicate insert y Why does MySQL autoincrement increase on failed inserts?

ideas en una solución? ¿He estructurado la base de datos incorrectamente de alguna manera?

****** EDIT ****: Parece que agregar innodb_autoinc_lock_mode = 0 a su archivo my.ini corrige el problema, pero ¿qué opciones tengo para el alojamiento compartido?

****** EDIT 2 ******: OK, creo que mi única opción es cambiar a MyISAM como el motor de almacenamiento. Al ser un novato mega mySQL, espero que no cause muchos problemas. ¿Sí?

+0

Un gran problema con MyISAM es que no es compatible con la definición de las relaciones de bases de datos. InnoDB sí lo admite. – bakkerjoeri

+2

innodb_autoinc_lock_mode = 0 trabajado para mí. gracias –

+0

Cambié a Aria (MyISAM en MariaDB) que impide el auto_increment – DanFromGermany

Respuesta

12

No creo que haya una forma de eludir este comportamiento de INSERT ... ON DUPLICTE KEY UPDATE.

Sin embargo, puede poner dos estados, uno UPDATE y uno INSERT, en una transaction:

START TRANSACTION ; 

UPDATE pages 
SET etc = 'randomness' 
WHERE name = 'bob' ; 

INSERT INTO pages (name, etc) 
SELECT 
     'bob' AS name 
    , 'randomness' AS etc 
FROM dual 
WHERE NOT EXISTS 
     (SELECT * 
     FROM pages p 
     WHERE p.name = 'bob' 
    ) ; 

COMMIT ; 
+0

Gracias amigo. Terminé yendo por esta ruta. Ese problema de incremento automático es un dolor en el culo. No necesitaba las partes "AS name" y "AS etc". –

+0

No, esos alias no son necesarios, de hecho. –

+0

@NathanWaters: Se agregó un enlace a la documentación de MySQL sobre transacciones. –

-3

La funcionalidad de clave duplicada de MySQL es exactamente la misma que hacer dos consultas separadas, una para seleccionar, luego una para actualizar el registro seleccionado o insertar un nuevo registro. Hacerlo programáticamente es igual de rápido y evitará este problema en el futuro, además de hacer que su código sea más portátil.

+3

no es tan rápido de acuerdo con lo que estoy viendo –

Cuestiones relacionadas