91 lines
2.4 KiB
Ruby
91 lines
2.4 KiB
Ruby
|
# We are hacking net/http to change semantics of streaming handling
|
||
|
# from "block" semantics to regular "return" semnatics.
|
||
|
# We need it to construct a streamable rack triplet:
|
||
|
#
|
||
|
# [status, headers, streamable_body]
|
||
|
#
|
||
|
# See http://github.com/aniero/rack-streaming-proxy
|
||
|
# for alternative that uses additional process.
|
||
|
#
|
||
|
# BTW I don't like monkey patching either
|
||
|
# but this is not real monkey patching.
|
||
|
# I just added some methods and named them very uniquely
|
||
|
# to avoid eventual conflicts. You're safe. Trust me.
|
||
|
#
|
||
|
# Also, in Ruby 1.9.2 you could use Fibers to avoid hacking net/http.
|
||
|
|
||
|
require 'net/https'
|
||
|
|
||
|
class Net::HTTP
|
||
|
# Original #request with block semantics.
|
||
|
#
|
||
|
# def request(req, body = nil, &block)
|
||
|
# unless started?
|
||
|
# start {
|
||
|
# req['connection'] ||= 'close'
|
||
|
# return request(req, body, &block)
|
||
|
# }
|
||
|
# end
|
||
|
# if proxy_user()
|
||
|
# unless use_ssl?
|
||
|
# req.proxy_basic_auth proxy_user(), proxy_pass()
|
||
|
# end
|
||
|
# end
|
||
|
#
|
||
|
# req.set_body_internal body
|
||
|
# begin_transport req
|
||
|
# req.exec @socket, @curr_http_version, edit_path(req.path)
|
||
|
# begin
|
||
|
# res = HTTPResponse.read_new(@socket)
|
||
|
# end while res.kind_of?(HTTPContinue)
|
||
|
# res.reading_body(@socket, req.response_body_permitted?) {
|
||
|
# yield res if block_given?
|
||
|
# }
|
||
|
# end_transport req, res
|
||
|
#
|
||
|
# res
|
||
|
# end
|
||
|
|
||
|
def begin_request_hacked(req)
|
||
|
begin_transport req
|
||
|
req.exec @socket, @curr_http_version, edit_path(req.path)
|
||
|
begin
|
||
|
res = Net::HTTPResponse.read_new(@socket)
|
||
|
end while res.kind_of?(Net::HTTPContinue)
|
||
|
res.begin_reading_body_hacked(@socket, req.response_body_permitted?)
|
||
|
@req_hacked, @res_hacked = req, res
|
||
|
@res_hacked
|
||
|
end
|
||
|
|
||
|
def end_request_hacked
|
||
|
@res_hacked.end_reading_body_hacked
|
||
|
end_transport @req_hacked, @res_hacked
|
||
|
@res_hacked
|
||
|
end
|
||
|
end
|
||
|
|
||
|
class Net::HTTPResponse
|
||
|
# Original #reading_body with block semantics
|
||
|
#
|
||
|
# def reading_body(sock, reqmethodallowbody) #:nodoc: internal use only
|
||
|
# @socket = sock
|
||
|
# @body_exist = reqmethodallowbody && self.class.body_permitted?
|
||
|
# begin
|
||
|
# yield
|
||
|
# self.body # ensure to read body
|
||
|
# ensure
|
||
|
# @socket = nil
|
||
|
# end
|
||
|
# end
|
||
|
|
||
|
def begin_reading_body_hacked(sock, reqmethodallowbody)
|
||
|
@socket = sock
|
||
|
@body_exist = reqmethodallowbody && self.class.body_permitted?
|
||
|
end
|
||
|
|
||
|
def end_reading_body_hacked
|
||
|
self.body
|
||
|
@socket = nil
|
||
|
end
|
||
|
end
|