定时任务自动加载报too many open files

1. 运行环境

1). 当前使用的 Laravel 版本?

Laravel Framework Lumen (8.3.4) (Laravel Components ^8.0)

2). 当前使用的 php/php-fpm 版本?

PHP 版本:7.3

3). 当前系统

Red Hat 4.8.5

4). 业务环境

生产环境,服务器上使用 ulimit -n 查看允许打开最大文件为 65536

2. 问题描述?

在使用 php artisan 执行定时任务过程中,出现了报错,看报错信息好像是自动加载文件时超出了系统允许打开文件数量。

[2023-03-15 00:14:13] local.ERROR: include(/www/vendor/symfony/string/UnicodeString.php): failed to open stream: Too many open files {"exception":"[object] (ErrorException(code: 0): include(/www/vendor/symfony/string/UnicodeString.php): failed to open stream: Too many open files at /www/vendor/composer/ClassLoader.php:571)
[stacktrace]
#0 /www/vendor/laravel/lumen-framework/src/Concerns/RegistersExceptionHandlers.php(47): Laravel\\Lumen\\Application->handleError(2, 'include(/wwwroo...', '/www/ve...', 571)
#1 /www/vendor/composer/ClassLoader.php(571): Laravel\\Lumen\\Application->Laravel\\Lumen\\Concerns\\{closure}(2, 'include(/wwwroo...', '/www/ve...', 571, Array)
#2 /www/vendor/composer/ClassLoader.php(571): include()
#3 /www/vendor/composer/ClassLoader.php(428): Composer\\Autoload\\includeFile('/www/ve...')
#4 [internal function]: Composer\\Autoload\\ClassLoader->loadClass('Symfony\\\\Compone...')
#5 /www/vendor/symfony/console/Helper/Helper.php(65): spl_autoload_call('Symfony\\\\Compone...')
#6 /www/vendor/symfony/console/Application.php(871): Symfony\\Component\\Console\\Helper\\Helper::width('mysqli_query() ...')
#7 /www/vendor/symfony/console/Application.php(840): Symfony\\Component\\Console\\Application->doRenderThrowable(Object(ErrorException), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
#8 /www/vendor/laravel/lumen-framework/src/Exceptions/Handler.php(202): Symfony\\Component\\Console\\Application->renderThrowable(Object(ErrorException), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
#9 /www/vendor/laravel/lumen-framework/src/Console/Kernel.php(250): Laravel\\Lumen\\Exceptions\\Handler->renderForConsole(Object(Symfony\\Component\\Console\\Output\\ConsoleOutput), Object(ErrorException))
#10 /www/vendor/laravel/lumen-framework/src/Console/Kernel.php(120): Laravel\\Lumen\\Console\\Kernel->renderException(Object(Symfony\\Component\\Console\\Output\\ConsoleOutput), Object(ErrorException))
#11 /www/artisan(35): Laravel\\Lumen\\Console\\Kernel->handle(Object(Symfony\\Component\\Console\\Input\\ArgvInput), Object(Symfony\\Component\\Console\\Output\\ConsoleOutput))
#12 {main}
"} 

请教下各位大佬这个问题该如何解决?

《L04 微信小程序从零到发布》
从小程序个人账户申请开始,带你一步步进行开发一个微信小程序,直到提交微信控制台上线发布。
《L03 构架 API 服务器》
你将学到如 RESTFul 设计风格、PostMan 的使用、OAuth 流程,JWT 概念及使用 和 API 开发相关的进阶知识。
讨论数量: 5
Mutoulee

ulimit -n 你查看的是root用户的吧 ?

如果是php-fpm,你在配置文件里rlimit_files = 65535试试能不能解决。

1年前 评论
sunhaozi (楼主) 1年前
Mutoulee (作者) 1年前

是否是打开的文件太多了忘了关闭。 常驻内存应用一直占着句柄。

1年前 评论

增加系统打开文件数量限制:可以通过修改系统配置文件来增加打开文件数量限制。例如,在 Ubuntu 系统上,可以修改 /etc/security/limits.conf 文件,添加以下内容:

  • soft nofile 65535
  • hard nofile 65535 然后重启系统或者重新登录,使配置生效。

减少 Laravel 定时任务的并发数:如果你的系统打开文件数量限制已经比较高了,那么可能是由于 Laravel 定时任务并发数过高导致的。你可以通过修改 Laravel 定时任务的并发数来解决这个问题。例如,在 app/Console/Kernel.php 文件中,可以将 $schedule->command('your-command')->withoutOverlapping(); 修改为 $schedule->command('your-command')->withoutOverlapping(1);,限制并发数为 1。

使用内存队列:如果你的系统打开文件数量限制已经比较高了,而且你也不想减少 Laravel 定时任务的并发数,那么可以考虑使用内存队列来代替文件队列。Laravel 支持多种队列驱动,例如 Redis、Beanstalkd 等,这些队列驱动可以将队列数据存储在内存中,避免频繁读写文件导致打开文件数量过多的问题。

1年前 评论

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!