mysql - 将 MaxMind 的 GeoLite2 导入 MySQL

标签 mysql import geoip geolite2

MaxMind 的 GeoLite2 是一个很棒的数据库,如果您想将 IP 地址映射到国家/地区,它会非常有用。

为了高效地执行此操作,我想使用如下方案将其导入 MySQL 数据库:

Model

我记得很久以前为 CSV 数据库编写了一个导入脚本,但是今天您可以下载的 CSV 格式很难理解,至少对我来说是这样:

network,geoname_id,registered_country_geoname_id,represented_country_geoname_id,is_anonymous_proxy,is_satellite_provider 1.0.0.0/24,2077456,2077456,,0,0 1.0.1.0/24,1814991,1814991,,0,0 1.0.2.0/23,1814991,1814991,,0,0 1.0.4.0/22,2077456,2077456,,0,0 1.0.8.0/21,1814991,1814991,,0,0 1.0.16.0/20,1861060,1861060,,0,0 1.0.32.0/19,1814991,1814991,,0,0 1.0.64.0/18,1861060,1861060,,0,0 1.0.128.0/17,1605651,1605651,,0,0

我真的被困在了这里的基础知识上。 将数据库从 CSV 表示形式导入 MySQL 的最有效和最简单的方法是什么?

最佳答案

network,geoname_id,registered_country_geoname_id,represented_country_geoname_id,is_anonymous_proxy,is_satellite_provider
1.0.0.0/24,2077456,2077456,,0,0
1.0.1.0/24,1814991,1814991,,0,0
1.0.2.0/23,1814991,1814991,,0,0
1.0.4.0/22,2077456,2077456,,0,0

create table thing1
(   network varchar(20) not null,
    geoname_id varchar(20) not null,
    registered_country_geoname_id varchar(20) not null,
    represented_country_geoname_id varchar(20) not null,
    is_anonymous_proxy varchar(20) not null,
    is_satellite_provider varchar(20) not null
);

LOAD DATA INFILE 'c:\\dev\\ipaddr.txt' 
INTO TABLE thing1
FIELDS TERMINATED BY ',' 
LINES TERMINATED BY '\n'
IGNORE 1 LINES
(@v1,@v2,@v3,@v4,@v5,@v6)
set network=ifnull(@v1,''),
geoname_id=ifnull(@v2,''),
registered_country_geoname_id=ifnull(@v3,''),
represented_country_geoname_id=ifnull(@v4,''),
is_anonymous_proxy=ifnull(@v5,''),
is_satellite_provider=ifnull(@v6,'');

以上对我来说很好。

下方编辑开始

对于以下内容,根据 stijn-de-witt 在评论中提出的观点,尝试改进此答案。

但是请注意,评论中引用的博客在进入整数的更新语句中存在错误。因此,在我解决这个问题之前,我暂时找到了一个 varchar 修改,如下所示。

Edit1(更多内容,请参阅答案下方的评论):

Alter the table to get a "from ip to ip range"

alter table thing1 add column from_ip varchar(20), add column to_ip varchar(20);
-- note that those two are nullable at the moment. You can always change that later

为刚刚添加的 varchar 更新表

update thing1
set from_ip=  INET_NTOA(INET_ATON( SUBSTRING_INDEX(network, '/', 1)) 
   & 0xffffffff ^ ((0x1 << ( 32 - SUBSTRING_INDEX(network, '/', -1))  ) -1 )),
to_ip=   INET_NTOA(INET_ATON( SUBSTRING_INDEX(network, '/', 1)) 
   | ((0x100000000 >> SUBSTRING_INDEX(network, '/', -1) ) -1 ))
select * from thing1;

(对于上述更新声明,感谢本 answer 中的 Bernd Buffen)

上述更新语句的结果:

mysql> select network,from_ip,to_ip from thing1;
+------------+---------+-----------+
| network    | from_ip | to_ip     |
+------------+---------+-----------+
| 1.0.1.0/24 | 1.0.1.0 | 1.0.1.255 |
| 1.0.2.0/23 | 1.0.2.0 | 1.0.3.255 |
| 1.0.4.0/22 | 1.0.4.0 | 1.0.7.255 |
+------------+---------+-----------+

从这里,查看 INET_ATON(expr) 的 MySQL 手册页 Miscellaneous Functions

Edit2(再次感谢 stijn-de-witt):

alter table thing1 add column uint_from_ip int unsigned, add column uint_to_ip int unsigned;

UPDATE thing1 SET uint_from_ip = inet_aton(SUBSTRING(network, 1, LOCATE('/', network) - 1)), 
uint_to_ip = (inet_aton(SUBSTRING(network, 1, LOCATE('/', network) - 1)) + (pow(2, (32-CONVERT(SUBSTRING(network, LOCATE('/', network) + 1), UNSIGNED INT)))-1));

结果:

select network,from_ip,to_ip,uint_from_ip,uint_to_ip from thing1;
+------------+---------+-----------+--------------+------------+
| network    | from_ip | to_ip     | uint_from_ip | uint_to_ip |
+------------+---------+-----------+--------------+------------+
| 1.0.1.0/24 | 1.0.1.0 | 1.0.1.255 |     16777472 |   16777727 |
| 1.0.2.0/23 | 1.0.2.0 | 1.0.3.255 |     16777728 |   16778239 |
| 1.0.4.0/22 | 1.0.4.0 | 1.0.7.255 |     16778240 |   16779263 |
+------------+---------+-----------+--------------+------------+

(在提到一些修复后,以上归功于此 S0BEIT blog)

关于mysql - 将 MaxMind 的 GeoLite2 导入 MySQL,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32019915/

相关文章:

python - MySQL 列名中的通配符

ios - #在xcode 5中导入多个非框架类头文件?

java - 打包和导出带有引用库错误的 Jar 文件

python - 如何将 python 脚本分成几部分并循环导入这些部分?

mysql - 在 JOIN 查询中生成匿名 ID

php - oscommerce $php_self 返回不正确的值

mysql - 在sql中选择具有一组行的最大值的行

ruby-on-rails - Rails 从 ZIP Geoip 获取状态

nginx - geoip_country_name 在 nginx 中返回 "-"

linux - 在没有 sudo 访问权限的情况下安装 perl 模块