34 votes

Comment stocker une adresse compatible IPv6 dans une base de données relationnelle

Comment dois-je faire?

Maintenant, IPv6 ne sera pas utilisé, mais j'ai besoin de conception de l'application pour le rendre prêt pour IPv6. Il est nécessaire de stocker les adresses IP et les blocs CIDR (également BGP NLRI, mais ceci est une autre histoire) dans une base de données MySQL. J'ai toujours utilisé un INT pour IPv4 + un TINYINT pour masklen, mais IPv6 est de 128 bits.

Quelle est l'approche qui sera le mieux pour qui? 2xBIGINT? CHAR(16) pour le stockage binaire? CHAR(39) pour le texte de stockage? 8xSMALLINT dans une table?

Que recommanderiez-vous?

21voto

Alnitak Points 143355

Je ne suis pas sûr de ce qui est le droit de réponse de MySQL étant donné qu'il ne prend pas encore en charge les adresses IPv6 des formats nativement (bien que bien que "WL#798: MySQL support de l'IPv6", suggère qu'il allait être dans MySQL v6.0, le courant de documentation n'est pas de retour que vers le haut).

Cependant, ceux que vous avez proposé, je vous conseille d'aller pour les 2 * BIGINT, mais assurez-vous qu'ils sont pas signés. Il y a une sorte de naturel split à l' /64 adresse frontière en IPv6 (depuis un /64 est le plus petit netblock taille) qui harmoniserait bien avec qui.

6voto

ʞɔıu Points 15907

Si vous vous penchez vers char(16), certainement utiliser les binaires(16) à la place. binaire(n) n'est pas un concept de classement ou de jeu de caractères (ou plutôt, c'est un char(n) avec un jeu de caractères/classement de "binary"). La valeur par défaut pour l'omble de mysql est latin1_swedish_ci, ce qui signifie qu'il va tenter de la casse, de tri et de comparaisons pour les valeurs d'octets qui sont valables pour les points de code en latin1, qui va vous causer toutes sortes de problèmes inattendus.

Une autre option est d'utiliser la virgule (39, 0) unsigned zerofill ne, pas tout à fait aussi efficace que deux bigints (décimal va utiliser 4 octets par neuf chiffres dans les versions actuelles de mysql), mais vous permettra de garder tout ça dans une colonne et d'impression de très bien.

6voto

Steve-o Points 9043

Notez que la longueur maximale d'une adresse IPv6, identificateur de portée comprise, est de 46 octets, comme défini par INET6_ADDRSTRLEN dans les en-têtes C standard. Pour utiliser Internet, vous devriez pouvoir ignorer l' identifiant de la zone (% 10, # eth0, etc.), mais sachez que getaddrinfo renvoie un résultat plus long que prévu.

4voto

James Anderson Points 18253

Je choisirais le format imprimé "standard" complet de 39 caractères: -

"2001: 0db8: 85a3: 0000: 0000: 8a2e: 0370: 7334"

40 avec un terminateur nul.

Il s’agit du format utilisé par les outils de ligne de commande * nix et le format d’une adresse IPV6 est indiqué normalement dans (?).

1voto

Jonathan Leffler Points 299946

Est l'adresse IP va utilisé par un programme pour lequel binaire du sens? Ou voulez-vous être mieux de stockage d'une représentation de texte? Aussi, avec l'IPv6, vous êtes moins susceptibles d'utiliser l'adresse en général, et plus susceptibles d'utiliser des noms d'hôte. Si c'est pertinent dépend de l'application, en partie. CHAR(16) serait un mauvais choix; char est les données de type caractère et n'aime pas les grands cours d'eau de zéro octets qui sont répandues dans les adresses IPv6. 2 x BIGINT serait mal à l'aise - deux champs qui sont vraiment une (plus est la valeur stockée big-endian ou little-endian?). J'avais utilisé une taille fixe de type BINAIRE, ou si ce n'est pas disponible, un type blob.

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