httparty 0.19.0 → 0.24.0
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 +4 -4
- data/.github/dependabot.yml +6 -0
- data/.github/workflows/ci.yml +10 -14
- data/.gitignore +2 -1
- data/Changelog.md +399 -311
- data/Gemfile +3 -0
- data/Guardfile +3 -2
- data/README.md +17 -17
- data/docs/README.md +27 -5
- data/examples/party_foul_mode.rb +90 -0
- data/httparty.gemspec +4 -2
- data/lib/httparty/connection_adapter.rb +6 -25
- data/lib/httparty/decompressor.rb +11 -1
- data/lib/httparty/exceptions.rb +34 -3
- data/lib/httparty/hash_conversions.rb +1 -1
- data/lib/httparty/logger/curl_formatter.rb +1 -1
- data/lib/httparty/logger/logstash_formatter.rb +1 -0
- data/lib/httparty/module_inheritable_attributes.rb +3 -5
- data/lib/httparty/parser.rb +3 -0
- data/lib/httparty/request/body.rb +40 -13
- data/lib/httparty/request/streaming_multipart_body.rb +188 -0
- data/lib/httparty/request.rb +98 -34
- data/lib/httparty/response.rb +3 -3
- data/lib/httparty/text_encoder.rb +1 -1
- data/lib/httparty/version.rb +1 -1
- data/lib/httparty.rb +23 -11
- data/script/release +4 -4
- metadata +30 -13
- data/.simplecov +0 -1
|
@@ -0,0 +1,188 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module HTTParty
|
|
4
|
+
class Request
|
|
5
|
+
class StreamingMultipartBody
|
|
6
|
+
NEWLINE = "\r\n"
|
|
7
|
+
CHUNK_SIZE = 64 * 1024 # 64 KB chunks
|
|
8
|
+
|
|
9
|
+
def initialize(parts, boundary)
|
|
10
|
+
@parts = parts
|
|
11
|
+
@boundary = boundary
|
|
12
|
+
@part_index = 0
|
|
13
|
+
@state = :header
|
|
14
|
+
@current_file = nil
|
|
15
|
+
@header_buffer = nil
|
|
16
|
+
@header_offset = 0
|
|
17
|
+
@footer_sent = false
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
def size
|
|
21
|
+
@size ||= calculate_size
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
def read(length = nil, outbuf = nil)
|
|
25
|
+
outbuf = outbuf ? outbuf.replace(''.b) : ''.b
|
|
26
|
+
|
|
27
|
+
return read_all(outbuf) if length.nil?
|
|
28
|
+
|
|
29
|
+
while outbuf.bytesize < length
|
|
30
|
+
chunk = read_chunk(length - outbuf.bytesize)
|
|
31
|
+
break if chunk.nil?
|
|
32
|
+
outbuf << chunk
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
outbuf.empty? ? nil : outbuf
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
def rewind
|
|
39
|
+
@part_index = 0
|
|
40
|
+
@state = :header
|
|
41
|
+
@current_file = nil
|
|
42
|
+
@header_buffer = nil
|
|
43
|
+
@header_offset = 0
|
|
44
|
+
@footer_sent = false
|
|
45
|
+
@parts.each do |_key, value, _is_file|
|
|
46
|
+
value.rewind if value.respond_to?(:rewind)
|
|
47
|
+
end
|
|
48
|
+
end
|
|
49
|
+
|
|
50
|
+
private
|
|
51
|
+
|
|
52
|
+
def read_all(outbuf)
|
|
53
|
+
while (chunk = read_chunk(CHUNK_SIZE))
|
|
54
|
+
outbuf << chunk
|
|
55
|
+
end
|
|
56
|
+
outbuf.empty? ? nil : outbuf
|
|
57
|
+
end
|
|
58
|
+
|
|
59
|
+
def read_chunk(max_length)
|
|
60
|
+
loop do
|
|
61
|
+
return nil if @part_index >= @parts.size && @footer_sent
|
|
62
|
+
|
|
63
|
+
if @part_index >= @parts.size
|
|
64
|
+
@footer_sent = true
|
|
65
|
+
return "--#{@boundary}--#{NEWLINE}".b
|
|
66
|
+
end
|
|
67
|
+
|
|
68
|
+
key, value, is_file = @parts[@part_index]
|
|
69
|
+
|
|
70
|
+
case @state
|
|
71
|
+
when :header
|
|
72
|
+
chunk = read_header_chunk(key, value, is_file, max_length)
|
|
73
|
+
return chunk if chunk
|
|
74
|
+
|
|
75
|
+
when :body
|
|
76
|
+
chunk = read_body_chunk(value, is_file, max_length)
|
|
77
|
+
return chunk if chunk
|
|
78
|
+
|
|
79
|
+
when :newline
|
|
80
|
+
@state = :header
|
|
81
|
+
@part_index += 1
|
|
82
|
+
return NEWLINE.b
|
|
83
|
+
end
|
|
84
|
+
end
|
|
85
|
+
end
|
|
86
|
+
|
|
87
|
+
def read_header_chunk(key, value, is_file, max_length)
|
|
88
|
+
if @header_buffer.nil?
|
|
89
|
+
@header_buffer = build_part_header(key, value, is_file)
|
|
90
|
+
@header_offset = 0
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
remaining = @header_buffer.bytesize - @header_offset
|
|
94
|
+
if remaining > 0
|
|
95
|
+
chunk_size = [remaining, max_length].min
|
|
96
|
+
chunk = @header_buffer.byteslice(@header_offset, chunk_size)
|
|
97
|
+
@header_offset += chunk_size
|
|
98
|
+
return chunk
|
|
99
|
+
end
|
|
100
|
+
|
|
101
|
+
@header_buffer = nil
|
|
102
|
+
@header_offset = 0
|
|
103
|
+
@state = :body
|
|
104
|
+
nil
|
|
105
|
+
end
|
|
106
|
+
|
|
107
|
+
def read_body_chunk(value, is_file, max_length)
|
|
108
|
+
if is_file
|
|
109
|
+
chunk = read_file_chunk(value, max_length)
|
|
110
|
+
if chunk
|
|
111
|
+
return chunk
|
|
112
|
+
else
|
|
113
|
+
@current_file = nil
|
|
114
|
+
@state = :newline
|
|
115
|
+
return nil
|
|
116
|
+
end
|
|
117
|
+
else
|
|
118
|
+
@state = :newline
|
|
119
|
+
return value.to_s.b
|
|
120
|
+
end
|
|
121
|
+
end
|
|
122
|
+
|
|
123
|
+
def read_file_chunk(file, max_length)
|
|
124
|
+
chunk_size = [max_length, CHUNK_SIZE].min
|
|
125
|
+
chunk = file.read(chunk_size)
|
|
126
|
+
return nil if chunk.nil?
|
|
127
|
+
chunk.force_encoding(Encoding::BINARY) if chunk.respond_to?(:force_encoding)
|
|
128
|
+
chunk
|
|
129
|
+
end
|
|
130
|
+
|
|
131
|
+
def build_part_header(key, value, is_file)
|
|
132
|
+
header = "--#{@boundary}#{NEWLINE}".b
|
|
133
|
+
header << %(Content-Disposition: form-data; name="#{key}").b
|
|
134
|
+
if is_file
|
|
135
|
+
header << %(; filename="#{file_name(value).gsub(/["\r\n]/, replacement_table)}").b
|
|
136
|
+
header << NEWLINE.b
|
|
137
|
+
header << "Content-Type: #{content_type(value)}#{NEWLINE}".b
|
|
138
|
+
end
|
|
139
|
+
header << NEWLINE.b
|
|
140
|
+
header
|
|
141
|
+
end
|
|
142
|
+
|
|
143
|
+
def calculate_size
|
|
144
|
+
total = 0
|
|
145
|
+
@parts.each do |key, value, is_file|
|
|
146
|
+
total += build_part_header(key, value, is_file).bytesize
|
|
147
|
+
total += content_size(value, is_file)
|
|
148
|
+
total += NEWLINE.bytesize
|
|
149
|
+
end
|
|
150
|
+
total += "--#{@boundary}--#{NEWLINE}".bytesize
|
|
151
|
+
total
|
|
152
|
+
end
|
|
153
|
+
|
|
154
|
+
def content_size(value, is_file)
|
|
155
|
+
if is_file
|
|
156
|
+
if value.respond_to?(:size)
|
|
157
|
+
value.size
|
|
158
|
+
elsif value.respond_to?(:stat)
|
|
159
|
+
value.stat.size
|
|
160
|
+
else
|
|
161
|
+
value.read.bytesize.tap { value.rewind }
|
|
162
|
+
end
|
|
163
|
+
else
|
|
164
|
+
value.to_s.b.bytesize
|
|
165
|
+
end
|
|
166
|
+
end
|
|
167
|
+
|
|
168
|
+
def content_type(object)
|
|
169
|
+
return object.content_type if object.respond_to?(:content_type)
|
|
170
|
+
require 'mini_mime'
|
|
171
|
+
mime = MiniMime.lookup_by_filename(object.path)
|
|
172
|
+
mime ? mime.content_type : 'application/octet-stream'
|
|
173
|
+
end
|
|
174
|
+
|
|
175
|
+
def file_name(object)
|
|
176
|
+
object.respond_to?(:original_filename) ? object.original_filename : File.basename(object.path)
|
|
177
|
+
end
|
|
178
|
+
|
|
179
|
+
def replacement_table
|
|
180
|
+
@replacement_table ||= {
|
|
181
|
+
'"' => '%22',
|
|
182
|
+
"\r" => '%0D',
|
|
183
|
+
"\n" => '%0A'
|
|
184
|
+
}.freeze
|
|
185
|
+
end
|
|
186
|
+
end
|
|
187
|
+
end
|
|
188
|
+
end
|
data/lib/httparty/request.rb
CHANGED
|
@@ -46,6 +46,15 @@ module HTTParty
|
|
|
46
46
|
end.flatten.join('&')
|
|
47
47
|
end
|
|
48
48
|
|
|
49
|
+
def self._load(data)
|
|
50
|
+
http_method, path, options, last_response, last_uri, raw_request = Marshal.load(data)
|
|
51
|
+
instance = new(http_method, path, options)
|
|
52
|
+
instance.last_response = last_response
|
|
53
|
+
instance.last_uri = last_uri
|
|
54
|
+
instance.instance_variable_set("@raw_request", raw_request)
|
|
55
|
+
instance
|
|
56
|
+
end
|
|
57
|
+
|
|
49
58
|
attr_accessor :http_method, :options, :last_response, :redirect, :last_uri
|
|
50
59
|
attr_reader :path
|
|
51
60
|
|
|
@@ -104,6 +113,8 @@ module HTTParty
|
|
|
104
113
|
new_uri = path.clone
|
|
105
114
|
end
|
|
106
115
|
|
|
116
|
+
validate_uri_safety!(new_uri) unless redirect
|
|
117
|
+
|
|
107
118
|
# avoid double query string on redirects [#12]
|
|
108
119
|
unless redirect
|
|
109
120
|
new_uri.query = query_string(new_uri)
|
|
@@ -144,24 +155,28 @@ module HTTParty
|
|
|
144
155
|
chunked_body = nil
|
|
145
156
|
current_http = http
|
|
146
157
|
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
158
|
+
begin
|
|
159
|
+
self.last_response = current_http.request(@raw_request) do |http_response|
|
|
160
|
+
if block
|
|
161
|
+
chunks = []
|
|
150
162
|
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
163
|
+
http_response.read_body do |fragment|
|
|
164
|
+
encoded_fragment = encode_text(fragment, http_response['content-type'])
|
|
165
|
+
chunks << encoded_fragment if !options[:stream_body]
|
|
166
|
+
block.call ResponseFragment.new(encoded_fragment, http_response, current_http)
|
|
167
|
+
end
|
|
156
168
|
|
|
157
|
-
|
|
169
|
+
chunked_body = chunks.join
|
|
170
|
+
end
|
|
158
171
|
end
|
|
159
|
-
end
|
|
160
172
|
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
173
|
+
handle_host_redirection if response_redirects?
|
|
174
|
+
result = handle_unauthorized
|
|
175
|
+
result ||= handle_response(chunked_body, &block)
|
|
176
|
+
result
|
|
177
|
+
rescue *COMMON_NETWORK_ERRORS => e
|
|
178
|
+
raise options[:foul] ? HTTParty::NetworkError.new("#{e.class}: #{e.message}") : e
|
|
179
|
+
end
|
|
165
180
|
end
|
|
166
181
|
|
|
167
182
|
def handle_unauthorized(&block)
|
|
@@ -175,6 +190,13 @@ module HTTParty
|
|
|
175
190
|
@raw_request.body
|
|
176
191
|
end
|
|
177
192
|
|
|
193
|
+
def _dump(_level)
|
|
194
|
+
opts = options.dup
|
|
195
|
+
opts.delete(:logger)
|
|
196
|
+
opts.delete(:parser) if opts[:parser] && opts[:parser].is_a?(Proc)
|
|
197
|
+
Marshal.dump([http_method, path, opts, last_response, @last_uri, @raw_request])
|
|
198
|
+
end
|
|
199
|
+
|
|
178
200
|
private
|
|
179
201
|
|
|
180
202
|
def http
|
|
@@ -225,8 +247,17 @@ module HTTParty
|
|
|
225
247
|
if body.multipart?
|
|
226
248
|
content_type = "multipart/form-data; boundary=#{body.boundary}"
|
|
227
249
|
@raw_request['Content-Type'] = content_type
|
|
250
|
+
elsif options[:body].respond_to?(:to_hash) && !@raw_request['Content-Type']
|
|
251
|
+
@raw_request['Content-Type'] = 'application/x-www-form-urlencoded'
|
|
252
|
+
end
|
|
253
|
+
|
|
254
|
+
if body.streaming? && options[:stream_body] != false
|
|
255
|
+
stream = body.to_stream
|
|
256
|
+
@raw_request.body_stream = stream
|
|
257
|
+
@raw_request['Content-Length'] = stream.size.to_s
|
|
258
|
+
else
|
|
259
|
+
@raw_request.body = body.call
|
|
228
260
|
end
|
|
229
|
-
@raw_request.body = body.call
|
|
230
261
|
end
|
|
231
262
|
|
|
232
263
|
@raw_request.instance_variable_set(:@decode_content, decompress_content?)
|
|
@@ -279,24 +310,7 @@ module HTTParty
|
|
|
279
310
|
|
|
280
311
|
def handle_response(raw_body, &block)
|
|
281
312
|
if response_redirects?
|
|
282
|
-
|
|
283
|
-
if options[:logger]
|
|
284
|
-
logger = HTTParty::Logger.build(options[:logger], options[:log_level], options[:log_format])
|
|
285
|
-
logger.format(self, last_response)
|
|
286
|
-
end
|
|
287
|
-
self.path = last_response['location']
|
|
288
|
-
self.redirect = true
|
|
289
|
-
if last_response.class == Net::HTTPSeeOther
|
|
290
|
-
unless options[:maintain_method_across_redirects] && options[:resend_on_redirect]
|
|
291
|
-
self.http_method = Net::HTTP::Get
|
|
292
|
-
end
|
|
293
|
-
elsif last_response.code != '307' && last_response.code != '308'
|
|
294
|
-
unless options[:maintain_method_across_redirects]
|
|
295
|
-
self.http_method = Net::HTTP::Get
|
|
296
|
-
end
|
|
297
|
-
end
|
|
298
|
-
capture_cookies(last_response)
|
|
299
|
-
perform(&block)
|
|
313
|
+
handle_redirection(&block)
|
|
300
314
|
else
|
|
301
315
|
raw_body ||= last_response.body
|
|
302
316
|
|
|
@@ -315,10 +329,34 @@ module HTTParty
|
|
|
315
329
|
end
|
|
316
330
|
end
|
|
317
331
|
|
|
332
|
+
def handle_redirection(&block)
|
|
333
|
+
options[:limit] -= 1
|
|
334
|
+
if options[:logger]
|
|
335
|
+
logger = HTTParty::Logger.build(options[:logger], options[:log_level], options[:log_format])
|
|
336
|
+
logger.format(self, last_response)
|
|
337
|
+
end
|
|
338
|
+
self.path = last_response['location']
|
|
339
|
+
self.redirect = true
|
|
340
|
+
if last_response.class == Net::HTTPSeeOther
|
|
341
|
+
unless options[:maintain_method_across_redirects] && options[:resend_on_redirect]
|
|
342
|
+
self.http_method = Net::HTTP::Get
|
|
343
|
+
end
|
|
344
|
+
elsif last_response.code != '307' && last_response.code != '308'
|
|
345
|
+
unless options[:maintain_method_across_redirects]
|
|
346
|
+
self.http_method = Net::HTTP::Get
|
|
347
|
+
end
|
|
348
|
+
end
|
|
349
|
+
if http_method == Net::HTTP::Get
|
|
350
|
+
clear_body
|
|
351
|
+
end
|
|
352
|
+
capture_cookies(last_response)
|
|
353
|
+
perform(&block)
|
|
354
|
+
end
|
|
355
|
+
|
|
318
356
|
def handle_host_redirection
|
|
319
357
|
check_duplicate_location_header
|
|
320
358
|
redirect_path = options[:uri_adapter].parse(last_response['location']).normalize
|
|
321
|
-
return if redirect_path.relative? || path.host == redirect_path.host
|
|
359
|
+
return if redirect_path.relative? || path.host == redirect_path.host || uri.host == redirect_path.host
|
|
322
360
|
@changed_hosts = true
|
|
323
361
|
end
|
|
324
362
|
|
|
@@ -346,6 +384,14 @@ module HTTParty
|
|
|
346
384
|
parser.call(body, format)
|
|
347
385
|
end
|
|
348
386
|
|
|
387
|
+
# Some Web Application Firewalls reject incoming GET requests that have a body
|
|
388
|
+
# if we redirect, and the resulting verb is GET then we will clear the body that
|
|
389
|
+
# may be left behind from the initiating request
|
|
390
|
+
def clear_body
|
|
391
|
+
options[:body] = nil
|
|
392
|
+
@raw_request.body = nil
|
|
393
|
+
end
|
|
394
|
+
|
|
349
395
|
def capture_cookies(response)
|
|
350
396
|
return unless response['Set-Cookie']
|
|
351
397
|
cookies_hash = HTTParty::CookieHash.new
|
|
@@ -398,5 +444,23 @@ module HTTParty
|
|
|
398
444
|
assume_utf16_is_big_endian: assume_utf16_is_big_endian
|
|
399
445
|
).call
|
|
400
446
|
end
|
|
447
|
+
|
|
448
|
+
def validate_uri_safety!(new_uri)
|
|
449
|
+
return if options[:skip_uri_validation]
|
|
450
|
+
|
|
451
|
+
configured_base_uri = options[:base_uri]
|
|
452
|
+
return unless configured_base_uri
|
|
453
|
+
|
|
454
|
+
normalized_base = options[:uri_adapter].parse(
|
|
455
|
+
HTTParty.normalize_base_uri(configured_base_uri)
|
|
456
|
+
)
|
|
457
|
+
|
|
458
|
+
return if new_uri.host == normalized_base.host
|
|
459
|
+
|
|
460
|
+
raise UnsafeURIError,
|
|
461
|
+
"Requested URI '#{new_uri}' has host '#{new_uri.host}' but the " \
|
|
462
|
+
"configured base_uri '#{normalized_base}' has host '#{normalized_base.host}'. " \
|
|
463
|
+
"This request could send credentials to an unintended server."
|
|
464
|
+
end
|
|
401
465
|
end
|
|
402
466
|
end
|
data/lib/httparty/response.rb
CHANGED
|
@@ -67,12 +67,12 @@ module HTTParty
|
|
|
67
67
|
end
|
|
68
68
|
|
|
69
69
|
# Support old multiple_choice? method from pre 2.0.0 era.
|
|
70
|
-
if ::
|
|
70
|
+
if ::RUBY_PLATFORM != 'java'
|
|
71
71
|
alias_method :multiple_choice?, :multiple_choices?
|
|
72
72
|
end
|
|
73
73
|
|
|
74
74
|
# Support old status codes method from pre 2.6.0 era.
|
|
75
|
-
if ::
|
|
75
|
+
if ::RUBY_PLATFORM != 'java'
|
|
76
76
|
alias_method :gateway_time_out?, :gateway_timeout?
|
|
77
77
|
alias_method :request_entity_too_large?, :payload_too_large?
|
|
78
78
|
alias_method :request_time_out?, :request_timeout?
|
|
@@ -133,7 +133,7 @@ module HTTParty
|
|
|
133
133
|
end
|
|
134
134
|
|
|
135
135
|
def throw_exception
|
|
136
|
-
if @request.options[:raise_on]
|
|
136
|
+
if @request.options[:raise_on].to_a.detect { |c| code.to_s.match(/#{c.to_s}/) }
|
|
137
137
|
::Kernel.raise ::HTTParty::ResponseError.new(@response), "Code #{code} - #{body}"
|
|
138
138
|
end
|
|
139
139
|
end
|
|
@@ -5,7 +5,7 @@ module HTTParty
|
|
|
5
5
|
attr_reader :text, :content_type, :assume_utf16_is_big_endian
|
|
6
6
|
|
|
7
7
|
def initialize(text, assume_utf16_is_big_endian: true, content_type: nil)
|
|
8
|
-
@text = text
|
|
8
|
+
@text = +text
|
|
9
9
|
@content_type = content_type
|
|
10
10
|
@assume_utf16_is_big_endian = assume_utf16_is_big_endian
|
|
11
11
|
end
|
data/lib/httparty/version.rb
CHANGED
data/lib/httparty.rb
CHANGED
|
@@ -2,13 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
require 'pathname'
|
|
4
4
|
require 'net/http'
|
|
5
|
-
require 'net/https'
|
|
6
5
|
require 'uri'
|
|
7
|
-
require 'zlib'
|
|
8
|
-
require 'multi_xml'
|
|
9
|
-
require 'mime/types'
|
|
10
|
-
require 'json'
|
|
11
|
-
require 'csv'
|
|
12
6
|
|
|
13
7
|
require 'httparty/module_inheritable_attributes'
|
|
14
8
|
require 'httparty/cookie_hash'
|
|
@@ -68,6 +62,16 @@ module HTTParty
|
|
|
68
62
|
# * :+ssl_ca_path+: see HTTParty::ClassMethods.ssl_ca_path.
|
|
69
63
|
|
|
70
64
|
module ClassMethods
|
|
65
|
+
# Turns on or off the foul option.
|
|
66
|
+
#
|
|
67
|
+
# class Foo
|
|
68
|
+
# include HTTParty
|
|
69
|
+
# foul true
|
|
70
|
+
# end
|
|
71
|
+
def foul(bool)
|
|
72
|
+
default_options[:foul] = bool
|
|
73
|
+
end
|
|
74
|
+
|
|
71
75
|
# Turns on logging
|
|
72
76
|
#
|
|
73
77
|
# class Foo
|
|
@@ -84,7 +88,7 @@ module HTTParty
|
|
|
84
88
|
#
|
|
85
89
|
# class Foo
|
|
86
90
|
# include HTTParty
|
|
87
|
-
# raise_on [404, 500]
|
|
91
|
+
# raise_on [404, 500, '5[0-9]*']
|
|
88
92
|
# end
|
|
89
93
|
def raise_on(codes = [])
|
|
90
94
|
default_options[:raise_on] = *codes
|
|
@@ -592,6 +596,13 @@ module HTTParty
|
|
|
592
596
|
perform_request Net::HTTP::Unlock, path, options, &block
|
|
593
597
|
end
|
|
594
598
|
|
|
599
|
+
def build_request(http_method, path, options = {})
|
|
600
|
+
options = ModuleInheritableAttributes.hash_deep_dup(default_options).merge(options)
|
|
601
|
+
HeadersProcessor.new(headers, options).call
|
|
602
|
+
process_cookies(options)
|
|
603
|
+
Request.new(http_method, path, options)
|
|
604
|
+
end
|
|
605
|
+
|
|
595
606
|
attr_reader :default_options
|
|
596
607
|
|
|
597
608
|
private
|
|
@@ -607,10 +618,7 @@ module HTTParty
|
|
|
607
618
|
end
|
|
608
619
|
|
|
609
620
|
def perform_request(http_method, path, options, &block) #:nodoc:
|
|
610
|
-
|
|
611
|
-
HeadersProcessor.new(headers, options).call
|
|
612
|
-
process_cookies(options)
|
|
613
|
-
Request.new(http_method, path, options).perform(&block)
|
|
621
|
+
build_request(http_method, path, options).perform(&block)
|
|
614
622
|
end
|
|
615
623
|
|
|
616
624
|
def process_cookies(options) #:nodoc:
|
|
@@ -677,6 +685,10 @@ module HTTParty
|
|
|
677
685
|
def self.options(*args, &block)
|
|
678
686
|
Basement.options(*args, &block)
|
|
679
687
|
end
|
|
688
|
+
|
|
689
|
+
def self.build_request(*args, &block)
|
|
690
|
+
Basement.build_request(*args, &block)
|
|
691
|
+
end
|
|
680
692
|
end
|
|
681
693
|
|
|
682
694
|
require 'httparty/hash_conversions'
|
data/script/release
CHANGED
|
@@ -18,9 +18,9 @@ gem_name=httparty
|
|
|
18
18
|
rm -rf $gem_name-*.gem
|
|
19
19
|
gem build -q $gem_name.gemspec
|
|
20
20
|
|
|
21
|
-
# Make sure we're on the
|
|
22
|
-
(git branch | grep -q '*
|
|
23
|
-
echo "Only release from the
|
|
21
|
+
# Make sure we're on the main branch.
|
|
22
|
+
(git branch | grep -q '* main') || {
|
|
23
|
+
echo "Only release from the main branch."
|
|
24
24
|
exit 1
|
|
25
25
|
}
|
|
26
26
|
|
|
@@ -39,4 +39,4 @@ git fetch -t origin
|
|
|
39
39
|
|
|
40
40
|
# Tag it and bag it.
|
|
41
41
|
gem push $gem_name-*.gem && git tag "$tag" &&
|
|
42
|
-
git push origin
|
|
42
|
+
git push origin main && git push origin "$tag"
|
metadata
CHANGED
|
@@ -1,16 +1,30 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: httparty
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.
|
|
4
|
+
version: 0.24.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- John Nunemaker
|
|
8
8
|
- Sandro Turriate
|
|
9
|
-
autorequire:
|
|
9
|
+
autorequire:
|
|
10
10
|
bindir: bin
|
|
11
11
|
cert_chain: []
|
|
12
|
-
date:
|
|
12
|
+
date: 2025-12-28 00:00:00.000000000 Z
|
|
13
13
|
dependencies:
|
|
14
|
+
- !ruby/object:Gem::Dependency
|
|
15
|
+
name: csv
|
|
16
|
+
requirement: !ruby/object:Gem::Requirement
|
|
17
|
+
requirements:
|
|
18
|
+
- - ">="
|
|
19
|
+
- !ruby/object:Gem::Version
|
|
20
|
+
version: '0'
|
|
21
|
+
type: :runtime
|
|
22
|
+
prerelease: false
|
|
23
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
24
|
+
requirements:
|
|
25
|
+
- - ">="
|
|
26
|
+
- !ruby/object:Gem::Version
|
|
27
|
+
version: '0'
|
|
14
28
|
- !ruby/object:Gem::Dependency
|
|
15
29
|
name: multi_xml
|
|
16
30
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -26,19 +40,19 @@ dependencies:
|
|
|
26
40
|
- !ruby/object:Gem::Version
|
|
27
41
|
version: 0.5.2
|
|
28
42
|
- !ruby/object:Gem::Dependency
|
|
29
|
-
name:
|
|
43
|
+
name: mini_mime
|
|
30
44
|
requirement: !ruby/object:Gem::Requirement
|
|
31
45
|
requirements:
|
|
32
|
-
- - "
|
|
46
|
+
- - ">="
|
|
33
47
|
- !ruby/object:Gem::Version
|
|
34
|
-
version:
|
|
48
|
+
version: 1.0.0
|
|
35
49
|
type: :runtime
|
|
36
50
|
prerelease: false
|
|
37
51
|
version_requirements: !ruby/object:Gem::Requirement
|
|
38
52
|
requirements:
|
|
39
|
-
- - "
|
|
53
|
+
- - ">="
|
|
40
54
|
- !ruby/object:Gem::Version
|
|
41
|
-
version:
|
|
55
|
+
version: 1.0.0
|
|
42
56
|
description: Makes http fun! Also, makes consuming restful web services dead easy.
|
|
43
57
|
email:
|
|
44
58
|
- nunemaker@gmail.com
|
|
@@ -48,11 +62,11 @@ extensions: []
|
|
|
48
62
|
extra_rdoc_files: []
|
|
49
63
|
files:
|
|
50
64
|
- ".editorconfig"
|
|
65
|
+
- ".github/dependabot.yml"
|
|
51
66
|
- ".github/workflows/ci.yml"
|
|
52
67
|
- ".gitignore"
|
|
53
68
|
- ".rubocop.yml"
|
|
54
69
|
- ".rubocop_todo.yml"
|
|
55
|
-
- ".simplecov"
|
|
56
70
|
- CONTRIBUTING.md
|
|
57
71
|
- Changelog.md
|
|
58
72
|
- Gemfile
|
|
@@ -77,6 +91,7 @@ files:
|
|
|
77
91
|
- examples/microsoft_graph.rb
|
|
78
92
|
- examples/multipart.rb
|
|
79
93
|
- examples/nokogiri_html_parser.rb
|
|
94
|
+
- examples/party_foul_mode.rb
|
|
80
95
|
- examples/peer_cert.rb
|
|
81
96
|
- examples/rescue_json.rb
|
|
82
97
|
- examples/rubyurl.rb
|
|
@@ -103,6 +118,7 @@ files:
|
|
|
103
118
|
- lib/httparty/request.rb
|
|
104
119
|
- lib/httparty/request/body.rb
|
|
105
120
|
- lib/httparty/request/multipart_boundary.rb
|
|
121
|
+
- lib/httparty/request/streaming_multipart_body.rb
|
|
106
122
|
- lib/httparty/response.rb
|
|
107
123
|
- lib/httparty/response/headers.rb
|
|
108
124
|
- lib/httparty/response_fragment.rb
|
|
@@ -115,7 +131,8 @@ files:
|
|
|
115
131
|
homepage: https://github.com/jnunemaker/httparty
|
|
116
132
|
licenses:
|
|
117
133
|
- MIT
|
|
118
|
-
metadata:
|
|
134
|
+
metadata:
|
|
135
|
+
changelog_uri: https://github.com/jnunemaker/httparty/releases
|
|
119
136
|
post_install_message: When you HTTParty, you must party hard!
|
|
120
137
|
rdoc_options: []
|
|
121
138
|
require_paths:
|
|
@@ -124,15 +141,15 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
|
124
141
|
requirements:
|
|
125
142
|
- - ">="
|
|
126
143
|
- !ruby/object:Gem::Version
|
|
127
|
-
version: 2.
|
|
144
|
+
version: 2.7.0
|
|
128
145
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
129
146
|
requirements:
|
|
130
147
|
- - ">="
|
|
131
148
|
- !ruby/object:Gem::Version
|
|
132
149
|
version: '0'
|
|
133
150
|
requirements: []
|
|
134
|
-
rubygems_version: 3.
|
|
135
|
-
signing_key:
|
|
151
|
+
rubygems_version: 3.3.7
|
|
152
|
+
signing_key:
|
|
136
153
|
specification_version: 4
|
|
137
154
|
summary: Makes http fun! Also, makes consuming restful web services dead easy.
|
|
138
155
|
test_files: []
|
data/.simplecov
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
SimpleCov.start "test_frameworks"
|