我有一个包含超过30,000条记录的文件,另一条有41,000条记录。有没有最好的案例研究使用laravel 4的db:seed
命令播种?一种使插入更快速的方法。
感谢您的帮助。
答案 0 :(得分:5)
DB::disableQueryLog();
在禁用它之前,Laravel浪费了我所有的PHP内存限制,无论我给它多少。
我使用fgets()
从.txt文件中读取数据,以编程方式构建数组并执行:
DB::table($table)->insert($row);
一个接一个,可能特别慢。
我的数据库服务器是PostgreSQL,插入大约需要1.5小时才能完成,可能是因为我使用的是使用低内存的虚拟机。我会在一台更好的机器上做一个基准测试。
答案 1 :(得分:0)
我从不同的数据库迁移,我不得不使用带有批量插入语句的原始sql(从外部文件加载)(我通过navicat导出结构,可以选择每250KiB分解插入语句)。例如:
$sqlStatements = array(
"INSERT INTO `users` (`name`, `email`)
VALUES
('John Doe','john.doe@gmail.com'),.....
('Jane Doe','jane.doe@gmail.com')",
"INSERT INTO `users` (`name`, `email`)
VALUES
('John Doe2','john.doe2@gmail.com'),.....
('Jane Doe2','jane.doe2@gmail.com')"
);
然后我循环使用insert语句并使用
执行DB::statement($sql).
我无法一次插入一行。我确定有更好的选择,但这至少有效,同时让我把它留在Laravel的迁移/播种中。
答案 2 :(得分:0)
我今天遇到了同样的问题。禁用查询日志还不够。看起来事件也会被解雇。
DB :: disableQueryLog();
// DO INSERTS
//重置事件以释放内存。
DB :: setEventDispatcher(new Illuminate \ Events \ Dispatcher());
答案 3 :(得分:0)
我遇到了同样的问题,经过2天的头痛之后,我终于可以编写脚本在不到30s的时间内播种42K条目了!
您问如何?
此方法假定您有一个包含某些条目的数据库(在我的情况下为42k条目),并且您希望将其导入其他数据库。将数据库导出为带有标头名称的CSV文件,并将其放入项目的公共文件夹中,然后您可以解析该文件,并通过播种器将所有条目一一插入到新数据库中。
因此您的播种机将如下所示:
<?php
use Illuminate\Database\Seeder;
class {TableName}TableSeeder extends Seeder
{
/**
* Run the database seeds.
*
* @return void
*/
public function run()
{
$row = 1;
if (($handle = fopen(base_path("public/name_of_your_csv_import.csv"), "r")) !== false) {
while (($data = fgetcsv($handle, 0, ",")) !== false) {
if ($row === 1) {
$row++;
continue;
}
$row++;
$dbData = [
'col1' => '"'.$data[0].'"',
'col2' => '"'.$data[1].'"',
'col3' => '"'.$data[2].'"',
so on...how many columns you have
];
$colNames = array_keys($dbData);
$createQuery = 'INSERT INTO locations ('.implode(',', $colNames).') VALUES ('.implode(',', $dbData).')';
DB::statement($createQuery, $data);
$this->command->info($row);
}
fclose($handle);
}
}
}
简单易用:)
如果您可以修改PHP的设置并为特定的脚本分配较大的大小,则此方法也将起作用。
基本上,您需要专注于三个主要步骤:
insert()
一次创建1K的块。因此,如果我将上述所有步骤组合到播种机中,则您的播种机将如下所示:
<?php
use Illuminate\Database\Seeder;
class {TableName}TableSeeder extends Seeder
{
/**
* Run the database seeds.
*
* @return void
*/
public function run()
{
ini_set('memory_limit', '512M');//allocate memory
DB::disableQueryLog();//disable log
//create chunks
$data = [
[
[
'col1'=>1,
'col2'=>1,
'col3'=>1,
'col4'=>1,
'col5'=>1
],
[
'col1'=>1,
'col2'=>1,
'col3'=>1,
'col4'=>1,
'col5'=>1
],
so on..until 1000 entries
],
[
[
'col1'=>1,
'col2'=>1,
'col3'=>1,
'col4'=>1,
'col5'=>1
],
[
'col1'=>1,
'col2'=>1,
'col3'=>1,
'col4'=>1,
'col5'=>1
],
so on..until 1000 entries
],
so on...until how many entries you have, i had 42000
]
//iterate and insert
foreach ($data as $key => $d) {
DB::table('locations')->insert($d);
$this->command->info($key);//gives you an idea where your iterator is in command line, best feeling in the world to see it rising if you ask me :D
}
}
}
和VOILA,你很好:)
我希望对您有帮助