Posts JRuby/Rails Streaming in development environment (and beyond)
Post
Cancel

JRuby/Rails Streaming in development environment (and beyond)

Rails streaming is a great feature that allows you to optimize on server resources when dealing with large generated content. However – it might be a bit tricky to validate and test in local development.

First off – a local server that supports streaming is required. The only one I could find was trinidad which is moving to the likely defacto for JRuby/Rails projects. Trinidad uses tomcat-core as it’s servlet container and server.

Then make sure you grab the latest jruby-rack resolving most recent issues (1.1.10 at the time of writing).

This StackOverflow answer, along with this guide offer a comprehensive support as to what options work with Rails version as well as some gotchas (newrelic, caching, haml, …).

For Rails 3.2.x – It boils down to assigning an object that responds to an each method call to the response_body of a controller’s action. However – this doesn’t allow you to set a :stream =>true where it explicitly tells Rails to stream the respons. To resolve that I opted to use a render call, with a passed option hash as follows:

# Controller

def streaming_action
  @objs = MyObj.where(:foo => 'bar')
  render :nothing => true, :stream => true #setting the response to stream while rendering nothing

  self.response_body = Streamer.new(@objs) # the object responding to 'each' call

end

#models/streamer.rb

class Streamer
  attr_accssor :objs

  def initialize(objs)
    @objs = objs
  end

  # all the magic

  def each
    yield "Some initial output for header"
    @objs.each do |obj|
      yield "#{obj.attr}\n"
    end
  end
end

This works with the following releases: JRuby 1.6.8 Rails 3.2.8 jruby-rack 1.1.10 trinidad 1.4.4

Contents

Search Results