我有一个PHP函数,可以调用API并提取数据。 这大约需要6个小时。 我想要的不是让Cron-Job计时,而是让函数在完成后立即运行。
例如...
<?php
function run_for_six_hours() {
// runs for six hours
copy_of_the_above_function();
}
function copy_of_the_above_function() {
// do the same thing again
run_for_six_hours()
}
此方法是否可以奏效,还是有更好的方法?
我已经做过一些研究,并且我知道无限期地运行PHP不是最佳实践,但是对于这种情况,我们目前没有更好的选择。
答案 0 :(得分:7)
您所描述的方法是无限递归-该函数会反复调用自身(从技术上讲,您拥有的是“相互递归”,因为您拥有额外的包装器copy_of_the_above_function
,没必要)。这样做的问题是,在大多数语言(包括PHP)中,每个调用都将其状态存储在堆栈上,直到内部所有内容返回为止,因此,像run_for_six_hours -> copy_of_the_above_function -> run_for_six_hours -> copy_of_the_above_function -> run_for_six_hours -> copy_of_the_above_function -> ...
这样的堆栈会越来越长。最终,PHP将达到极限(内存或最大堆栈深度)并崩溃。
一种简单得多的方法是将函数置于无限循环中:
while ( true ) {
run_for_six_hours();
}
PHP将等待函数完成,然后一次又一次地运行它。只要实现中没有内存泄漏,它将无限期地运行。您需要将PHP's max_execution_time
setting设置为0
(永久运行)以将其禁用。
但是,如果脚本由于任何原因崩溃,则只有在您登录并再次运行它后,脚本才会重新启动。更好的方法是让脚本运行一次代码,然后使用外部程序重复运行该脚本。 Supervisor正是为此目的而构建的-像cron
那样思考,但您不是说“在指定时间运行”,而是说“确保它始终在运行”。
答案 1 :(得分:2)
编辑:使用IMSoP描述的上述解决方案
如果您知道后果以及为使脚本无限期运行需要进行哪些设置,则可以再次调用同一函数:
function run_for_six_hours() {
// runs for six hours
run_for_six_hours();
}