faraday 0.12.0 → 1.4.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +5 -5
- data/CHANGELOG.md +380 -0
- data/LICENSE.md +1 -1
- data/README.md +21 -308
- data/Rakefile +7 -0
- data/examples/client_spec.rb +65 -0
- data/examples/client_test.rb +79 -0
- data/lib/faraday/adapter/httpclient.rb +83 -59
- data/lib/faraday/adapter/patron.rb +92 -36
- data/lib/faraday/adapter/rack.rb +30 -13
- data/lib/faraday/adapter/test.rb +103 -62
- data/lib/faraday/adapter/typhoeus.rb +7 -115
- data/lib/faraday/adapter.rb +77 -22
- data/lib/faraday/adapter_registry.rb +30 -0
- data/lib/faraday/autoload.rb +42 -36
- data/lib/faraday/connection.rb +345 -179
- data/lib/faraday/dependency_loader.rb +37 -0
- data/lib/faraday/encoders/flat_params_encoder.rb +105 -0
- data/lib/faraday/encoders/nested_params_encoder.rb +176 -0
- data/lib/faraday/error.rb +127 -38
- data/lib/faraday/file_part.rb +128 -0
- data/lib/faraday/logging/formatter.rb +105 -0
- data/lib/faraday/methods.rb +6 -0
- data/lib/faraday/middleware.rb +19 -25
- data/lib/faraday/middleware_registry.rb +129 -0
- data/lib/faraday/options/connection_options.rb +22 -0
- data/lib/faraday/options/env.rb +181 -0
- data/lib/faraday/options/proxy_options.rb +32 -0
- data/lib/faraday/options/request_options.rb +22 -0
- data/lib/faraday/options/ssl_options.rb +59 -0
- data/lib/faraday/options.rb +39 -193
- data/lib/faraday/param_part.rb +53 -0
- data/lib/faraday/parameters.rb +4 -196
- data/lib/faraday/rack_builder.rb +84 -48
- data/lib/faraday/request/authorization.rb +44 -30
- data/lib/faraday/request/basic_authentication.rb +14 -7
- data/lib/faraday/request/instrumentation.rb +45 -27
- data/lib/faraday/request/multipart.rb +86 -48
- data/lib/faraday/request/retry.rb +209 -133
- data/lib/faraday/request/token_authentication.rb +15 -10
- data/lib/faraday/request/url_encoded.rb +43 -23
- data/lib/faraday/request.rb +94 -32
- data/lib/faraday/response/logger.rb +22 -69
- data/lib/faraday/response/raise_error.rb +49 -14
- data/lib/faraday/response.rb +27 -23
- data/lib/faraday/utils/headers.rb +139 -0
- data/lib/faraday/utils/params_hash.rb +61 -0
- data/lib/faraday/utils.rb +38 -238
- data/lib/faraday/version.rb +5 -0
- data/lib/faraday.rb +124 -187
- data/spec/external_adapters/faraday_specs_setup.rb +14 -0
- data/spec/faraday/adapter/em_http_spec.rb +47 -0
- data/spec/faraday/adapter/em_synchrony_spec.rb +16 -0
- data/spec/faraday/adapter/excon_spec.rb +49 -0
- data/spec/faraday/adapter/httpclient_spec.rb +73 -0
- data/spec/faraday/adapter/net_http_spec.rb +64 -0
- data/spec/faraday/adapter/patron_spec.rb +18 -0
- data/spec/faraday/adapter/rack_spec.rb +8 -0
- data/spec/faraday/adapter/test_spec.rb +260 -0
- data/spec/faraday/adapter/typhoeus_spec.rb +7 -0
- data/spec/faraday/adapter_registry_spec.rb +28 -0
- data/spec/faraday/adapter_spec.rb +55 -0
- data/spec/faraday/composite_read_io_spec.rb +80 -0
- data/spec/faraday/connection_spec.rb +736 -0
- data/spec/faraday/error_spec.rb +60 -0
- data/spec/faraday/middleware_spec.rb +52 -0
- data/spec/faraday/options/env_spec.rb +70 -0
- data/spec/faraday/options/options_spec.rb +297 -0
- data/spec/faraday/options/proxy_options_spec.rb +44 -0
- data/spec/faraday/options/request_options_spec.rb +19 -0
- data/spec/faraday/params_encoders/flat_spec.rb +42 -0
- data/spec/faraday/params_encoders/nested_spec.rb +142 -0
- data/spec/faraday/rack_builder_spec.rb +345 -0
- data/spec/faraday/request/authorization_spec.rb +88 -0
- data/spec/faraday/request/instrumentation_spec.rb +76 -0
- data/spec/faraday/request/multipart_spec.rb +302 -0
- data/spec/faraday/request/retry_spec.rb +242 -0
- data/spec/faraday/request/url_encoded_spec.rb +83 -0
- data/spec/faraday/request_spec.rb +120 -0
- data/spec/faraday/response/logger_spec.rb +220 -0
- data/spec/faraday/response/middleware_spec.rb +68 -0
- data/spec/faraday/response/raise_error_spec.rb +169 -0
- data/spec/faraday/response_spec.rb +75 -0
- data/spec/faraday/utils/headers_spec.rb +82 -0
- data/spec/faraday/utils_spec.rb +56 -0
- data/spec/faraday_spec.rb +37 -0
- data/spec/spec_helper.rb +132 -0
- data/spec/support/disabling_stub.rb +14 -0
- data/spec/support/fake_safe_buffer.rb +15 -0
- data/spec/support/helper_methods.rb +133 -0
- data/spec/support/shared_examples/adapter.rb +105 -0
- data/spec/support/shared_examples/params_encoder.rb +18 -0
- data/spec/support/shared_examples/request_method.rb +262 -0
- data/spec/support/streaming_response_checker.rb +35 -0
- data/spec/support/webmock_rack_app.rb +68 -0
- metadata +164 -16
- data/lib/faraday/adapter/em_http.rb +0 -243
- data/lib/faraday/adapter/em_http_ssl_patch.rb +0 -56
- data/lib/faraday/adapter/em_synchrony/parallel_manager.rb +0 -66
- data/lib/faraday/adapter/em_synchrony.rb +0 -106
- data/lib/faraday/adapter/excon.rb +0 -80
- data/lib/faraday/adapter/net_http.rb +0 -135
- data/lib/faraday/adapter/net_http_persistent.rb +0 -50
- data/lib/faraday/upload_io.rb +0 -67
data/lib/faraday/connection.rb
CHANGED
|
@@ -1,8 +1,10 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
1
3
|
module Faraday
|
|
2
|
-
#
|
|
4
|
+
# Connection objects manage the default properties and the middleware
|
|
3
5
|
# stack for fulfilling an HTTP request.
|
|
4
6
|
#
|
|
5
|
-
#
|
|
7
|
+
# @example
|
|
6
8
|
#
|
|
7
9
|
# conn = Faraday::Connection.new 'http://sushi.com'
|
|
8
10
|
#
|
|
@@ -12,52 +14,55 @@ module Faraday
|
|
|
12
14
|
#
|
|
13
15
|
class Connection
|
|
14
16
|
# A Set of allowed HTTP verbs.
|
|
15
|
-
METHODS = Set.new [
|
|
17
|
+
METHODS = Set.new %i[get post put delete head patch options trace]
|
|
16
18
|
|
|
17
|
-
#
|
|
19
|
+
# @return [Hash] URI query unencoded key/value pairs.
|
|
18
20
|
attr_reader :params
|
|
19
21
|
|
|
20
|
-
#
|
|
22
|
+
# @return [Hash] unencoded HTTP header key/value pairs.
|
|
21
23
|
attr_reader :headers
|
|
22
24
|
|
|
23
|
-
#
|
|
24
|
-
#
|
|
25
|
+
# @return [String] a URI with the prefix used for all requests from this
|
|
26
|
+
# Connection. This includes a default host name, scheme, port, and path.
|
|
25
27
|
attr_reader :url_prefix
|
|
26
28
|
|
|
27
|
-
#
|
|
29
|
+
# @return [Faraday::Builder] Builder for this Connection.
|
|
28
30
|
attr_reader :builder
|
|
29
31
|
|
|
30
|
-
#
|
|
31
|
-
attr_reader :options
|
|
32
|
-
|
|
33
|
-
# Public: Returns a Hash of the SSL options.
|
|
32
|
+
# @return [Hash] SSL options.
|
|
34
33
|
attr_reader :ssl
|
|
35
34
|
|
|
36
|
-
#
|
|
35
|
+
# @return [Object] the parallel manager for this Connection.
|
|
37
36
|
attr_reader :parallel_manager
|
|
38
37
|
|
|
39
|
-
#
|
|
38
|
+
# Sets the default parallel manager for this connection.
|
|
40
39
|
attr_writer :default_parallel_manager
|
|
41
40
|
|
|
42
|
-
#
|
|
41
|
+
# @return [Hash] proxy options.
|
|
42
|
+
attr_reader :proxy
|
|
43
|
+
|
|
44
|
+
# Initializes a new Faraday::Connection.
|
|
43
45
|
#
|
|
44
|
-
# url
|
|
46
|
+
# @param url [URI, String] URI or String base URL to use as a prefix for all
|
|
45
47
|
# requests (optional).
|
|
46
|
-
# options
|
|
47
|
-
#
|
|
48
|
-
#
|
|
49
|
-
#
|
|
50
|
-
#
|
|
51
|
-
#
|
|
52
|
-
#
|
|
53
|
-
#
|
|
54
|
-
#
|
|
55
|
-
#
|
|
56
|
-
#
|
|
48
|
+
# @param options [Hash, Faraday::ConnectionOptions]
|
|
49
|
+
# @option options [URI, String] :url ('http:/') URI or String base URL
|
|
50
|
+
# @option options [Hash<String => String>] :params URI query unencoded
|
|
51
|
+
# key/value pairs.
|
|
52
|
+
# @option options [Hash<String => String>] :headers Hash of unencoded HTTP
|
|
53
|
+
# header key/value pairs.
|
|
54
|
+
# @option options [Hash] :request Hash of request options.
|
|
55
|
+
# @option options [Hash] :ssl Hash of SSL options.
|
|
56
|
+
# @option options [Hash, URI, String] :proxy proxy options, either as a URL
|
|
57
|
+
# or as a Hash
|
|
58
|
+
# @option options [URI, String] :proxy[:uri]
|
|
59
|
+
# @option options [String] :proxy[:user]
|
|
60
|
+
# @option options [String] :proxy[:password]
|
|
61
|
+
# @yield [self] after all setup has been done
|
|
57
62
|
def initialize(url = nil, options = nil)
|
|
58
63
|
options = ConnectionOptions.from(options)
|
|
59
64
|
|
|
60
|
-
if url.is_a?(Hash)
|
|
65
|
+
if url.is_a?(Hash) || url.is_a?(ConnectionOptions)
|
|
61
66
|
options = options.merge(url)
|
|
62
67
|
url = options.url
|
|
63
68
|
end
|
|
@@ -68,10 +73,11 @@ module Faraday
|
|
|
68
73
|
@options = options.request
|
|
69
74
|
@ssl = options.ssl
|
|
70
75
|
@default_parallel_manager = options.parallel_manager
|
|
76
|
+
@manual_proxy = nil
|
|
71
77
|
|
|
72
78
|
@builder = options.builder || begin
|
|
73
79
|
# pass an empty block to Builder so it doesn't assume default middleware
|
|
74
|
-
options.new_builder(block_given? ?
|
|
80
|
+
options.new_builder(block_given? ? proc { |b| } : nil)
|
|
75
81
|
end
|
|
76
82
|
|
|
77
83
|
self.url_prefix = url || 'http:/'
|
|
@@ -79,35 +85,31 @@ module Faraday
|
|
|
79
85
|
@params.update(options.params) if options.params
|
|
80
86
|
@headers.update(options.headers) if options.headers
|
|
81
87
|
|
|
82
|
-
|
|
83
|
-
proxy(options.fetch(:proxy) {
|
|
84
|
-
uri = nil
|
|
85
|
-
if URI.parse("").respond_to?(:find_proxy)
|
|
86
|
-
case url
|
|
87
|
-
when String
|
|
88
|
-
uri = URI.parse(url).find_proxy
|
|
89
|
-
when URI
|
|
90
|
-
uri = url.find_proxy
|
|
91
|
-
when nil
|
|
92
|
-
uri = find_default_proxy
|
|
93
|
-
end
|
|
94
|
-
else
|
|
95
|
-
uri = find_default_proxy
|
|
96
|
-
end
|
|
97
|
-
uri
|
|
98
|
-
})
|
|
88
|
+
initialize_proxy(url, options)
|
|
99
89
|
|
|
100
90
|
yield(self) if block_given?
|
|
101
91
|
|
|
102
92
|
@headers[:user_agent] ||= "Faraday v#{VERSION}"
|
|
103
93
|
end
|
|
104
94
|
|
|
105
|
-
|
|
95
|
+
def initialize_proxy(url, options)
|
|
96
|
+
@manual_proxy = !!options.proxy
|
|
97
|
+
@proxy =
|
|
98
|
+
if options.proxy
|
|
99
|
+
ProxyOptions.from(options.proxy)
|
|
100
|
+
else
|
|
101
|
+
proxy_from_env(url)
|
|
102
|
+
end
|
|
103
|
+
end
|
|
104
|
+
|
|
105
|
+
# Sets the Hash of URI query unencoded key/value pairs.
|
|
106
|
+
# @param hash [Hash]
|
|
106
107
|
def params=(hash)
|
|
107
108
|
@params.replace hash
|
|
108
109
|
end
|
|
109
110
|
|
|
110
|
-
#
|
|
111
|
+
# Sets the Hash of unencoded HTTP header key/value pairs.
|
|
112
|
+
# @param hash [Hash]
|
|
111
113
|
def headers=(hash)
|
|
112
114
|
@headers.replace hash
|
|
113
115
|
end
|
|
@@ -116,71 +118,163 @@ module Faraday
|
|
|
116
118
|
|
|
117
119
|
def_delegators :builder, :build, :use, :request, :response, :adapter, :app
|
|
118
120
|
|
|
119
|
-
#
|
|
121
|
+
# Closes the underlying resources and/or connections. In the case of
|
|
122
|
+
# persistent connections, this closes all currently open connections
|
|
123
|
+
# but does not prevent new connections from being made.
|
|
124
|
+
def close
|
|
125
|
+
app.close
|
|
126
|
+
end
|
|
127
|
+
|
|
128
|
+
# @!method get(url = nil, params = nil, headers = nil)
|
|
129
|
+
# Makes a GET HTTP request without a body.
|
|
130
|
+
# @!scope class
|
|
120
131
|
#
|
|
121
|
-
# url
|
|
122
|
-
#
|
|
123
|
-
# params
|
|
124
|
-
# headers
|
|
132
|
+
# @param url [String] The optional String base URL to use as a prefix for
|
|
133
|
+
# all requests. Can also be the options Hash.
|
|
134
|
+
# @param params [Hash] Hash of URI query unencoded key/value pairs.
|
|
135
|
+
# @param headers [Hash] unencoded HTTP header key/value pairs.
|
|
125
136
|
#
|
|
126
|
-
#
|
|
127
|
-
#
|
|
128
|
-
# conn.get '/items', {:page => 1}, :accept => 'application/json'
|
|
129
|
-
# conn.head '/items/1'
|
|
137
|
+
# @example
|
|
138
|
+
# conn.get '/items', { page: 1 }, :accept => 'application/json'
|
|
130
139
|
#
|
|
131
140
|
# # ElasticSearch example sending a body with GET.
|
|
132
141
|
# conn.get '/twitter/tweet/_search' do |req|
|
|
133
142
|
# req.headers[:content_type] = 'application/json'
|
|
134
143
|
# req.params[:routing] = 'kimchy'
|
|
135
|
-
# req.body = JSON.generate(:
|
|
144
|
+
# req.body = JSON.generate(query: {...})
|
|
136
145
|
# end
|
|
137
146
|
#
|
|
138
|
-
#
|
|
139
|
-
#
|
|
147
|
+
# @yield [Faraday::Request] for further request customizations
|
|
148
|
+
# @return [Faraday::Response]
|
|
149
|
+
|
|
150
|
+
# @!method head(url = nil, params = nil, headers = nil)
|
|
151
|
+
# Makes a HEAD HTTP request without a body.
|
|
152
|
+
# @!scope class
|
|
140
153
|
#
|
|
141
|
-
#
|
|
154
|
+
# @param url [String] The optional String base URL to use as a prefix for
|
|
155
|
+
# all requests. Can also be the options Hash.
|
|
156
|
+
# @param params [Hash] Hash of URI query unencoded key/value pairs.
|
|
157
|
+
# @param headers [Hash] unencoded HTTP header key/value pairs.
|
|
142
158
|
#
|
|
143
|
-
#
|
|
159
|
+
# @example
|
|
160
|
+
# conn.head '/items/1'
|
|
144
161
|
#
|
|
145
|
-
#
|
|
146
|
-
|
|
162
|
+
# @yield [Faraday::Request] for further request customizations
|
|
163
|
+
# @return [Faraday::Response]
|
|
164
|
+
|
|
165
|
+
# @!method delete(url = nil, params = nil, headers = nil)
|
|
166
|
+
# Makes a DELETE HTTP request without a body.
|
|
167
|
+
# @!scope class
|
|
168
|
+
#
|
|
169
|
+
# @param url [String] The optional String base URL to use as a prefix for
|
|
170
|
+
# all requests. Can also be the options Hash.
|
|
171
|
+
# @param params [Hash] Hash of URI query unencoded key/value pairs.
|
|
172
|
+
# @param headers [Hash] unencoded HTTP header key/value pairs.
|
|
173
|
+
#
|
|
174
|
+
# @example
|
|
175
|
+
# conn.delete '/items/1'
|
|
176
|
+
#
|
|
177
|
+
# @yield [Faraday::Request] for further request customizations
|
|
178
|
+
# @return [Faraday::Response]
|
|
179
|
+
|
|
180
|
+
# @!method trace(url = nil, params = nil, headers = nil)
|
|
181
|
+
# Makes a TRACE HTTP request without a body.
|
|
182
|
+
# @!scope class
|
|
183
|
+
#
|
|
184
|
+
# @param url [String] The optional String base URL to use as a prefix for
|
|
185
|
+
# all requests. Can also be the options Hash.
|
|
186
|
+
# @param params [Hash] Hash of URI query unencoded key/value pairs.
|
|
187
|
+
# @param headers [Hash] unencoded HTTP header key/value pairs.
|
|
188
|
+
#
|
|
189
|
+
# @example
|
|
190
|
+
# conn.connect '/items/1'
|
|
191
|
+
#
|
|
192
|
+
# @yield [Faraday::Request] for further request customizations
|
|
193
|
+
# @return [Faraday::Response]
|
|
194
|
+
|
|
195
|
+
# @!visibility private
|
|
196
|
+
METHODS_WITH_QUERY.each do |method|
|
|
147
197
|
class_eval <<-RUBY, __FILE__, __LINE__ + 1
|
|
148
198
|
def #{method}(url = nil, params = nil, headers = nil)
|
|
149
|
-
run_request(:#{method}, url, nil, headers)
|
|
199
|
+
run_request(:#{method}, url, nil, headers) do |request|
|
|
150
200
|
request.params.update(params) if params
|
|
151
|
-
yield
|
|
152
|
-
|
|
201
|
+
yield request if block_given?
|
|
202
|
+
end
|
|
153
203
|
end
|
|
154
204
|
RUBY
|
|
155
205
|
end
|
|
156
206
|
|
|
157
|
-
#
|
|
207
|
+
# @overload options()
|
|
208
|
+
# Returns current Connection options.
|
|
158
209
|
#
|
|
159
|
-
# url
|
|
160
|
-
#
|
|
161
|
-
#
|
|
162
|
-
#
|
|
210
|
+
# @overload options(url, params = nil, headers = nil)
|
|
211
|
+
# Makes an OPTIONS HTTP request to the given URL.
|
|
212
|
+
# @param url [String] String base URL to sue as a prefix for all requests.
|
|
213
|
+
# @param params [Hash] Hash of URI query unencoded key/value pairs.
|
|
214
|
+
# @param headers [Hash] unencoded HTTP header key/value pairs.
|
|
163
215
|
#
|
|
164
|
-
#
|
|
216
|
+
# @example
|
|
217
|
+
# conn.options '/items/1'
|
|
165
218
|
#
|
|
166
|
-
#
|
|
219
|
+
# @yield [Faraday::Request] for further request customizations
|
|
220
|
+
# @return [Faraday::Response]
|
|
221
|
+
def options(*args)
|
|
222
|
+
return @options if args.size.zero?
|
|
223
|
+
|
|
224
|
+
url, params, headers = *args
|
|
225
|
+
run_request(:options, url, nil, headers) do |request|
|
|
226
|
+
request.params.update(params) if params
|
|
227
|
+
yield request if block_given?
|
|
228
|
+
end
|
|
229
|
+
end
|
|
230
|
+
|
|
231
|
+
# @!method post(url = nil, body = nil, headers = nil)
|
|
232
|
+
# Makes a POST HTTP request with a body.
|
|
233
|
+
# @!scope class
|
|
234
|
+
#
|
|
235
|
+
# @param url [String] The optional String base URL to use as a prefix for
|
|
236
|
+
# all requests. Can also be the options Hash.
|
|
237
|
+
# @param body [String] body for the request.
|
|
238
|
+
# @param headers [Hash] unencoded HTTP header key/value pairs.
|
|
239
|
+
#
|
|
240
|
+
# @example
|
|
241
|
+
# conn.post '/items', data, content_type: 'application/json'
|
|
167
242
|
#
|
|
168
243
|
# # Simple ElasticSearch indexing sample.
|
|
169
244
|
# conn.post '/twitter/tweet' do |req|
|
|
170
245
|
# req.headers[:content_type] = 'application/json'
|
|
171
246
|
# req.params[:routing] = 'kimchy'
|
|
172
|
-
# req.body = JSON.generate(:
|
|
247
|
+
# req.body = JSON.generate(user: 'kimchy', ...)
|
|
173
248
|
# end
|
|
174
249
|
#
|
|
175
|
-
#
|
|
176
|
-
#
|
|
250
|
+
# @yield [Faraday::Request] for further request customizations
|
|
251
|
+
# @return [Faraday::Response]
|
|
252
|
+
|
|
253
|
+
# @!method put(url = nil, body = nil, headers = nil)
|
|
254
|
+
# Makes a PUT HTTP request with a body.
|
|
255
|
+
# @!scope class
|
|
256
|
+
#
|
|
257
|
+
# @param url [String] The optional String base URL to use as a prefix for
|
|
258
|
+
# all requests. Can also be the options Hash.
|
|
259
|
+
# @param body [String] body for the request.
|
|
260
|
+
# @param headers [Hash] unencoded HTTP header key/value pairs.
|
|
177
261
|
#
|
|
178
|
-
#
|
|
262
|
+
# @example
|
|
263
|
+
# # TODO: Make it a PUT example
|
|
264
|
+
# conn.post '/items', data, content_type: 'application/json'
|
|
179
265
|
#
|
|
180
|
-
#
|
|
266
|
+
# # Simple ElasticSearch indexing sample.
|
|
267
|
+
# conn.post '/twitter/tweet' do |req|
|
|
268
|
+
# req.headers[:content_type] = 'application/json'
|
|
269
|
+
# req.params[:routing] = 'kimchy'
|
|
270
|
+
# req.body = JSON.generate(user: 'kimchy', ...)
|
|
271
|
+
# end
|
|
181
272
|
#
|
|
182
|
-
#
|
|
183
|
-
|
|
273
|
+
# @yield [Faraday::Request] for further request customizations
|
|
274
|
+
# @return [Faraday::Response]
|
|
275
|
+
|
|
276
|
+
# @!visibility private
|
|
277
|
+
METHODS_WITH_BODY.each do |method|
|
|
184
278
|
class_eval <<-RUBY, __FILE__, __LINE__ + 1
|
|
185
279
|
def #{method}(url = nil, body = nil, headers = nil, &block)
|
|
186
280
|
run_request(:#{method}, url, body, headers, &block)
|
|
@@ -188,123 +282,126 @@ module Faraday
|
|
|
188
282
|
RUBY
|
|
189
283
|
end
|
|
190
284
|
|
|
191
|
-
#
|
|
285
|
+
# Sets up the Authorization header with these credentials, encoded
|
|
192
286
|
# with base64.
|
|
193
287
|
#
|
|
194
|
-
# login
|
|
195
|
-
# pass
|
|
288
|
+
# @param login [String] The authentication login.
|
|
289
|
+
# @param pass [String] The authentication password.
|
|
196
290
|
#
|
|
197
|
-
#
|
|
291
|
+
# @example
|
|
198
292
|
#
|
|
199
293
|
# conn.basic_auth 'Aladdin', 'open sesame'
|
|
200
294
|
# conn.headers['Authorization']
|
|
201
295
|
# # => "Basic QWxhZGRpbjpvcGVuIHNlc2FtZQ=="
|
|
202
296
|
#
|
|
203
|
-
#
|
|
297
|
+
# @return [void]
|
|
204
298
|
def basic_auth(login, pass)
|
|
205
299
|
set_authorization_header(:basic_auth, login, pass)
|
|
206
300
|
end
|
|
207
301
|
|
|
208
|
-
#
|
|
302
|
+
# Sets up the Authorization header with the given token.
|
|
209
303
|
#
|
|
210
|
-
# token
|
|
211
|
-
# options
|
|
304
|
+
# @param token [String]
|
|
305
|
+
# @param options [Hash] extra token options.
|
|
212
306
|
#
|
|
213
|
-
#
|
|
307
|
+
# @example
|
|
214
308
|
#
|
|
215
|
-
# conn.token_auth 'abcdef', :
|
|
309
|
+
# conn.token_auth 'abcdef', foo: 'bar'
|
|
216
310
|
# conn.headers['Authorization']
|
|
217
311
|
# # => "Token token=\"abcdef\",
|
|
218
312
|
# foo=\"bar\""
|
|
219
313
|
#
|
|
220
|
-
#
|
|
314
|
+
# @return [void]
|
|
221
315
|
def token_auth(token, options = nil)
|
|
222
316
|
set_authorization_header(:token_auth, token, options)
|
|
223
317
|
end
|
|
224
318
|
|
|
225
|
-
#
|
|
319
|
+
# Sets up a custom Authorization header.
|
|
226
320
|
#
|
|
227
|
-
# type
|
|
228
|
-
# token
|
|
229
|
-
# a Hash is encoded into comma
|
|
321
|
+
# @param type [String] authorization type
|
|
322
|
+
# @param token [String, Hash] token. A String value is taken literally, and
|
|
323
|
+
# a Hash is encoded into comma-separated key/value pairs.
|
|
230
324
|
#
|
|
231
|
-
#
|
|
325
|
+
# @example
|
|
232
326
|
#
|
|
233
327
|
# conn.authorization :Bearer, 'mF_9.B5f-4.1JqM'
|
|
234
328
|
# conn.headers['Authorization']
|
|
235
329
|
# # => "Bearer mF_9.B5f-4.1JqM"
|
|
236
330
|
#
|
|
237
|
-
# conn.authorization :Token, :
|
|
331
|
+
# conn.authorization :Token, token: 'abcdef', foo: 'bar'
|
|
238
332
|
# conn.headers['Authorization']
|
|
239
333
|
# # => "Token token=\"abcdef\",
|
|
240
334
|
# foo=\"bar\""
|
|
241
335
|
#
|
|
242
|
-
#
|
|
336
|
+
# @return [void]
|
|
243
337
|
def authorization(type, token)
|
|
244
338
|
set_authorization_header(:authorization, type, token)
|
|
245
339
|
end
|
|
246
340
|
|
|
247
|
-
#
|
|
248
|
-
# parallel-capable adapter.
|
|
341
|
+
# Check if the adapter is parallel-capable.
|
|
249
342
|
#
|
|
250
|
-
#
|
|
343
|
+
# @yield if the adapter isn't parallel-capable, or if no adapter is set yet.
|
|
251
344
|
#
|
|
252
|
-
#
|
|
345
|
+
# @return [Object, nil] a parallel manager or nil if yielded
|
|
346
|
+
# @api private
|
|
253
347
|
def default_parallel_manager
|
|
254
348
|
@default_parallel_manager ||= begin
|
|
255
|
-
|
|
256
|
-
h.klass.respond_to?(:supports_parallel?) and h.klass.supports_parallel?
|
|
257
|
-
end
|
|
349
|
+
adapter = @builder.adapter.klass if @builder.adapter
|
|
258
350
|
|
|
259
|
-
if
|
|
260
|
-
|
|
351
|
+
if support_parallel?(adapter)
|
|
352
|
+
adapter.setup_parallel_manager
|
|
261
353
|
elsif block_given?
|
|
262
354
|
yield
|
|
263
355
|
end
|
|
264
356
|
end
|
|
265
357
|
end
|
|
266
358
|
|
|
267
|
-
#
|
|
359
|
+
# Determine if this Faraday::Connection can make parallel requests.
|
|
268
360
|
#
|
|
269
|
-
#
|
|
361
|
+
# @return [Boolean]
|
|
270
362
|
def in_parallel?
|
|
271
363
|
!!@parallel_manager
|
|
272
364
|
end
|
|
273
365
|
|
|
274
|
-
#
|
|
366
|
+
# Sets up the parallel manager to make a set of requests.
|
|
275
367
|
#
|
|
276
|
-
# manager
|
|
368
|
+
# @param manager [Object] The parallel manager that this Connection's
|
|
369
|
+
# Adapter uses.
|
|
277
370
|
#
|
|
278
|
-
#
|
|
279
|
-
#
|
|
371
|
+
# @yield a block to execute multiple requests.
|
|
372
|
+
# @return [void]
|
|
280
373
|
def in_parallel(manager = nil)
|
|
281
|
-
@parallel_manager = manager || default_parallel_manager
|
|
282
|
-
warn
|
|
283
|
-
|
|
374
|
+
@parallel_manager = manager || default_parallel_manager do
|
|
375
|
+
warn 'Warning: `in_parallel` called but no parallel-capable adapter ' \
|
|
376
|
+
'on Faraday stack'
|
|
377
|
+
warn caller[2, 10].join("\n")
|
|
284
378
|
nil
|
|
285
|
-
|
|
379
|
+
end
|
|
286
380
|
yield
|
|
287
|
-
@parallel_manager
|
|
381
|
+
@parallel_manager&.run
|
|
288
382
|
ensure
|
|
289
383
|
@parallel_manager = nil
|
|
290
384
|
end
|
|
291
385
|
|
|
292
|
-
#
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
386
|
+
# Sets the Hash proxy options.
|
|
387
|
+
#
|
|
388
|
+
# @param new_value [Object]
|
|
389
|
+
def proxy=(new_value)
|
|
390
|
+
@manual_proxy = true
|
|
391
|
+
@proxy = new_value ? ProxyOptions.from(new_value) : nil
|
|
296
392
|
end
|
|
297
393
|
|
|
298
394
|
def_delegators :url_prefix, :scheme, :scheme=, :host, :host=, :port, :port=
|
|
299
395
|
def_delegator :url_prefix, :path, :path_prefix
|
|
300
396
|
|
|
301
|
-
#
|
|
302
|
-
# components in this connection.
|
|
397
|
+
# Parses the given URL with URI and stores the individual
|
|
398
|
+
# components in this connection. These components serve as defaults for
|
|
303
399
|
# requests made by this connection.
|
|
304
400
|
#
|
|
305
|
-
# url
|
|
401
|
+
# @param url [String, URI]
|
|
402
|
+
# @param encoder [Object]
|
|
306
403
|
#
|
|
307
|
-
#
|
|
404
|
+
# @example
|
|
308
405
|
#
|
|
309
406
|
# conn = Faraday::Connection.new { ... }
|
|
310
407
|
# conn.url_prefix = "https://sushi.com/api"
|
|
@@ -312,8 +409,6 @@ module Faraday
|
|
|
312
409
|
# conn.path_prefix # => "/api"
|
|
313
410
|
#
|
|
314
411
|
# conn.get("nigiri?page=2") # accesses https://sushi.com/api/nigiri
|
|
315
|
-
#
|
|
316
|
-
# Returns the parsed URI from teh given input..
|
|
317
412
|
def url_prefix=(url, encoder = nil)
|
|
318
413
|
uri = @url_prefix = Utils.URI(url)
|
|
319
414
|
self.path_prefix = uri.path
|
|
@@ -326,57 +421,71 @@ module Faraday
|
|
|
326
421
|
uri.user = uri.password = nil
|
|
327
422
|
end
|
|
328
423
|
|
|
329
|
-
|
|
424
|
+
@proxy = proxy_from_env(url) unless @manual_proxy
|
|
330
425
|
end
|
|
331
426
|
|
|
332
|
-
#
|
|
427
|
+
# Sets the path prefix and ensures that it always has a leading
|
|
333
428
|
# slash.
|
|
334
429
|
#
|
|
335
|
-
# value
|
|
430
|
+
# @param value [String]
|
|
336
431
|
#
|
|
337
|
-
#
|
|
432
|
+
# @return [String] the new path prefix
|
|
338
433
|
def path_prefix=(value)
|
|
339
434
|
url_prefix.path = if value
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
435
|
+
value = "/#{value}" unless value[0, 1] == '/'
|
|
436
|
+
value
|
|
437
|
+
end
|
|
343
438
|
end
|
|
344
439
|
|
|
345
|
-
#
|
|
440
|
+
# Takes a relative url for a request and combines it with the defaults
|
|
346
441
|
# set on the connection instance.
|
|
347
442
|
#
|
|
443
|
+
# @param url [String]
|
|
444
|
+
# @param extra_params [Hash]
|
|
445
|
+
#
|
|
446
|
+
# @example
|
|
348
447
|
# conn = Faraday::Connection.new { ... }
|
|
349
448
|
# conn.url_prefix = "https://sushi.com/api?token=abc"
|
|
350
449
|
# conn.scheme # => https
|
|
351
450
|
# conn.path_prefix # => "/api"
|
|
352
451
|
#
|
|
353
|
-
# conn.build_url("nigiri?page=2")
|
|
354
|
-
#
|
|
452
|
+
# conn.build_url("nigiri?page=2")
|
|
453
|
+
# # => https://sushi.com/api/nigiri?token=abc&page=2
|
|
454
|
+
#
|
|
455
|
+
# conn.build_url("nigiri", page: 2)
|
|
456
|
+
# # => https://sushi.com/api/nigiri?token=abc&page=2
|
|
355
457
|
#
|
|
356
458
|
def build_url(url = nil, extra_params = nil)
|
|
357
459
|
uri = build_exclusive_url(url)
|
|
358
460
|
|
|
359
461
|
query_values = params.dup.merge_query(uri.query, options.params_encoder)
|
|
360
|
-
query_values.update
|
|
361
|
-
uri.query =
|
|
462
|
+
query_values.update(extra_params) if extra_params
|
|
463
|
+
uri.query =
|
|
464
|
+
if query_values.empty?
|
|
465
|
+
nil
|
|
466
|
+
else
|
|
467
|
+
query_values.to_query(options.params_encoder)
|
|
468
|
+
end
|
|
362
469
|
|
|
363
470
|
uri
|
|
364
471
|
end
|
|
365
472
|
|
|
366
473
|
# Builds and runs the Faraday::Request.
|
|
367
474
|
#
|
|
368
|
-
# method
|
|
369
|
-
# url
|
|
370
|
-
# body
|
|
371
|
-
#
|
|
475
|
+
# @param method [Symbol] HTTP method.
|
|
476
|
+
# @param url [String, URI] String or URI to access.
|
|
477
|
+
# @param body [Object] The request body that will eventually be converted to
|
|
478
|
+
# a string.
|
|
479
|
+
# @param headers [Hash] unencoded HTTP header key/value pairs.
|
|
372
480
|
#
|
|
373
|
-
#
|
|
481
|
+
# @return [Faraday::Response]
|
|
374
482
|
def run_request(method, url, body, headers)
|
|
375
|
-
|
|
483
|
+
unless METHODS.include?(method)
|
|
376
484
|
raise ArgumentError, "unknown http method: #{method}"
|
|
377
485
|
end
|
|
378
486
|
|
|
379
487
|
request = build_request(method) do |req|
|
|
488
|
+
req.options.proxy = proxy_for_request(url)
|
|
380
489
|
req.url(url) if url
|
|
381
490
|
req.headers.update(headers) if headers
|
|
382
491
|
req.body = body if body
|
|
@@ -388,68 +497,125 @@ module Faraday
|
|
|
388
497
|
|
|
389
498
|
# Creates and configures the request object.
|
|
390
499
|
#
|
|
391
|
-
#
|
|
500
|
+
# @param method [Symbol]
|
|
501
|
+
#
|
|
502
|
+
# @yield [Faraday::Request] if block given
|
|
503
|
+
# @return [Faraday::Request]
|
|
392
504
|
def build_request(method)
|
|
393
505
|
Request.create(method) do |req|
|
|
394
|
-
req.params =
|
|
395
|
-
req.headers =
|
|
396
|
-
req.options =
|
|
506
|
+
req.params = params.dup
|
|
507
|
+
req.headers = headers.dup
|
|
508
|
+
req.options = options.dup
|
|
397
509
|
yield(req) if block_given?
|
|
398
510
|
end
|
|
399
511
|
end
|
|
400
512
|
|
|
401
|
-
#
|
|
513
|
+
# Build an absolute URL based on url_prefix.
|
|
402
514
|
#
|
|
403
|
-
# url
|
|
404
|
-
# params
|
|
515
|
+
# @param url [String, URI]
|
|
516
|
+
# @param params [Faraday::Utils::ParamsHash] A Faraday::Utils::ParamsHash to
|
|
517
|
+
# replace the query values
|
|
405
518
|
# of the resulting url (default: nil).
|
|
406
519
|
#
|
|
407
|
-
#
|
|
520
|
+
# @return [URI]
|
|
408
521
|
def build_exclusive_url(url = nil, params = nil, params_encoder = nil)
|
|
409
|
-
url = nil if url.respond_to?(:empty?)
|
|
410
|
-
base = url_prefix
|
|
411
|
-
if url
|
|
412
|
-
base = base.
|
|
413
|
-
base.path = base.path + '/' # ensure trailing slash
|
|
522
|
+
url = nil if url.respond_to?(:empty?) && url.empty?
|
|
523
|
+
base = url_prefix.dup
|
|
524
|
+
if url && base.path && base.path !~ %r{/$}
|
|
525
|
+
base.path = "#{base.path}/" # ensure trailing slash
|
|
414
526
|
end
|
|
527
|
+
url = url && URI.parse(url.to_s).opaque ? url.to_s.gsub(':', '%3A') : url
|
|
415
528
|
uri = url ? base + url : base
|
|
416
|
-
|
|
417
|
-
|
|
529
|
+
if params
|
|
530
|
+
uri.query = params.to_query(params_encoder || options.params_encoder)
|
|
531
|
+
end
|
|
532
|
+
# rubocop:disable Style/SafeNavigation
|
|
533
|
+
uri.query = nil if uri.query && uri.query.empty?
|
|
534
|
+
# rubocop:enable Style/SafeNavigation
|
|
418
535
|
uri
|
|
419
536
|
end
|
|
420
537
|
|
|
421
|
-
#
|
|
538
|
+
# Creates a duplicate of this Faraday::Connection.
|
|
422
539
|
#
|
|
423
|
-
#
|
|
540
|
+
# @api private
|
|
541
|
+
#
|
|
542
|
+
# @return [Faraday::Connection]
|
|
424
543
|
def dup
|
|
425
544
|
self.class.new(build_exclusive_url,
|
|
426
|
-
:
|
|
427
|
-
:
|
|
428
|
-
:
|
|
429
|
-
:
|
|
430
|
-
:
|
|
545
|
+
headers: headers.dup,
|
|
546
|
+
params: params.dup,
|
|
547
|
+
builder: builder.dup,
|
|
548
|
+
ssl: ssl.dup,
|
|
549
|
+
request: options.dup)
|
|
431
550
|
end
|
|
432
551
|
|
|
433
|
-
#
|
|
552
|
+
# Yields username and password extracted from a URI if they both exist.
|
|
553
|
+
#
|
|
554
|
+
# @param uri [URI]
|
|
555
|
+
# @yield [username, password] any username and password
|
|
556
|
+
# @yieldparam username [String] any username from URI
|
|
557
|
+
# @yieldparam password [String] any password from URI
|
|
558
|
+
# @return [void]
|
|
559
|
+
# @api private
|
|
434
560
|
def with_uri_credentials(uri)
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
561
|
+
return unless uri.user && uri.password
|
|
562
|
+
|
|
563
|
+
yield(Utils.unescape(uri.user), Utils.unescape(uri.password))
|
|
438
564
|
end
|
|
439
565
|
|
|
440
566
|
def set_authorization_header(header_type, *args)
|
|
441
|
-
header = Faraday::Request
|
|
442
|
-
|
|
567
|
+
header = Faraday::Request
|
|
568
|
+
.lookup_middleware(header_type)
|
|
569
|
+
.header(*args)
|
|
570
|
+
|
|
443
571
|
headers[Faraday::Request::Authorization::KEY] = header
|
|
444
572
|
end
|
|
445
573
|
|
|
574
|
+
def proxy_from_env(url)
|
|
575
|
+
return if Faraday.ignore_env_proxy
|
|
576
|
+
|
|
577
|
+
uri = nil
|
|
578
|
+
if URI.parse('').respond_to?(:find_proxy)
|
|
579
|
+
case url
|
|
580
|
+
when String
|
|
581
|
+
uri = Utils.URI(url)
|
|
582
|
+
uri = if uri.host.nil?
|
|
583
|
+
find_default_proxy
|
|
584
|
+
else
|
|
585
|
+
URI.parse("#{uri.scheme}://#{uri.host}").find_proxy
|
|
586
|
+
end
|
|
587
|
+
when URI
|
|
588
|
+
uri = url.find_proxy
|
|
589
|
+
when nil
|
|
590
|
+
uri = find_default_proxy
|
|
591
|
+
end
|
|
592
|
+
else
|
|
593
|
+
warn 'no_proxy is unsupported' if ENV['no_proxy'] || ENV['NO_PROXY']
|
|
594
|
+
uri = find_default_proxy
|
|
595
|
+
end
|
|
596
|
+
ProxyOptions.from(uri) if uri
|
|
597
|
+
end
|
|
598
|
+
|
|
446
599
|
def find_default_proxy
|
|
447
|
-
warn 'no_proxy is unsupported' if ENV['no_proxy'] || ENV['NO_PROXY']
|
|
448
600
|
uri = ENV['http_proxy']
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
601
|
+
return unless uri && !uri.empty?
|
|
602
|
+
|
|
603
|
+
uri = "http://#{uri}" unless uri.match?(/^http/i)
|
|
604
|
+
uri
|
|
605
|
+
end
|
|
606
|
+
|
|
607
|
+
def proxy_for_request(url)
|
|
608
|
+
return proxy if @manual_proxy
|
|
609
|
+
|
|
610
|
+
if url && Utils.URI(url).absolute?
|
|
611
|
+
proxy_from_env(url)
|
|
612
|
+
else
|
|
613
|
+
proxy
|
|
452
614
|
end
|
|
453
615
|
end
|
|
616
|
+
|
|
617
|
+
def support_parallel?(adapter)
|
|
618
|
+
adapter&.respond_to?(:supports_parallel?) && adapter&.supports_parallel?
|
|
619
|
+
end
|
|
454
620
|
end
|
|
455
621
|
end
|