diff --git a/lib/faraday/adapter/em_http.rb b/lib/faraday/adapter/em_http.rb index 49364db4..d1d80e32 100644 --- a/lib/faraday/adapter/em_http.rb +++ b/lib/faraday/adapter/em_http.rb @@ -4,6 +4,80 @@ module Faraday # when in EM reactor loop or for making parallel requests in # synchronous code. class EMHttp < Faraday::Adapter + module Options + def connection_config(env) + options = {} + configure_ssl(options, env) + configure_proxy(options, env) + configure_timeout(options, env) + configure_socket(options, env) + options + end + + def request_config(env) + options = { + :body => read_body(env), + :head => env[:request_headers], + # :keepalive => true, + # :file => 'path/to/file', # stream data off disk + } + configure_compression(options, env) + # configure_proxy_auth + # :proxy => {:authorization => [user, pass]} + # proxy[:username] && proxy[:password] + options + end + + def read_body(env) + body = env[:body] + body.respond_to?(:read) ? body.read : body + end + + def configure_ssl(options, env) + if ssl = env[:ssl] + # :ssl => { + # :private_key_file => '/tmp/server.key', + # :cert_chain_file => '/tmp/server.crt', + # :verify_peer => false + end + end + + def configure_proxy(options, env) + if proxy = request_options(env)[:proxy] + options[:proxy] = { + :host => proxy[:uri].host, + :port => proxy[:uri].port + } + end + end + + def configure_socket(options, env) + if bind = request_options(env)[:bind] + options[:bind] = { + :host => bind[:host], + :port => bind[:port] + } + end + end + + def configure_timeout(options, env) + timeout, open_timeout = request_options(env).values_at(:timeout, :open_timeout) + options[:connect_timeout] = options[:inactivity_timeout] = timeout + options[:connect_timeout] = open_timeout if open_timeout + end + + def configure_compression(options, env) + if env[:method] == :get and not options[:head].key? 'accept-encoding' + options[:head]['accept-encoding'] = 'gzip, compressed' + end + end + + def request_options(env) + env[:request] + end + end + + include Options dependency 'em-http' @@ -80,67 +154,6 @@ module Faraday raise errklass, msg end - def connection_config(env) - options = {} - configure_ssl(options, env) - configure_proxy(options, env) - configure_timeout(options, env) - options - end - - def request_config(env) - options = { - :body => read_body(env), - :head => env[:request_headers], - # :keepalive => true, - # :file => 'path/to/file', # stream data off disk - } - configure_compression(options, env) - # configure_proxy_auth - # :proxy => {:authorization => [user, pass]} - # proxy[:username] && proxy[:password] - options - end - - def read_body(env) - body = env[:body] - body.respond_to?(:read) ? body.read : body - end - - def configure_ssl(options, env) - if ssl = env[:ssl] - # :ssl => { - # :private_key_file => '/tmp/server.key', - # :cert_chain_file => '/tmp/server.crt', - # :verify_peer => false - end - end - - def configure_proxy(options, env) - if proxy = request_options(env)[:proxy] - options[:proxy] = { - :host => proxy[:uri].host, - :port => proxy[:uri].port - } - end - end - - def configure_timeout(options, env) - timeout, open_timeout = request_options(env).values_at(:timeout, :open_timeout) - options[:connect_timeout] = options[:inactivity_timeout] = timeout - options[:connect_timeout] = open_timeout if open_timeout - end - - def configure_compression(options, env) - if env[:method] == :get and not options[:head].key? 'accept-encoding' - options[:head]['accept-encoding'] = 'gzip, compressed' - end - end - - def request_options(env) - env[:request] - end - def parallel?(env) !!env[:parallel_manager] end diff --git a/lib/faraday/adapter/em_synchrony.rb b/lib/faraday/adapter/em_synchrony.rb index 306fe7d4..22df1c48 100644 --- a/lib/faraday/adapter/em_synchrony.rb +++ b/lib/faraday/adapter/em_synchrony.rb @@ -3,6 +3,7 @@ require 'uri' module Faraday class Adapter class EMSynchrony < Faraday::Adapter + include EMHttp::Options dependency do require 'em-synchrony/em-http' @@ -18,41 +19,13 @@ module Faraday def call(env) super - request = EventMachine::HttpRequest.new(URI::parse(env[:url].to_s)) - options = {:head => env[:request_headers]} - options[:ssl] = env[:ssl] if env[:ssl] - - if env[:body] - if env[:body].respond_to? :read - options[:body] = env[:body].read - else - options[:body] = env[:body] - end - end - - if req = env[:request] - if proxy = req[:proxy] - uri = URI.parse(proxy[:uri]) - options[:proxy] = { - :host => uri.host, - :port => uri.port - } - if proxy[:username] && proxy[:password] - options[:proxy][:authorization] = [proxy[:username], proxy[:password]] - end - end - - # only one timeout currently supported by em http request - if req[:timeout] or req[:open_timeout] - options[:timeout] = [req[:timeout] || 0, req[:open_timeout] || 0].max - end - end + request = EventMachine::HttpRequest.new(URI::parse(env[:url].to_s), connection_config(env)) http_method = env[:method].to_s.downcase.to_sym # Queue requests for parallel execution. if env[:parallel_manager] - env[:parallel_manager].add(request, http_method, options) do |resp| + env[:parallel_manager].add(request, http_method, request_config(env)) do |resp| save_response(env, resp.response_header.status, resp.response) do |resp_headers| resp.response_header.each do |name, value| resp_headers[name.to_sym] = value @@ -66,7 +39,7 @@ module Faraday # Execute single request. else client = nil - block = lambda { request.send(http_method, options) } + block = lambda { request.send(http_method, request_config(env)) } if !EM.reactor_running? EM.run do diff --git a/test/adapters/em_http_test.rb b/test/adapters/em_http_test.rb index 49e3c7a9..f9de24b6 100644 --- a/test/adapters/em_http_test.rb +++ b/test/adapters/em_http_test.rb @@ -10,5 +10,11 @@ module Adapters undef :test_timeout end + def test_binds_local_socket + host = '1.2.3.4' + conn = create_connection :request => { :bind => { :host => host } } + #puts conn.get('/who-am-i').body + assert_equal host, conn.options[:bind][:host] + end end end diff --git a/test/adapters/em_synchrony_test.rb b/test/adapters/em_synchrony_test.rb index b16949df..5f5f0b44 100644 --- a/test/adapters/em_synchrony_test.rb +++ b/test/adapters/em_synchrony_test.rb @@ -10,5 +10,11 @@ module Adapters undef :test_timeout end + def test_binds_local_socket + host = '1.2.3.4' + conn = create_connection :request => { :bind => { :host => host } } + #put conn.get('/who-am-i').body + assert_equal host, conn.options[:bind][:host] + end end unless RUBY_VERSION < '1.9' or (defined? RUBY_ENGINE and 'jruby' == RUBY_ENGINE) end diff --git a/test/live_server.rb b/test/live_server.rb index e87d43cf..4e7906ea 100644 --- a/test/live_server.rb +++ b/test/live_server.rb @@ -35,6 +35,10 @@ class FaradayTestServer < Sinatra::Base [200, { 'Set-Cookie' => 'one, two' }, ''] end + get '/who-am-i' do + request.env['REMOTE_ADDR'] + end + get '/slow' do sleep 10 [200, {}, 'ok']