如何避免“允许...字节耗尽的记忆大小”当用照明插入多个大查询时?

发布于 2025-02-10 10:13:37 字数 993 浏览 1 评论 0原文

如何使用Laravel的myModel :: insert()db :: insert()用于大型SQL查询的方法而不遇到内存问题?

我正在尝试执行约500个插入1000个项目的插入。

每次将带有项目的数组转换为SQL时,请使用查询构建器很方便。但是,使用myModel :: insert()db :: insert()反复运行。

唯一的低内存解决方法是将数组转换为SQL并使用db :: statement()或 db :: getpdo() - > exec()。

在伪代码中:

  1. 这可以按预期工作:
for (many times) {
  DB::getPdo()->exec('a large insert into ... query');
}

内存使用量在每次插入后保持在11 MB左右。

  1. 这允许的记忆大小...字节用尽的异常,
DB::disableQueryLog();
for (many times) {
  MyModel::insert($large_array);
}

对于前几个插入记忆使用率也为11 MB,但随后每次迭代循环的每次迭代迅速生长,最终达到1 GB。

在此处遵循建议 https://stackoverflow.com/a/a/187777981656 :: DisableQueryLog()),但无济于事。

上下文:
Laravel 8.83.9
PHP 8.1
MacOS 12.3.1
我正在使用PHP Artisan服务运行代码

How can I use Laravel's MyModel::insert(), DB::insert() methods for large SQL queries without running into memory issues?

I'm attempting to execute around 500 inserts of 1000 items.

It would be convenient to have the query builder each time convert an array with the items to SQL. However using MyModel::insert() or DB::insert() repeatedly runs out of memory.

The only low-memory workaround was to convert the array to SQL and use DB::statement() or DB::getPdo()->exec().

In pseudo code:

  1. This works as expected:
for (many times) {
  DB::getPdo()->exec('a large insert into ... query');
}

Memory usage stays at around 11 MB after each insert.

  1. This throws Allowed memory size of ... bytes exhausted exception
DB::disableQueryLog();
for (many times) {
  MyModel::insert($large_array);
}

For the first few inserts memory usage is also at 11 MB but then it quickly grows with each iteration of the loop, eventually reaching 1 GB.

Following the advice here https://stackoverflow.com/a/18776710/17981656 I disabled query logging (DB::disableQueryLog()) but it didn't help.

Context:
Laravel 8.83.9
PHP 8.1
macOS 12.3.1
I'm running the code with php artisan serve

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

友欢 2025-02-17 10:13:37

其他开发人员发现查询日志 并在db连接上禁用事件调度程序有用。 IE:

DB::disableQueryLog();

$dispatcher = DB::connection()->getEventDispatcher();
DB::connection()->unsetEventDispatcher();

for (many times) {
    MyModel::insert($large_array);
}

DB::enableQueryLog();
DB::connection()->setEventDispatcher($dispatcher);

资源: QUERY BUILFERRER“> QUERY BUILLER”

Other developers have found disabling Query logs and unsetting/disabling the event dispatcher on the DB connection helpful. I.e:

DB::disableQueryLog();

$dispatcher = DB::connection()->getEventDispatcher();
DB::connection()->unsetEventDispatcher();

for (many times) {
    MyModel::insert($large_array);
}

DB::enableQueryLog();
DB::connection()->setEventDispatcher($dispatcher);

Resource: Query builder memory leak on large insert #27539

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文