Rails渲染/流式传输类似IO的对象而不缓冲

时间:2017-07-28 11:01:30

标签: ruby-on-rails ruby networking stream ruby-on-rails-5

我有一个控制器需要响应最多可能100MB的数据,这些数据来自网络上的其他来源(例如HTTP,FTP或自定义协议套接字),我试图弄清楚我应该怎么做渲染此响应时没有写入临时文件然后呈现/发送该文件的相当大的延迟。

我能够"关闭"当rails完成时的流,所以我可以限制活动连接的数量,或者使用池(例如,因为某些协议的速度很慢" connect")。

直接将IO传递给渲染不起作用。 render sock

'#<TCPSocket:fd 20>' is not an ActiveModel-compatible object

对于模板,我看到文档说只是使用render stream: true来禁用缓冲,但是对于那个Id仍然需要Rails接受(也许缓冲)我的对象。

1 个答案:

答案 0 :(得分:0)

一种可能的解决方案是利用ActionController::Live模块在​​Rails中使用内置live streaming support

  

Rails允许您传输的不仅仅是文件。实际上,您可以在响应对象中流式传输任何内容。 ActionController::Live模块允许您使用浏览器创建持久连接。使用此模块,您将能够在特定时间点向浏览器发送任意数据。

class MyController < ActionController::Base
  include ActionController::Live

  def my_action
    response.headers["Content-Type"] = "your/content-type"

    TCPSocket.open("server", 1234) do |socket|
      # for each chunk of data you read:
      response.stream.write data
    end
  ensure
    response.stream.close
  end
end