2009-09-22 9 views
6

J'ai un tableau comme indiqué ci-dessous. Pour contourner un défaut maintenant restriction de la colonne de MySQL je la pointe comme le montre hereValeur par défaut de l'horodatage de deux colonnes MySQL ERREUR 1067

CREATE TABLE IF NOT EXISTS mytable (
    id INT NOT NULL AUTO_INCREMENT , 
    create_date TIMESTAMP NULL DEFAULT '0000-00-00 00:00:00' , 
    update_date TIMESTAMP NULL DEFAULT NOW() ON UPDATE NOW() , 
    PRIMARY KEY (`parti_id`)) 
ENGINE = InnoDB; 

Mon sql_mode ne comprend pas NO_ZERO_DATE comme l'a here ma sortie:

mysql> SELECT @@sql_mode; 
+------------+ 
| @@sql_mode | 
+------------+ 
|   | 
+------------+ 
1 row in set (0.00 sec) 

Il est encore donner l'erreur comme indiqué ci-dessous:

ERROR 1067 (42000) at line xx in file: '/myschema.sql': Invalid default value for 'create_date' 

J'utilise MySQL 5.1.37 sur Ubuntu

Comment puis-je résoudre ce problème? Merci.

Répondre

12

Vous ne pouvez avoir une colonne horodatage par défaut CURRENT_TIMESTAMP ou NOW() par table. C'est un bug bien connu dans MySQL. Pour résoudre ce problème, définissez une valeur d'horodatage valide pour la colonne créée, puis insérez l'horodatage dans votre code d'application CRUD. Utilisez NOW() ou CURRENT_TIMESTAMP pour la mise à jour de la colonne par défaut.

Documents de référence: http://dev.mysql.com/doc/refman/5.1/en/timestamp.html

Pour illustrer davantage la lacune de MySQL dans ce domaine, considérez le code suivant:

CREATE TABLE testing_timestamps (
    id INT NOT NULL AUTO_INCREMENT, 
    pk_id INT NOT NULL, 
    col1 TIMESTAMP DEFAULT 0, 
    col2 TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, 
    PRIMARY KEY(id) 
); 

delimiter $$ 
CREATE TRIGGER testing_timestamps_trigger 
    AFTER INSERT ON testing_timestamps 
    FOR EACH ROW 
    BEGIN 
    UPDATE testing_timestamps SET col1 = NOW() WHERE id = MAX(id); 
    END; 
$$ 
delimiter ; 

INSERT INTO testing_timestamps (id) VALUES (0); 

La sortie de cet écran de volonté:

mysql> INSERT INTO testing_timestamps (id) VALUES (0); 
ERROR 1442 (HY000): Can't update table 'testing_timestamps' in stored function/trigger because it is already used by statement which invoked this stored function/trigger. 

C'est un bummer parce que l'utilisation d'un déclencheur dans ce cas serait un bon travail.

+0

Ce n'est pas un bug, il est une caractéristique: « Pour une colonne TIMESTAMP dans une table, vous pouvez attribuer l'horodatage en cours comme valeur par défaut et la valeur mise à jour automatique Il est possible que l'horodatage actuel soit la valeur par défaut pour l'initialisation de la colonne, pour la valeur de mise à jour automatique ou les deux Il n'est pas possible que l'horodatage actuel soit la valeur par défaut pour une colonne et la valeur de mise à jour automatique pour une autre colonne. " –

+0

Le débat sur la question de savoir s'il s'agit d'un" bug "ou non reste car cela est très ennuyeux. Pourquoi ne puis-je pas avoir deux colonnes d'horodatage avec une valeur par défaut de now() avec la deuxième colonne de mise à jour automatique? La réponse est que MySQL ne fait pas ça. Je n'appelle pas vraiment cela une fonctionnalité. –

+0

Randy merci pour votre réponse. Je suis conscient du lien que vous avez fourni. Je cherche juste une solution de contournement. Cependant, il semble que toutes les astuces affichées sur Internet ne fonctionnent tout simplement pas. –

7

En fait, le code de Randy est cassé. Ça ne marchera pas parce que c'est un déclencheur de mutation. Vous ne pouvez pas mettre à jour la table qui a initié la mise à jour. Par exemple, si vous mettez à jour la table SESSIONS, vous ne pouvez pas modifier la table dans votre déclencheur en utilisant une instruction UPDATE, INSERT ou DELETE. La seule façon dont vous êtes autorisé à modifier la table à laquelle le déclencheur est attaché est d'utiliser les préfixes "NEW" ou "OLD" comme démontré ci-dessous. (Bien sûr, vous êtes autorisé à mettre à jour d'autres tables à volonté.) Voici un exemple de la façon de surmonter le problème décrit par l'op.

create table sessions (
    id integer not null, 
    created timestamp not null default 0, 
    updated timestamp not null default 0 
); 

delimiter // 
create trigger bifer_sessions_ts before insert on sessions for each row 
begin 
    set new.created = now(); 
    set new.updated = now(); 
end; 
// 
create trigger bufer_sessions_ts before update on sessions for each row 
begin 
    set new.updated = now(); 
end; 
// 
delimiter ; 
1

Pour ce faire et le faire fonctionner:

col1 TIMESTAMP DEFAULT 0, 

col2 TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, 

Vous n'avez pas besoin d'un déclencheur pour col1, assurez-vous que la valeur est NULL dans votre requête. La réponse est dans le guide de certification.

0

Par défaut TIMESTAMP n'est pas supporté dans MySQL avant les versions 5.6.1 dans la même table.

Après la version MySQL 5.6. +, Il autorise deux ou plusieurs colonnes TIMESTAMP dans la même table.

Vous pouvez mettre à jour votre version de MySQL

Questions connexes