如何在Puma上清理已解散/僵尸进程或关闭与Sinatra长期运行的popen

时间:2016-02-24 19:26:20

标签: ruby sinatra popen puma

我在我的ruby sinatra应用程序中有以下内容可以即时传输大型tar文件,但是每个请求都会留下一个已经失效/僵尸的子进程。一旦浏览器弹出保存文件对话框,该过程就会失效。

我在Puma 2.12.2上运行它

我尝试了一个系统调用并在一个块中使用popen但它关闭了进程并在tar命令完成之前返回,因此客户端收到一个空文件。

我有什么想法可以自动清理已失效的子进程或保留io对象的句柄但仍然返回它以便它开始流式传输到客户端?

get '/:dir_name' do
    headers['Content-Type']="application/octet-stream"
    headers["Content-Disposition"]="attachment;filename=#{params[:dir_name]}.tar"
    IO.popen("tar -C /home/my/files -cf - #{params[:dir_name]}")
end

1 个答案:

答案 0 :(得分:1)

上面的代码似乎产生了两个子进程:一个用于正确关闭的tar命令;而另一个已经不复存在。

如果在下面的代码中分离了popen,则不会出现已解散的进程,并且tar命令仍然作为服务器的子级正确附加。

get '/:dir_name' do
    headers['Content-Type']="application/octet-stream"
    headers["Content-Disposition"]="attachment;filename=#{params[:dir_name]}.tar"
    io = IO.popen("tar -C /home/my/files -cf - #{params[:dir_name]}")
    Process.detach(io.pid)
    return io
end