当前位置: 首页 > 面试题库 >

显示长时间运行的PHP脚本的进度

张高义
2023-03-14
问题内容

我有一个PHP脚本,可能至少需要10秒钟才能运行。我想为用户显示进度。

在执行类中,我有一个$progress随进度(在1-100中)更新的属性和一个方法get_progress()(其目的应该很明显)。

问题是,如何更新<progress>前端的元素以供用户查看?

我认为AJAX是解决方案,但我只是无法解决。我无法到达同一对象实例。


问题答案:

如果您的任务是上载庞大的数据集或在服务器上处理它,则在将进度更新到服务器时,您应考虑采用某种作业架构,在该架构中启动作业并使用在服务器上运行的其他脚本执行该作业。服务器(例如缩放/处理图像等)。在这种情况下,您一次只能做一件事,因此形成了一个任务管道,其中有一个输入和一个最终的处理后的输出。

在流水线的每个步骤中,任务状态都会在数据库中更新,然后可以通过当前存在的任何服务器推送机制将其发送给用户。运行用于处理上载和更新的单个脚本会给您的服务器带来负担,并且还会限制您(如果浏览器关闭,发生其他错误怎么办)。将过程分为步骤时,您可以从成功完成的点开始继续执行失败的任务。

有很多方法可以做到这一点。但是整个流程看起来像这样

在此处输入图片说明

以下方法是我为个人项目所做的工作,此脚本非常适合将数千个高分辨率图像上传和处理到我的服务器,然后将其缩小到多个版本并上传到Amazon
s3,同时识别其中的对象。(我的原始代码在python中)

启动运输或任务

首先上传您的内容,然后通过简单的POST请求立即返回该交易的交易ID或uuid。如果您要在任务中执行多个文件或执行多项操作,则可能还需要在此步骤中处理该逻辑

第2步:

完成工作并返回进度。

一旦确定了事务处理的方式,就可以使用任何服务器端推送技术来发送更新数据包。我会选择WebSocket或服务器已发送事件,只要适用于回溯到不受支持的浏览器上的长时间轮询。一个简单的SSE方法如下所示。

function TrackProgress(upload_id){

    var progress = document.getElementById(upload_id);
    var source = new EventSource('/status/task/' + upload_id );

    source.onmessage = function (event) {
        var data = getData(event); // your custom method to get data, i am just using json here
        progress.setAttribute('value', data.filesDone );
        progress.setAttribute('max', data.filesTotal );
        progress.setAttribute('min', 0);
    };
}

request.post("/me/photos",{
    files: files
}).then(function(data){
     return data.upload_id;
}).then(TrackProgress);

在服务器端,您将需要创建一些东西来跟踪任务,带有job_id的简单Jobs体系结构和发送到db的进度就足够了。我将把作业调度和路由留给您,但是之后,概念代码(对于满足以上代码的最简单的SSE)如下。

<?php
header('Content-Type: text/event-stream');
header('Cache-Control: no-cache');
/* Other code to take care of how do you find how many files are left 
   this is really not required */
function sendStatusViaSSE($task_id){
    $status = getStatus($task_id);
    $json_payload = array('filesDone' => $status.files_done,
                          'filesTotal' => $status.files_total);
    echo 'data: ' . json_encode( $json_payload ) . '\n\n';
    ob_flush();
    flush();

    // End of the game
    if( $status.done ){
        die();
    }

}

while( True ){
     sendStatusViaSSE( $request.$task_id );
     sleep(4);
}

?>

可以在http://html5doctor.com/server-sent-events/找到有关SSE的好教程。

上面是一个概念上的解释,还有其他方法可以实现此目的,但这是解决我这个问题的解决方案。



 类似资料:
  • 本文向大家介绍Shell脚本获取进程的运行时间,包括了Shell脚本获取进程的运行时间的使用技巧和注意事项,需要的朋友参考一下 在我们的系统中,我曾写了一个脚本去定时更新一些repository,但偶尔会遇到问题,比如:git pull之时可能会卡在那里(可能由于某时刻的网络问题),它会阻碍后面的下一次更新。 所以我就在想,我今后启动这个脚本时,进行检查,如果上次运行的脚本还没结束,而且过了某个时

  • 本文向大家介绍codeigniter显示所有脚本执行时间的方法,包括了codeigniter显示所有脚本执行时间的方法的使用技巧和注意事项,需要的朋友参考一下 本文实例讲述了codeigniter显示所有脚本执行时间的方法。分享给大家供大家参考。具体分析如下: 如果你想显示所有脚本的执行时间,请将下面的代码加入到view里面 也可以使用下面的伪变量 希望本文所述对大家基于codeigniter的p

  • 问题内容: 我有一个JavaScript函数,其中包含一个for循环,该循环重复了很多次。 调用此函数后,IE浏览器将显示以下消息: 停止运行此脚本? 此页面上的脚本导致您的Web浏览器运行缓慢。如果继续运行,则您的计算机可能无响应。 我怎样才能解决这个问题? 无论如何,我可以从IE禁用此消息吗? 问题答案: 当InternetExplorer达到一段JavaScript的最大同步指令数时,将显示

  • 问题内容: 我写了Python脚本来处理大量的大文本文件,并且可能 要花费很多时间 。有时,需要停止正在运行的脚本并在以后恢复它。停止脚本的可能原因是程序崩溃,磁盘空间不足或需要执行此操作的其他原因。我想为脚本实现一种“停止/恢复”机制。 在 车站 :脚本退出和保存其当前状态。 在 简历 :剧本开始,但是从最新的保存状态持续 我将使用 pickle 和 信号 模块来实现它。 我将很高兴听到如何以p

  • 问题内容: 为了强制执行max_execution_time限制,PHP必须跟踪特定脚本使用的CPU时间。 有没有办法在脚本中访问此内容?我想在测试中包含一些日志记录,以了解实际PHP中的CPU消耗了多少(脚本坐着并等待数据库时,时间没有增加)。 我正在使用Linux机器。 问题答案: 在unixoid系统上(以及在Windows上的php 7+中),您可以使用getrusage,例如: 请注意,

  • 问题内容: 我的应用程序运行一些数据库查询,这可能需要很长时间。 在执行这些查询时,我的应用程序似乎死机了,看起来该应用程序已停止工作。 我需要使用progressbar来避免此问题,但是我不确定如何预测查询执行所花费的时间。 运行查询的代码如下 如何显示进度条以显示查询的进度? 问题答案: 您可以用来解决这类问题。 首先定义一个类的全局变量, 例如 然后在执行查询(如事件或其他任何内容)的过程中