我有一个Web应用程序,它充当运行非常长的任务的非现场服务器的接口。用户输入信息并点击提交,然后chrome等待响应,并在接收到新页面时加载它。但是,根据网络和用户的输入,任务可能会花费相当长的时间,并且在返回数据之前(尽管任务仍在运行),chrome有时会加载“无数据接收页”。
有没有办法在我的任务正在思考时放置一个临时页面,或者只是强制chrome继续等待?提前致谢
尽管你可以更改服务器上的超时时间或其他技巧来尝试保持页面“活动”,但请记住,连接的其他部分可能无法控制,可能会使请求超时(例如超时)浏览器的值,或浏览器和服务器之间的任何代理等)。此外,如果任务需要更长的时间才能完成(变得更高级,或者由于更多的人使用它而变得更慢),则可能需要不断提高超时值。
最后,这种问题通常可以通过更改体系结构来解决。
对长时间运行的任务使用单独的过程 该视图不是在处理视图中提交请求并运行任务,而是在单独的进程中开始运行任务,然后立即返回响应。此响应可以使用户进入“请稍候,我们正在处理”页面。该页面可以使用多种推送技术之一来确定任务的完成时间(长轮询,Web套接字,服务器发送的事件,每N秒发出AJAX请求或最简单的方法:重新加载页面每5秒钟)。
让你的Web请求“启动”单独的流程 无论如何,就像我说的那样,处理请求的视图并不会执行冗长的操作:它只是启动了一个后台进程来完成该任务。你可以自行创建此后台进程(请查看此Flask片段以获取可能的想法),或使用诸如Celery或(RQ)之类的库。
任务完成后,你需要某种方式通知用户。这将取决于你在上面选择了哪种通知方法。对于一个简单的“每N秒发送一个ajax请求”,你需要创建一个视图来处理AJAX请求,以检查任务是否完成。一种典型的方法是执行长时间运行的任务,作为最后一步,对数据库进行一些更新。然后,检查状态的请求可以检查数据库的这一部分以进行更新。
的优点和缺点 使用此方法(而不是尝试将长时间运行的任务放入请求中)有一些好处:
1.)处理长时间运行的Web请求是一件棘手的事情,因为存在多个超时的事实(浏览器和服务器除外)。使用这种方法,你所有的Web请求都非常短,并且超时的可能性也大大降低。
2.)Flask(以及其他类似的框架)旨在仅支持可以响应Web查询的一定数量的线程。假设它有8个线程:如果其中四个正在处理长请求,则仅剩下四个请求实际处理更典型的请求(例如用户获取其个人资料页面)。你的Web服务器的一半可能被捆绑在执行不提供Web内容的操作!更糟糕的是,你可能让所有八个线程都运行很长时间,这意味着你的站点直到其中一个完成后才完全无法响应Web请求。
主要缺点:在启动和运行任务队列时,还有更多的设置工作,这会使你的整个系统稍微复杂一些。但是,对于长时间运行在Web上的任务,我强烈建议使用此策略。