2012-05-04 20:45:47 +00:00
|
|
|
require 'eventmachine'
|
|
|
|
|
|
|
|
module Rack
|
|
|
|
class EMStream
|
|
|
|
include EventMachine::Deferrable
|
|
|
|
|
2012-09-15 16:26:55 +00:00
|
|
|
def initialize(app, &block)
|
|
|
|
@app, @block = app, block
|
2012-05-04 20:45:47 +00:00
|
|
|
end
|
|
|
|
|
|
|
|
def each(&b)
|
|
|
|
@callback = b
|
|
|
|
end
|
|
|
|
|
|
|
|
def call(env)
|
|
|
|
dup._call(env)
|
|
|
|
end
|
|
|
|
|
|
|
|
def _call(env)
|
|
|
|
result = @app.call(env)
|
|
|
|
|
2012-09-15 16:28:35 +00:00
|
|
|
result[2].close if result[2].respond_to?(:close)
|
|
|
|
|
2012-05-04 20:45:47 +00:00
|
|
|
EM.next_tick {
|
|
|
|
env['async.callback'].call [ result[0], result[1], self ]
|
|
|
|
|
2012-09-15 16:26:55 +00:00
|
|
|
begin
|
|
|
|
result[2].each { |data|
|
|
|
|
EM.next_tick {
|
|
|
|
begin
|
|
|
|
@callback.call(data)
|
|
|
|
rescue => e
|
|
|
|
@callback.call(@block.call(e, env)) if @block
|
|
|
|
end
|
|
|
|
}
|
|
|
|
}
|
|
|
|
rescue => e
|
|
|
|
@callback.call(@block.call(e, env)) if @block
|
|
|
|
end
|
|
|
|
|
2012-05-04 20:45:47 +00:00
|
|
|
EM.next_tick { succeed }
|
|
|
|
}
|
|
|
|
|
|
|
|
throw :async
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|