Mysql载入大量数据(load data infile)的优化过程

公司开发的某个产品需要从文本格式的文件导入大量数据, 其中某一个表特别大, 数据文件有接近30G, 大概有6千万行数据. MySQL提供了很强大的工具, load data infile, 具体格式不去介绍了, 它的主要优势在于批量插入数据.

服务器是20核 cpu.

MySQL 部分配置大概如下:

innodb_buffer_pool_size = 20000M

innodb_file_per_table = 1
innodb_flush_method = O_DIRECT

innodb_flush_log_at_trx_commit = 0

直接开始load数据,  结果悲剧开始了, 命令执行了1个小时,没结果,  2个小时, 还是没结果.

开另外一个终端连到数据库, 查询当前表的行数, 结果是0,  说明 load data infile是一个transaction, 在当前的隔离级别下, 没load完是看不到数据的.

用TOP看了一下资源使用情况, MySQL 只使用了接近100%的CPU(最高2000%).

漫长的等待,  只好做点别的事情...

快下班了, 终于load结束, 看时间统计,执行了5个半小时尴尬!

晚上睡觉还一直在思考这个问题, 号称最快的load data infile为什么这样慢?是innodb_buffer_pool_size 太小? 很有可能, 因为文件已近有30G, 比buffer小了10G! 一阵狂喜, 找到答案啦!大笑

一早赶到公司,  把buffer改成40G, 重新执行load data infile, 漫长的等待...

结果很失望,  只加快了十几分钟, 没什么根本的改善! 想了很久,  发现有个地方有点问题,  MySQL号称多线程,  为什么加载数据的时候只使用了5%的总CPU时间呢?  其他19个CPU在看戏啊发火!

想到这个, 立刻有了思路, 多线程解决之! 先将这个大文件切割成,小文件,然后多线程执行load data infile!

linux提供了split命令, 非常方便, 将文件切成150万行的40个小文件.

改代码, 启动40个线程, 分别执行load data infile!

很快遇到了错误:  Lock wait timeout exceeded!

Google之,  发现innodb_lock_wait_timeout使用了默认值, 50秒, 改成1000秒.

重新执行,  没有看到lock的错误.  察看CPU使用率,接近900%, 说明MySQL的多线程起作用了!等待了接近50分钟,  加载完成, 登陆到数据库,

查行数,  和待导入文件的行数一致!大笑

补充其他几个需要配置的参数:

innodb_doublewrite = 0

innodb_log_file_size = 2048M

innodb_log_buffer_size=2048M

总结:

1, 多观察程序执行时候的资源使用情况.

2, 数据库是很笨的, 不要想当然的以为它很聪明, 这也是

为什么数据库要简单,简洁的原因!




  • 2
    点赞
  • 30
    收藏
    觉得还不错? 一键收藏
  • 3
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值