Skip to content

Instantly share code, notes, and snippets.

@voloko
Created October 12, 2009 08:23
Show Gist options
  • Save voloko/208243 to your computer and use it in GitHub Desktop.
Save voloko/208243 to your computer and use it in GitHub Desktop.
module Sinatra
module AsyncHelpers
def async_start
env['async.callback'].call [response.status, response.headers, dbody]
throw :async
end
def async_write data
dbody << data
end
def async_finish
dbody.succeed
end
def on_async_interrupt &block
dbody.callback { block.call }
dbody.errback { block.call }
end
def dbody
@dbody ||= DeferrableBody.new
end
protected
class DeferrableBody
include EventMachine::Deferrable
def << body
body.each do |chunk|
@body_callback.call(chunk)
end
end
alias_method :call, :<<
def each &blk
@body_callback = blk
end
end
end
end
get '/delay/:n' do |n|
EM.add_timer(n) do
async_write ["{a:'delayed for #{n} seconds'}"]
async_finish
end
response.headers['Content-Type'] = 'application/x-javascript'
async_start
end
get '/timer/:n' do |n|
cancel = false
writer = proc {
unless cancel
async_write ["time: " + Time.now.to_s, "<br />"]
EM.add_timer(n, writer)
end
}
EM.add_timer(n, writer)
on_async_interrupt do
cancel = true
end
async_start
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment