Лучший способ хранить IP в базе данных? - PullRequest
48 голосов
/ 13 февраля 2011

Каков наилучший тип и длина поля для хранения IP-адресов в базе данных MySQL?

А как насчет IPv6?

Ответы [ 6 ]

58 голосов
/ 13 февраля 2011

Сохраните ip как INT(11) UNSIGNED, затем используйте функции INET_ATON и INET_NTOA для сохранения / получения адреса ip.

Пример кода:

INSERT table(ip) VALUES (INET_ATON('192.168.0.1')); /*ip = 3232235521*/
SELECT INET_NTOA(ip) As IPAddress FROM table; /*IPAddress = 192.168.0.1*/
17 голосов
/ 13 февраля 2011

Это зависит от того, что вы хотите с ним сделать, но, вероятно, самый простой способ - представить его в виде строки.И этот вопрос охватывает, сколько символов потребуется для его обработки.(Сейчас 45).

6 голосов
/ 20 ноября 2013

Если вы хотите поддерживать как IPv6, так и IPv4, сохраните его как BINARY(16) и преобразуйте IP-адрес перед вставкой в ​​базу данных. Например, в PHP (язык обычно используется с MySQL) вы можете сделать это с помощью функции inet_pton().

5 голосов
/ 04 августа 2011

IPv6-адреса 128-битные (16 байт), поэтому вам нужно достаточно большое поле для его хранения.Также вам может понадобиться поле, чтобы указать, является ли IP-адрес IPv4 или IPv6 (:: 192.168.4.10 в IPv6 численно совпадает с 192.168.4.10 в IPv4, но в зависимости от вашего приложения вам может потребоваться различать два).

Если вам нужно сохранить подсети, вы можете сохранить первый адрес, маску CIDR и вычисленный верхний адрес (широковещательный адрес) подсети.Это поможет при поиске, поэтому вы можете выполнять такие запросы:

SELECT * FROM networks WHERE lowerBound<=MYIP AND upperBound>=MYIP

. Если вы используете подсети, вам также следует рассчитать эту нижнюю границу самостоятельно, а не просто полагаться на то, что пользователь делает это правильно (псевдокод):

lowerBound = AND(networkAddress, subnetMask)
upperBound = OR(lowerBound, complement(subnetMask))

Это относится как к IPv4, так и к IPv6.

3 голосов
/ 12 апреля 2011

Если вы планируете поиск в базе данных по IP-адресу, тогда INT будет намного быстрее запрашивать.Если вы просто храните для отображения (например, в выходных данных журнала), тогда строка будет лучше, поскольку вам не нужно преобразовывать ее туда и обратно.

0 голосов
/ 13 февраля 2011

Я полностью согласен со Scrum Meister, что лучший способ - использовать INT(11) UNSIGNED с хранением / извлечением в функциях INET, но иногда, если вы не собираетесь запрашивать по подсети, вы можете выбратьдля VARCHAR(45)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...