laravel实战-批量插入万条记录时,避免超时
在laravel框架项目中使用PHPExcel从excel文件中读取了3万多条记录,要批量插入到数据库表中,报了下图的异常
明明提交的是$.post(...)
请求,路由也是用Route::post(...)
,为什么还是提示我提交的不是post请求呢?
经西门老师提点,这很可能是服务器超时引起的,然后在导入数据的action做了以下测试:
public function importVoteData(Request $req) {
set_time_limit(0);
// 尝试把时间分别设置为35,40,45,50
sleep(50);
return 'aaa';
}
经过几次测试,发现每次请求的执行时间都是40秒左右,见下图:
自此,基本可以确定是超时引起的。然后做了以下设置:
tips:我本地使用的是phpstudy集成环境,在这里可以快速打开各种配置文件:
PHP设置(php.ini)
Apache设置(httpd.conf)
改完重启Apache,问题依旧,还是超过40秒报错。然后再做以下设置:
站点配置(域名.conf)
改完再重启Apache,终于可以突破40秒的限制了,但是直接使用laravel的批量插入操作插入3万多条数据,请求在执行7分多钟后,还是报错了:
$voteDatas数组中有3万多条数据↑
最后,修改批量插入代码,把3万多条数据拆分成小批量(2000条)依次插入,大功告成
// 执行插入
$voteDatasPart = [];
$count = 0;
foreach($voteDatas as $vd) {
$voteDatasPart[] = $vd;
// 分批量插入,每次插入2000条
if(count($voteDatasPart) >= 2000) {
DB::table('vote_data_ori')->insert($voteDatasPart);
$count += count($voteDatasPart);
// 插入完成,清空
$voteDatasPart = [];
}
}
// 插入最后少于2000条的数据
if(count($voteDatasPart) > 0) {
DB::table('vote_data_ori')->insert($voteDatasPart);
$count += count($voteDatasPart);
}