【发布时间】:2012-03-19 17:21:54
【问题描述】:
我有一个 PHP cron 作业在运行 29 分钟后失败。日志中的错误(/var/log/php_errors.log)是:
[01-Mar-2012 00:32:57 UTC] PHP Fatal error: Maximum execution time of 60 seconds exceeded in /path/file.php on line 2079
触发 cron 的 crontab 条目是:
00 00 * * * /usr/bin/php /path/file.php
根据我的研究,我认为这与 max_execution_time 配置设置无关,因为:
- 我知道它运行了 29:18 分钟(即像错误消息一样超过 60 秒)。
- 来自the PHP docs - 从命令行运行 PHP 时,默认设置为 0。
问:为什么脚本会提前终止?
注意事项:
脚本非常繁重,确实运行了数千个数据库查询,但我运行的是top,CPU 负载并不高。
错误日志中的行是mysql_query 调用:
$sql = "SELECT SUM(amount) FROM mytab WHERE mem = '$id' AND validto > '$now'";
$res = mysql_query($sql);
> php -v
PHP 5.3.10 (cli) (built: Feb 2 2012 17:34:38)
Copyright (c) 1997-2012 The PHP Group
Zend Engine v2.3.0, Copyright (c) 1998-2012 Zend Technologies
with Suhosin v0.9.33, Copyright (c) 2007-2012, by SektionEins GmbH
> cat /etc/redhat-release
Red Hat Enterprise Linux Server release 5.7 (Tikanga)
更新 - 我发现了为什么脚本可以实时运行 29 分钟,但 PHP 可以退出引用执行时间要短得多。
在确定脚本运行的最长时间时,不包括在脚本执行之外发生的活动所花费的任何时间,例如使用 system() 的系统调用、流操作、数据库查询等。
p>
(来自the set_time_limit() docs,但也提到了the max-execution-time docs)。这对我来说很重要,因为大部分脚本都是长时间运行的数据库查询和支付 API 调用,它们不会计时执行时间。
【问题讨论】:
-
cron 作业与您的错误无关,这是一个纯 PHP 问题。检查内存泄漏,在执行循环后尝试取消设置一些错误数组。在查询之间释放其他大变量。
-
您还会在文档中注意到它说:最大执行时间不受系统调用、流操作等影响。你能确定它实际上是由 cron 触发的 PHP CLI 吗?
-
我还会检查您是否有合适的索引来加快选择速度。你有关于 mem 和 validto 的索引吗?
-
谢谢。我通过手动从 CLI 触发它来验证它正在使用 PHP CLI,得到了同样的错误。我确实有索引,查询非常快(没有 mysql 慢日志条目),但是这些查询有很多(例如 200,000)。
标签: php cron fatal-error