1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 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 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299
|
module HeaderDowncaser
def downcase_headers(headers)
{}.tap do |downcased|
headers.each do |k, v|
downcased[k.downcase] = v
end
end
end
end
HTTP_LIBRARY_ADAPTERS = {}
HTTP_LIBRARY_ADAPTERS['net/http'] = Module.new do
include HeaderDowncaser
def self.http_library_name; 'Net::HTTP'; end
def get_body_string(response); response.body; end
alias get_body_object get_body_string
def get_header(header_key, response)
response.get_fields(header_key)
end
def make_http_request(method, url, body = nil, headers = {})
uri = URI.parse(url)
http = Net::HTTP.new(uri.host, uri.port)
if uri.scheme == "https"
http.use_ssl = true
http.verify_mode = OpenSSL::SSL::VERIFY_NONE
end
http.send_request(method.to_s.upcase, uri.request_uri, body, headers)
end
DEFAULT_REQUEST_HEADERS = { "Accept"=>["*/*"] }
DEFAULT_REQUEST_HEADERS['User-Agent'] = ["Ruby"]
DEFAULT_REQUEST_HEADERS['Accept-Encoding'] = ["gzip;q=1.0,deflate;q=0.6,identity;q=0.3"] if RUBY_VERSION.to_f > 1.9
def normalize_request_headers(headers)
defined?(super) ? super :
downcase_headers(headers.merge(DEFAULT_REQUEST_HEADERS))
end
end
HTTP_LIBRARY_ADAPTERS['patron'] = Module.new do
def self.http_library_name; 'Patron'; end
def get_body_string(response); response.body; end
alias get_body_object get_body_string
def get_header(header_key, response)
response.headers[header_key]
end
def make_http_request(method, url, body = nil, headers = {})
Patron::Session.new.request(method, url, headers, :data => body || '')
end
def normalize_request_headers(headers)
headers.merge('Expect' => [''])
end
end
HTTP_LIBRARY_ADAPTERS['httpclient'] = Module.new do
def self.http_library_name; 'HTTP Client'; end
def get_body_string(response)
body = response.body
string = body.is_a?(String) ? body : body.content
string.respond_to?(:read) ? string.read : string
end
def get_body_object(response)
response.body
end
def get_header(header_key, response)
response.header[header_key]
end
def make_http_request(method, url, body = nil, headers = {})
HTTPClient.new.request(method, url, nil, body, headers)
end
def normalize_request_headers(headers)
headers.merge({
'Accept' => ["*/*"],
'User-Agent' => ["HTTPClient/1.0 (#{HTTPClient::VERSION}, ruby #{RUBY_VERSION} (#{RUBY_RELEASE_DATE}))"],
'Date' => [Time.now.httpdate]
})
end
end
HTTP_LIBRARY_ADAPTERS['em-http-request'] = Module.new do
def self.http_library_name; 'EM HTTP Request'; end
def get_body_string(response)
response.response
end
alias get_body_object get_body_string
def get_header(header_key, response)
values = response.response_header[header_key.upcase.gsub('-', '_')]
values.is_a?(Array) ? values : values.split(', ')
end
def make_http_request(method, url, body = nil, headers = {})
http = nil
EventMachine.run do
# Several request options are required to prevent em-http-request from inserting headers
request_options = {
body: body,
head: headers.merge({"user-agent" => nil}),
compressed: false,
keepalive: true
}
http = EventMachine::HttpRequest.new(url).send(method, **request_options)
http.callback { EventMachine.stop }
end
http
end
def normalize_request_headers(headers)
headers
end
end
HTTP_LIBRARY_ADAPTERS['curb'] = Module.new do
def self.http_library_name; "Curb"; end
def get_body_string(response)
response.body_str
end
alias get_body_object get_body_string
def get_header(header_key, response)
headers = response.header_str.split("\r\n")[1..-1]
value = nil
headers.each do |h|
next unless h =~ /^#{Regexp.escape(header_key)}: (.*)$/
new_value = $1.split(', ')
value = value ? Array(value) + Array(new_value) : new_value
end
value
end
def make_http_request(method, url, body = nil, headers = {})
Curl::Easy.new(url) do |c|
c.headers = headers
if [:post, :put].include?(method)
c.send("http_#{method}", body)
else
c.send("http_#{method}")
end
end
end
def normalize_request_headers(headers)
headers
end
end
HTTP_LIBRARY_ADAPTERS['typhoeus'] = Module.new do
def self.http_library_name; "Typhoeus"; end
def get_body_string(response)
response.body
end
alias get_body_object get_body_string
def get_header(header_key, response)
# Due to https://github.com/typhoeus/typhoeus/commit/256c95473d5d40d7ec2f5db603687323ddd73689
# headers are now downcased.
# ...except when they're not. I'm not 100% why (I haven't had time to dig into it yet)
# but in some situations the headers aren't downcased. I think it has to do with playback; VCR
# isn't sending the headers in downcased to typhoeus. It gets complicated with the interaction
# w/ WebMock, and the fact that webmock normalizes headers in a different fashion.
#
# For now this hack works.
response.headers.fetch(header_key.downcase) { response.headers[header_key] }
end
def make_http_request(method, url, body = nil, headers = {})
request = Typhoeus::Request.new(url, :method => method, :body => body, :headers => headers)
request.run
request.response
end
def normalize_request_headers(headers)
headers.merge("User-Agent"=>["Typhoeus - https://github.com/typhoeus/typhoeus"], 'Expect' => [''])
end
end
HTTP_LIBRARY_ADAPTERS['typhoeus 0.4'] = Module.new do
def self.http_library_name; "Typhoeus"; end
def get_body_string(response)
response.body
end
alias get_body_object get_body_string
def get_header(header_key, response)
response.headers_hash[header_key]
end
def make_http_request(method, url, body = nil, headers = {})
Typhoeus::Request.send(method, url, :body => body, :headers => headers)
end
def normalize_request_headers(headers)
headers
end
end
HTTP_LIBRARY_ADAPTERS['excon'] = Module.new do
def self.http_library_name; "Excon"; end
def get_body_string(response)
response.body
end
alias get_body_object get_body_string
def get_header(header_key, response)
response.headers[header_key]
end
def make_http_request(method, url, body = nil, headers = {})
# There are multiple ways to use Excon but this is how fog (the main user of excon) uses it:
# https://github.com/fog/fog/blob/v1.1.1/lib/fog/aws/rds.rb#L139-147
Excon.new(url).request(:method => method.to_s.upcase, :body => body, :headers => headers)
end
def normalize_request_headers(headers)
if Gem::Version.new(Excon::VERSION) < Gem::Version.new("0.63")
headers.merge('User-Agent' => [Excon::USER_AGENT])
else
headers.merge('User-Agent' => [Excon::USER_AGENT], 'Accept' => ['*/*'])
end
end
end
%w[ net_http typhoeus patron ].each do |_faraday_adapter|
if _faraday_adapter == 'typhoeus' &&
defined?(::Typhoeus::VERSION) &&
::Typhoeus::VERSION.to_f >= 0.5
require 'typhoeus/adapters/faraday'
end
HTTP_LIBRARY_ADAPTERS["faraday (w/ #{_faraday_adapter})"] = Module.new do
class << self; self; end.class_eval do
define_method(:http_library_name) do
"Faraday (#{_faraday_adapter})"
end
end
define_method(:faraday_adapter) { _faraday_adapter.to_sym }
def get_body_string(response)
response.body
end
alias get_body_object get_body_string
def get_header(header_key, response)
value = response.headers[header_key]
value.split(', ') if value
end
def make_http_request(method, url, body = nil, headers = {})
url_root, url_rest = split_url(url)
faraday_connection(url_root).send(method) do |req|
req.url url_rest
headers.each { |k, v| req[k] = v }
req.body = body if body
end
end
def split_url(url)
uri = URI.parse(url)
url_root = "#{uri.scheme}://#{uri.host}:#{uri.port}"
rest = url.sub(url_root, '')
[url_root, rest]
end
def faraday_connection(url_root)
Faraday::Connection.new(:url => url_root) do |builder|
builder.adapter faraday_adapter
end
end
def normalize_request_headers(headers)
headers.merge("User-Agent" => ["Faraday v#{Faraday::VERSION}"])
end
end
end
|