965 votes

Comment spécifier une contrainte unique pour plusieurs colonnes dans MySQL ?

J'ai une table :

table votes (
    id,
    user,
    email,
    address,
    primary key(id),
);

Maintenant je veux faire les colonnes utilisateur, email, adresse unique (ensemble).

Comment puis-je faire cela dans MySql ?

Bien sûr, l'exemple n'est qu'un... exemple. Alors ne vous inquiétez pas de la sémantique.

1591voto

jonstjohn Points 23326

Pour ajouter une contrainte unique, vous devez utiliser deux composants :

ALTER TABLE - pour modifier le schéma de la table et,

ADD UNIQUE - pour ajouter la contrainte unique.

Vous pouvez ensuite définir votre nouvelle clé unique avec le format 'name'('column1', 'column2'...)

Donc pour votre problème particulier, vous pouvez utiliser cette commande :

ALTER TABLE `votes` ADD UNIQUE `unique_index`(`user`, `email`, `address`);

37 votes

Cela fonctionnerait-il correctement avec la clause ON DUPLICATE KEY des instructions INSERT ? En d'autres termes, si j'essayais d'insérer une ligne qui entre en conflit avec les valeurs utilisateur/email/adresse d'une autre ligne, l'INSERT effectuerait-il les actions spécifiées par la clause ON DUPLICATE KEY à la place ?

11 votes

De cette façon, la combinaison des trois serait unique ? Ou les trois colonnes individuelles seraient uniques ?

114 votes

Pour les personnes qui utilisent MySQL workbench : allez dans l'onglet Indexes et sélectionnez UNIQUE comme type. Donnez un nom à votre index et cochez les colonnes appropriées dans la section "Colonnes d'index".

271voto

Frodik Points 2739

J'ai une table MySQL :

CREATE TABLE `content_html` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `id_box_elements` int(11) DEFAULT NULL,
  `id_router` int(11) DEFAULT NULL,
  `content` mediumtext COLLATE utf8_czech_ci NOT NULL,
  PRIMARY KEY (`id`),
  UNIQUE KEY `id_box_elements` (`id_box_elements`,`id_router`)
);

et la CLÉ UNIQUE fonctionne comme prévu, elle permet plusieurs lignes NULL de id_box_elements et id_router.

J'utilise MySQL 5.1.42, il y a donc probablement eu une mise à jour du problème évoqué ci-dessus. Heureusement, cela fonctionne et j'espère que cela restera ainsi.

40 votes

Je voulais signaler cette réponse car elle vous montre comment créer une nouvelle table avec un index unique alors que la réponse de jonstjohn ci-dessus vous indique comment mettre à jour une table existante. Elles font la même chose, mais tout dépend si vous créez une nouvelle table ou si vous mettez à jour une table existante :)

3 votes

C'est quoi toutes ces citations, elles servent à quelque chose ?

8 votes

La sortie se fait à partir d'Adminer (www.adminer.org), qui insère automatiquement ces guillemets, de sorte qu'il n'y a pas de problème de collision entre les mots-clés mysql utilisés comme noms de colonnes.

58voto

niksoft Points 209

Les index uniques multi-colonnes ne fonctionnent pas dans MySQL si vous avez une valeur NULL dans une ligne, car MySQL considère NULL comme une valeur unique et n'a pas de logique pour contourner ce problème dans les index multi-colonnes, du moins actuellement. Oui, ce comportement est insensé, car il limite un grand nombre d'applications légitimes des index multi-colonnes, mais il est ce qu'il est... Pour l'instant, c'est un bogue qui a été marqué du sceau "will not fix" sur le bug-track de MySQL...

11 votes

Deux points de clarification : 1) ce comportement n'est pas valable pour ENGINE BDB et, 2) c'est documenté Bien que, à mon avis, ce comportement ne soit pas suffisamment documenté étant donné qu'il peut être surprenant et désagréable. Voir le bogue MySQL 25544 bugs.mysql.com/bug.php?id=25544 pour une discussion.

3 votes

Merci pour le NULL heads up, qui a résolu le problème que j'avais... Je pense que je vais utiliser une somme de contrôle de type hash.

0 votes

Les documents officiels disent : Notez que, depuis MySQL 5.1, BDB n'est plus supporté.

25voto

Erick Points 2430

Avez-vous essayé ceci ?

UNIQUE KEY `thekey` (`user`,`email`,`address`)

0 votes

Ce que dit Erick fonctionne très bien pour moi : UNIQUE KEY la clé " ( user , email , address )`. J'utilise la version 5.5.24 de MYSQL. Vous pouvez définir ceci même dans PHPMYADMIN si vous l'utilisez. J'utilise la version 3.5.1 de PMA.

0 votes

Je l'ai essayé avec MySQL 5.6. Fonctionne du premier coup. Merci Erick !

16voto

rizon Points 2751

Cela fonctionne pour mysql version 5.5.32

ALTER TABLE  `tablename` ADD UNIQUE (`column1` ,`column2`);

1 votes

Il semble fonctionner sans les guillemets simples sur le nom de la colonne.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X