2009-11-12 2 views
0

J'ai une table mysql qui contient des pièces IPAddressInnoDB Transaction Aide - Sélectionnez ensuite si Introuvable Ajouter unique ligne

TABLE `EndPoints`(
    `EndPointId` BIGINT(19) UNSIGNED NOT NULL AUTO_INCREMENT , 
    `IpPart1` TINYINT(3) UNSIGNED NOT NULL , 
    `IpPart2` TINYINT(3) UNSIGNED NOT NULL , 
    `IpPart3` TINYINT(3) UNSIGNED NOT NULL , 
    `IpPart4` TINYINT(3) UNSIGNED NOT NULL , 
    PRIMARY KEY (`EndPointId`)) 
ENGINE = InnoDB 

Chaque IpPart contient l'octet d'un tableau d'octets IPADDRESS. par exemple. adresse 100.101.102.103
IpPart1 = 101;
IpPart2 = 102;
IpPart3 = 103;
IpPart4 = 104;


Quoi qu'il en soit!

Je veux faire ce qui suit:

SELECT EndPointId FROM EndPoints WHERE 
    IpPart1 = @a AND 
    IpPart2 = @b AND 
    IpPart3 = @c AND 
    IpPart4 = @d; 

Ensuite, si l'adresse est introuvable, ajoutez

INSERT INTO EndPoints (IpPart1,IpPart2,IpPart3,IpPart4) 
    Values(@a,@b,@c,@d); 

Utilisation des transactions MySql Comment puis-je faire en sorte que seulement une ligne est ajoutée pour chaque adresse IP?

Merci!

Répondre

0

Bien vous pourrait COMMENCER une transaction, faites les deux requêtes que vous avez cité, puis COMMIT. Mais ne serait-il pas plus facile de simplement mettre une clé UNIQUE (IpPart1, IpPart2, IpPart3, IpPart4)?

(Il y a vraiment quelque chose à gagner en séparant les octets de cette façon Il semble peu probable que vous vouliez par exemple rechercher et indexer IpPart3 seul Les adresses IPv4 sont souvent stockées sous la forme d'une chaîne ou simple entier converti par inet_aton.Les adresses IPv6 sont un peu plus de travail, en utilisant une chaîne canonicalisée ou un char binaire (16).)

+0

merci bobince, ouais je sais que c'est étrange, mais je veux être en mesure de mapper des classes ip etc. voulez-vous aller à propos de la transaction? Je pense que je devrais faire un choix non verrouillé. Si ce n'est pas le cas, verrouillez la table avec IsolationLevel.Serializable (qui verrouille la table) puis effectuez une nouvelle sélection! - pour voir si elle vient d'être insérée, alors si elle n'est pas encore là, effectuez l'insertion .. commit ... suis-je sur la bonne voie? – divinci

+0

Étant donné que la requête est basée sur l'existence de la ligne que vous ne pouvez pas sortir avec un simple 'SELECT FOR update', mais il existe d'autres moyens qu'un verrou de table complet (qui est en général à éviter). Avec une contrainte 'UNIQUE' sur l'index IpParts composé, il serait aussi simple que de faire l'INSERT seul, puis d'attraper et d'ignorer l'exception si elle était déjà là. Ou, en utilisant la syntaxe spécifique à MySQL, 'INSERT IGNORE'. – bobince

Questions connexes