Class: Faraday::Adapter::EMHttp

Inherits:
Faraday::Adapter show all
Includes:
Options
Defined in:
lib/faraday/adapter/em_http.rb

Overview

EventMachine adapter is useful for either asynchronous requests when in EM reactor loop or for making parallel requests in synchronous code.

Defined Under Namespace

Modules: Options Classes: Manager

Constant Summary

Constants inherited from Faraday::Adapter

CONTENT_LENGTH

Instance Attribute Summary

Attributes included from Parallelism

#supports_parallel

Class Method Summary collapse

Instance Method Summary collapse

Methods included from Options

#configure_compression, #configure_proxy, #configure_socket, #configure_ssl, #configure_timeout, #connection_config, #read_body, #request_config, #request_options

Methods inherited from Faraday::Adapter

adapter?, #prepend_proxy_auth_string, #save_response

Methods included from Faraday::AutoloadHelper

#all_loaded_constants, #autoload_all, #load_autoloaded_constants

Methods included from MiddlewareRegistry

#lookup_middleware, #register_middleware

Methods included from Parallelism

#inherited, #supports_parallel?

Methods inherited from Middleware

adapter?, dependency, inherited, #initialize, loaded?, new

Constructor Details

This class inherits a constructor from Faraday::Middleware

Class Method Details

.setup_parallel_manager(options = nil) ⇒ Object



86
87
88
# File 'lib/faraday/adapter/em_http.rb', line 86

def self.setup_parallel_manager(options = nil)
  Manager.new
end

Instance Method Details

#call(env) ⇒ Object



90
91
92
93
94
# File 'lib/faraday/adapter/em_http.rb', line 90

def call(env)
  super
  perform_request env
  @app.call env
end

#error_message(client) ⇒ Object



141
142
143
# File 'lib/faraday/adapter/em_http.rb', line 141

def error_message(client)
  client.error or "request failed"
end

#parallel?(env) ⇒ Boolean

Returns:

  • (Boolean)


157
158
159
# File 'lib/faraday/adapter/em_http.rb', line 157

def parallel?(env)
  !!env[:parallel_manager]
end

#perform_request(env) ⇒ Object



96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
# File 'lib/faraday/adapter/em_http.rb', line 96

def perform_request(env)
  if parallel?(env)
    manager = env[:parallel_manager]
    manager.add {
      perform_single_request(env).
        callback { env[:response].finish(env) }
    }
  else
    unless EventMachine.reactor_running?
      error = nil
      # start EM, block until request is completed
      EventMachine.run do
        perform_single_request(env).
          callback { EventMachine.stop }.
          errback { |client|
            error = error_message(client)
            EventMachine.stop
          }
      end
      raise_error(error) if error
    else
      # EM is running: instruct upstream that this is an async request
      env[:parallel_manager] = true
      perform_single_request(env).
        callback { env[:response].finish(env) }.
        errback {
          # TODO: no way to communicate the error in async mode
          raise NotImplementedError
        }
    end
  end
end

#perform_single_request(env) ⇒ Object

TODO: reuse the connection to support pipelining



130
131
132
133
134
135
136
137
138
139
# File 'lib/faraday/adapter/em_http.rb', line 130

def perform_single_request(env)
  req = EventMachine::HttpRequest.new(env[:url], connection_config(env))
  req.setup_request(env[:method], request_config(env)).callback { |client|
    save_response(env, client.response_header.status, client.response) do |resp_headers|
      client.response_header.each do |name, value|
        resp_headers[name.to_sym] = value
      end
    end
  }
end

#raise_error(msg) ⇒ Object

Raises:

  • (errklass)


145
146
147
148
149
150
151
152
153
154
155
# File 'lib/faraday/adapter/em_http.rb', line 145

def raise_error(msg)
  errklass = Faraday::Error::ClientError
  if msg == Errno::ETIMEDOUT
    errklass = Faraday::Error::TimeoutError
    msg = "request timed out"
  elsif msg == Errno::ECONNREFUSED
    errklass = Faraday::Error::ConnectionFailed
    msg = "connection refused"
  end
  raise errklass, msg
end