MySQL 将 CIDR 转换为 IP 范围的查询
MySQL query to convert CIDR into IP range
我有一个 table,其中包含一列作为 CIDR 值,如 1.0.85.128/25
,我还有 2 个其他列(start_ip_range 和 end_ip_range),我想填充那 2 列来自 CIDR 列
Java 代码可能如下所示:
String[] parts = cidr.split("/");
String ip = parts[0];
int prefix;
if (parts.length < 2) {
prefix = 0;
} else {
prefix = Integer.parseInt(parts[1]);
}
String[] ipParts = ip.split("\.");
int address = ((new Integer(ipParts[0]) << 24) & 0xFF000000)
| ((new Integer(ipParts[1]) << 16) & 0xFF0000)
| ((new Integer(ipParts[2]) << 8) & 0xFF00)
| (new Integer(ipParts[3]) & 0xFF);
int mask = (-1) << (32 - prefix);
int start = address & mask;
int end = start + (~mask);
如何将其转化为 MySql 查询。
你可以这样转换
查询
SELECT
INET_NTOA(INET_ATON( SUBSTRING_INDEX(val, '/', 1))
& 0xffffffff ^ ((0x1 << ( 32 - SUBSTRING_INDEX(val, '/', -1)) ) -1 )) from_ip,
INET_NTOA(INET_ATON( SUBSTRING_INDEX(val, '/', 1))
| ((0x100000000 >> SUBSTRING_INDEX(val, '/', -1) ) -1 )) to_ip
FROM cidr;
样本Table
CREATE TABLE `cidr` (
`id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`val` varchar(32) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
INSERT INTO `cidr` (`id`, `val`)
VALUES
(1, '192.168.2.12/24'),
(2, '192.168.2.12/25'),
(3, '1.0.85.128/25'),
(4, '192.168.2.12/32');
或者您可以在虚拟列中使用它。所以你直接得到正确的值。
虚拟字段
CREATE TABLE `cidr1` (
`id` INT(11) UNSIGNED NOT NULL AUTO_INCREMENT,
`val` VARCHAR(32) DEFAULT NULL,
`from_ip` VARCHAR(15) AS ( INET_NTOA(INET_ATON( SUBSTRING_INDEX(val, '/', 1)) & 0xffffffff ^ ((0x1 << ( 32 - SUBSTRING_INDEX(val, '/', -1)) ) -1 ))) PERSISTENT ,
`to_ip` VARCHAR(15) AS ( INET_NTOA(INET_ATON( SUBSTRING_INDEX(val, '/', 1)) | ((0x100000000 >> SUBSTRING_INDEX(val, '/', -1) ) -1 ))) PERSISTENT ,
PRIMARY KEY (`id`)
) ENGINE=INNODB DEFAULT CHARSET=utf8;
INSERT INTO `cidr1` (`id`, `val`)
VALUES
(1, '192.168.2.12/24'),
(2, '192.168.2.12/25'),
(3, '1.0.85.128/25'),
(4, '192.168.2.12/32');
MariaDB []> select * from cidr1;
+----+-----------------+--------------+---------------+
| id | val | from_ip | to_ip |
+----+-----------------+--------------+---------------+
| 1 | 192.168.2.12/24 | 192.168.2.0 | 192.168.2.255 |
| 2 | 192.168.2.12/25 | 192.168.2.0 | 192.168.2.127 |
| 3 | 1.0.85.128/25 | 1.0.85.128 | 1.0.85.255 |
| 4 | 192.168.2.12/32 | 192.168.2.12 | 192.168.2.12 |
+----+-----------------+--------------+---------------+
4 rows in set (0.00 sec)
MariaDB []>
我有一个 table,其中包含一列作为 CIDR 值,如 1.0.85.128/25
,我还有 2 个其他列(start_ip_range 和 end_ip_range),我想填充那 2 列来自 CIDR 列
Java 代码可能如下所示:
String[] parts = cidr.split("/");
String ip = parts[0];
int prefix;
if (parts.length < 2) {
prefix = 0;
} else {
prefix = Integer.parseInt(parts[1]);
}
String[] ipParts = ip.split("\.");
int address = ((new Integer(ipParts[0]) << 24) & 0xFF000000)
| ((new Integer(ipParts[1]) << 16) & 0xFF0000)
| ((new Integer(ipParts[2]) << 8) & 0xFF00)
| (new Integer(ipParts[3]) & 0xFF);
int mask = (-1) << (32 - prefix);
int start = address & mask;
int end = start + (~mask);
如何将其转化为 MySql 查询。
你可以这样转换
查询
SELECT
INET_NTOA(INET_ATON( SUBSTRING_INDEX(val, '/', 1))
& 0xffffffff ^ ((0x1 << ( 32 - SUBSTRING_INDEX(val, '/', -1)) ) -1 )) from_ip,
INET_NTOA(INET_ATON( SUBSTRING_INDEX(val, '/', 1))
| ((0x100000000 >> SUBSTRING_INDEX(val, '/', -1) ) -1 )) to_ip
FROM cidr;
样本Table
CREATE TABLE `cidr` (
`id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`val` varchar(32) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
INSERT INTO `cidr` (`id`, `val`)
VALUES
(1, '192.168.2.12/24'),
(2, '192.168.2.12/25'),
(3, '1.0.85.128/25'),
(4, '192.168.2.12/32');
或者您可以在虚拟列中使用它。所以你直接得到正确的值。
虚拟字段
CREATE TABLE `cidr1` (
`id` INT(11) UNSIGNED NOT NULL AUTO_INCREMENT,
`val` VARCHAR(32) DEFAULT NULL,
`from_ip` VARCHAR(15) AS ( INET_NTOA(INET_ATON( SUBSTRING_INDEX(val, '/', 1)) & 0xffffffff ^ ((0x1 << ( 32 - SUBSTRING_INDEX(val, '/', -1)) ) -1 ))) PERSISTENT ,
`to_ip` VARCHAR(15) AS ( INET_NTOA(INET_ATON( SUBSTRING_INDEX(val, '/', 1)) | ((0x100000000 >> SUBSTRING_INDEX(val, '/', -1) ) -1 ))) PERSISTENT ,
PRIMARY KEY (`id`)
) ENGINE=INNODB DEFAULT CHARSET=utf8;
INSERT INTO `cidr1` (`id`, `val`)
VALUES
(1, '192.168.2.12/24'),
(2, '192.168.2.12/25'),
(3, '1.0.85.128/25'),
(4, '192.168.2.12/32');
MariaDB []> select * from cidr1;
+----+-----------------+--------------+---------------+
| id | val | from_ip | to_ip |
+----+-----------------+--------------+---------------+
| 1 | 192.168.2.12/24 | 192.168.2.0 | 192.168.2.255 |
| 2 | 192.168.2.12/25 | 192.168.2.0 | 192.168.2.127 |
| 3 | 1.0.85.128/25 | 1.0.85.128 | 1.0.85.255 |
| 4 | 192.168.2.12/32 | 192.168.2.12 | 192.168.2.12 |
+----+-----------------+--------------+---------------+
4 rows in set (0.00 sec)
MariaDB []>