httpx 0.20.5 → 0.21.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.
Files changed (52) hide show
  1. checksums.yaml +4 -4
  2. data/doc/release_notes/0_13_0.md +1 -1
  3. data/doc/release_notes/0_21_0.md +94 -0
  4. data/lib/httpx/connection/http1.rb +2 -1
  5. data/lib/httpx/connection.rb +41 -2
  6. data/lib/httpx/errors.rb +18 -0
  7. data/lib/httpx/extensions.rb +8 -4
  8. data/lib/httpx/io/unix.rb +1 -1
  9. data/lib/httpx/options.rb +7 -3
  10. data/lib/httpx/plugins/circuit_breaker/circuit.rb +76 -0
  11. data/lib/httpx/plugins/circuit_breaker/circuit_store.rb +44 -0
  12. data/lib/httpx/plugins/circuit_breaker.rb +115 -0
  13. data/lib/httpx/plugins/cookies.rb +1 -1
  14. data/lib/httpx/plugins/expect.rb +1 -1
  15. data/lib/httpx/plugins/multipart/decoder.rb +1 -1
  16. data/lib/httpx/plugins/proxy.rb +7 -1
  17. data/lib/httpx/plugins/retries.rb +1 -1
  18. data/lib/httpx/plugins/webdav.rb +78 -0
  19. data/lib/httpx/request.rb +15 -25
  20. data/lib/httpx/resolver/https.rb +2 -7
  21. data/lib/httpx/resolver/native.rb +2 -1
  22. data/lib/httpx/response.rb +27 -9
  23. data/lib/httpx/timers.rb +3 -0
  24. data/lib/httpx/transcoder/form.rb +1 -1
  25. data/lib/httpx/transcoder/json.rb +19 -3
  26. data/lib/httpx/transcoder/xml.rb +57 -0
  27. data/lib/httpx/transcoder.rb +1 -0
  28. data/lib/httpx/version.rb +1 -1
  29. data/sig/buffer.rbs +1 -1
  30. data/sig/chainable.rbs +1 -0
  31. data/sig/connection.rbs +12 -4
  32. data/sig/errors.rbs +13 -0
  33. data/sig/io.rbs +6 -0
  34. data/sig/options.rbs +4 -1
  35. data/sig/plugins/circuit_breaker.rbs +61 -0
  36. data/sig/plugins/compression/brotli.rbs +1 -1
  37. data/sig/plugins/compression/deflate.rbs +1 -1
  38. data/sig/plugins/compression/gzip.rbs +3 -3
  39. data/sig/plugins/compression.rbs +1 -1
  40. data/sig/plugins/multipart.rbs +1 -1
  41. data/sig/plugins/proxy/socks5.rbs +3 -2
  42. data/sig/plugins/proxy.rbs +1 -1
  43. data/sig/registry.rbs +5 -4
  44. data/sig/request.rbs +7 -1
  45. data/sig/resolver/native.rbs +5 -2
  46. data/sig/response.rbs +3 -1
  47. data/sig/timers.rbs +1 -1
  48. data/sig/transcoder/json.rbs +4 -1
  49. data/sig/transcoder/xml.rbs +21 -0
  50. data/sig/transcoder.rbs +2 -2
  51. data/sig/utils.rbs +2 -2
  52. metadata +12 -2
@@ -0,0 +1,78 @@
1
+ # frozen_string_literal: true
2
+
3
+ module HTTPX
4
+ module Plugins
5
+ #
6
+ # This plugin implements convenience methods for performing WEBDAV requests.
7
+ #
8
+ # https://gitlab.com/honeyryderchuck/httpx/wikis/WEBDAV
9
+ #
10
+ module WebDav
11
+ module InstanceMethods
12
+ def copy(src, dest)
13
+ request(:copy, src, headers: { "destination" => @options.origin.merge(dest) })
14
+ end
15
+
16
+ def move(src, dest)
17
+ request(:move, src, headers: { "destination" => @options.origin.merge(dest) })
18
+ end
19
+
20
+ def lock(path, timeout: nil, &blk)
21
+ headers = {}
22
+ headers["timeout"] = if timeout && timeout.positive?
23
+ "Second-#{timeout}"
24
+ else
25
+ "Infinite, Second-4100000000"
26
+ end
27
+ xml = "<?xml version=\"1.0\" encoding=\"utf-8\" ?>" \
28
+ "<D:lockinfo xmlns:D=\"DAV:\">" \
29
+ "<D:lockscope><D:exclusive/></D:lockscope>" \
30
+ "<D:locktype><D:write/></D:locktype>" \
31
+ "<D:owner>null</D:owner>" \
32
+ "</D:lockinfo>"
33
+ response = request(:lock, path, headers: headers, xml: xml)
34
+
35
+ return response unless blk && response.status == 200
36
+
37
+ lock_token = response.headers["lock-token"]
38
+
39
+ begin
40
+ blk.call(response)
41
+ ensure
42
+ unlock(path, lock_token)
43
+ end
44
+ end
45
+
46
+ def unlock(path, lock_token)
47
+ request(:unlock, path, headers: { "lock-token" => lock_token })
48
+ end
49
+
50
+ def mkcol(dir)
51
+ request(:mkcol, dir)
52
+ end
53
+
54
+ def propfind(path, xml = nil)
55
+ body = case xml
56
+ when :acl
57
+ '<?xml version="1.0" encoding="utf-8" ?><D:propfind xmlns:D="DAV:"><D:prop><D:owner/>' \
58
+ "<D:supported-privilege-set/><D:current-user-privilege-set/><D:acl/></D:prop></D:propfind>"
59
+ when nil
60
+ '<?xml version="1.0" encoding="utf-8"?><DAV:propfind xmlns:DAV="DAV:"><DAV:allprop/></DAV:propfind>'
61
+ else
62
+ xml
63
+ end
64
+
65
+ request(:propfind, path, headers: { "depth" => "1" }, xml: body)
66
+ end
67
+
68
+ def proppatch(path, xml)
69
+ body = "<?xml version=\"1.0\"?>" \
70
+ "<D:propertyupdate xmlns:D=\"DAV:\" xmlns:Z=\"http://ns.example.com/standards/z39.50/\">#{xml}</D:propertyupdate>"
71
+ request(:proppatch, path, xml: body)
72
+ end
73
+ # %i[ orderpatch acl report search]
74
+ end
75
+ end
76
+ register_plugin(:webdav, WebDav)
77
+ end
78
+ end
data/lib/httpx/request.rb CHANGED
@@ -9,29 +9,6 @@ module HTTPX
9
9
  include Callbacks
10
10
  using URIExtensions
11
11
 
12
- METHODS = [
13
- # RFC 2616: Hypertext Transfer Protocol -- HTTP/1.1
14
- :options, :get, :head, :post, :put, :delete, :trace, :connect,
15
-
16
- # RFC 2518: HTTP Extensions for Distributed Authoring -- WEBDAV
17
- :propfind, :proppatch, :mkcol, :copy, :move, :lock, :unlock,
18
-
19
- # RFC 3648: WebDAV Ordered Collections Protocol
20
- :orderpatch,
21
-
22
- # RFC 3744: WebDAV Access Control Protocol
23
- :acl,
24
-
25
- # RFC 6352: vCard Extensions to WebDAV -- CardDAV
26
- :report,
27
-
28
- # RFC 5789: PATCH Method for HTTP
29
- :patch,
30
-
31
- # draft-reschke-webdav-search: WebDAV Search
32
- :search
33
- ].freeze
34
-
35
12
  USER_AGENT = "httpx.rb/#{VERSION}"
36
13
 
37
14
  attr_reader :verb, :uri, :headers, :body, :state, :options, :response
@@ -54,8 +31,6 @@ module HTTPX
54
31
  @uri = origin.merge("#{base_path}#{@uri}")
55
32
  end
56
33
 
57
- raise(Error, "unknown method: #{verb}") unless METHODS.include?(@verb)
58
-
59
34
  @headers = @options.headers_class.new(@options.headers)
60
35
  @headers["user-agent"] ||= USER_AGENT
61
36
  @headers["accept"] ||= "*/*"
@@ -64,6 +39,18 @@ module HTTPX
64
39
  @state = :idle
65
40
  end
66
41
 
42
+ def read_timeout
43
+ @options.timeout[:read_timeout]
44
+ end
45
+
46
+ def write_timeout
47
+ @options.timeout[:write_timeout]
48
+ end
49
+
50
+ def request_timeout
51
+ @options.timeout[:request_timeout]
52
+ end
53
+
67
54
  def trailers?
68
55
  defined?(@trailers)
69
56
  end
@@ -108,6 +95,7 @@ module HTTPX
108
95
 
109
96
  def path
110
97
  path = uri.path.dup
98
+ path = +"" if path.nil?
111
99
  path << "/" if path.empty?
112
100
  path << "?#{query}" unless query.empty?
113
101
  path
@@ -174,6 +162,8 @@ module HTTPX
174
162
  Transcoder.registry("form").encode(options.form)
175
163
  elsif options.json
176
164
  Transcoder.registry("json").encode(options.json)
165
+ elsif options.xml
166
+ Transcoder.registry("xml").encode(options.xml)
177
167
  end
178
168
  return if @body.nil?
179
169
 
@@ -102,7 +102,7 @@ module HTTPX
102
102
  @requests[request] = hostname
103
103
  resolver_connection.send(request)
104
104
  @connections << connection
105
- rescue ResolveError, Resolv::DNS::EncodeError, JSON::JSONError => e
105
+ rescue ResolveError, Resolv::DNS::EncodeError => e
106
106
  @queries.delete(hostname)
107
107
  emit_resolve_error(connection, connection.origin.host, e)
108
108
  end
@@ -129,7 +129,7 @@ module HTTPX
129
129
  def parse(request, response)
130
130
  begin
131
131
  answers = decode_response_body(response)
132
- rescue Resolv::DNS::DecodeError, JSON::JSONError => e
132
+ rescue Resolv::DNS::DecodeError => e
133
133
  host, connection = @queries.first
134
134
  @queries.delete(host)
135
135
  emit_resolve_error(connection, connection.origin.host, e)
@@ -203,11 +203,6 @@ module HTTPX
203
203
 
204
204
  def decode_response_body(response)
205
205
  case response.headers["content-type"]
206
- when "application/dns-json",
207
- "application/json",
208
- %r{^application/x-javascript} # because google...
209
- payload = JSON.parse(response.to_s)
210
- payload["Answer"]
211
206
  when "application/dns-udpwireformat",
212
207
  "application/dns-message"
213
208
  Resolver.decode_dns_answer(response.to_s)
@@ -77,7 +77,8 @@ module HTTPX
77
77
  nil
78
78
  rescue Errno::EHOSTUNREACH => e
79
79
  @ns_index += 1
80
- if @ns_index < @nameserver.size
80
+ nameserver = @nameserver
81
+ if nameserver && @ns_index < nameserver.size
81
82
  log { "resolver: failed resolving on nameserver #{@nameserver[@ns_index - 1]} (#{e.message})" }
82
83
  transition(:idle)
83
84
  else
@@ -31,6 +31,7 @@ module HTTPX
31
31
  @status = Integer(status)
32
32
  @headers = @options.headers_class.new(headers)
33
33
  @body = @options.response_body_class.new(self, @options)
34
+ @finished = complete?
34
35
  end
35
36
 
36
37
  def merge_headers(h)
@@ -41,15 +42,24 @@ module HTTPX
41
42
  @body.write(data)
42
43
  end
43
44
 
45
+ def content_type
46
+ @content_type ||= ContentType.new(@headers["content-type"])
47
+ end
48
+
49
+ def finished?
50
+ @finished
51
+ end
52
+
53
+ def finish!
54
+ @finished = true
55
+ @headers.freeze
56
+ end
57
+
44
58
  def bodyless?
45
59
  @request.verb == :head ||
46
60
  no_data?
47
61
  end
48
62
 
49
- def content_type
50
- @content_type ||= ContentType.new(@headers["content-type"])
51
- end
52
-
53
63
  def complete?
54
64
  bodyless? || (@request.verb == :connect && @status == 200)
55
65
  end
@@ -76,17 +86,21 @@ module HTTPX
76
86
  raise err
77
87
  end
78
88
 
79
- def json(options = nil)
80
- decode("json", options)
89
+ def json(*args)
90
+ decode("json", *args)
81
91
  end
82
92
 
83
93
  def form
84
94
  decode("form")
85
95
  end
86
96
 
97
+ def xml
98
+ decode("xml")
99
+ end
100
+
87
101
  private
88
102
 
89
- def decode(format, options = nil)
103
+ def decode(format, *args)
90
104
  # TODO: check if content-type is a valid format, i.e. "application/json" for json parsing
91
105
  transcoder = Transcoder.registry(format)
92
106
 
@@ -96,13 +110,13 @@ module HTTPX
96
110
 
97
111
  raise Error, "no decoder available for \"#{format}\"" unless decoder
98
112
 
99
- decoder.call(self, options)
113
+ decoder.call(self, *args)
100
114
  rescue Registry::Error
101
115
  raise Error, "no decoder available for \"#{format}\""
102
116
  end
103
117
 
104
118
  def no_data?
105
- @status < 200 ||
119
+ @status < 200 || # informational response
106
120
  @status == 204 ||
107
121
  @status == 205 ||
108
122
  @status == 304 || begin
@@ -339,6 +353,10 @@ module HTTPX
339
353
  end
340
354
  end
341
355
 
356
+ def finished?
357
+ true
358
+ end
359
+
342
360
  def raise_for_status
343
361
  raise @error
344
362
  end
data/lib/httpx/timers.rb CHANGED
@@ -37,9 +37,12 @@ module HTTPX
37
37
  elapsed_time = Utils.elapsed_time(@next_interval_at)
38
38
 
39
39
  @intervals.delete_if { |interval| interval.elapse(elapsed_time) <= 0 }
40
+
41
+ @next_interval_at = nil if @intervals.empty?
40
42
  end
41
43
 
42
44
  def cancel
45
+ @next_interval_at = nil
43
46
  @intervals.clear
44
47
  end
45
48
 
@@ -36,7 +36,7 @@ module HTTPX::Transcoder
36
36
  module Decoder
37
37
  module_function
38
38
 
39
- def call(response, _)
39
+ def call(response, *)
40
40
  URI.decode_www_form(response.to_s).each_with_object({}) do |(field, value), params|
41
41
  HTTPX::Transcoder.normalize_query(params, field, value, PARAM_DEPTH_LIMIT)
42
42
  end
@@ -1,7 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  require "forwardable"
4
- require "json"
5
4
 
6
5
  module HTTPX::Transcoder
7
6
  module JSON
@@ -19,7 +18,7 @@ module HTTPX::Transcoder
19
18
  def_delegator :@raw, :bytesize
20
19
 
21
20
  def initialize(json)
22
- @raw = ::JSON.dump(json)
21
+ @raw = JSON.json_dump(json)
23
22
  @charset = @raw.encoding.name.downcase
24
23
  end
25
24
 
@@ -37,8 +36,25 @@ module HTTPX::Transcoder
37
36
 
38
37
  raise HTTPX::Error, "invalid json mime type (#{content_type})" unless JSON_REGEX.match?(content_type)
39
38
 
40
- ::JSON.method(:parse)
39
+ method(:json_load)
41
40
  end
41
+
42
+ # rubocop:disable Style/SingleLineMethods
43
+ if defined?(MultiJson)
44
+ def json_load(*args); MultiJson.load(*args); end
45
+ def json_dump(*args); MultiJson.dump(*args); end
46
+ elsif defined?(Oj)
47
+ def json_load(response, *args); Oj.load(response.to_s, *args); end
48
+ def json_dump(*args); Oj.dump(*args); end
49
+ elsif defined?(Yajl)
50
+ def json_load(response, *args); Yajl::Parser.new(*args).parse(response.to_s); end
51
+ def json_dump(*args); Yajl::Encoder.encode(*args); end
52
+ else
53
+ require "json"
54
+ def json_load(*args); ::JSON.parse(*args); end
55
+ def json_dump(*args); ::JSON.dump(*args); end
56
+ end
57
+ # rubocop:enable Style/SingleLineMethods
42
58
  end
43
59
  register "json", JSON
44
60
  end
@@ -0,0 +1,57 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "delegate"
4
+ require "forwardable"
5
+ require "uri"
6
+
7
+ module HTTPX::Transcoder
8
+ module Xml
9
+ using HTTPX::RegexpExtensions
10
+
11
+ module_function
12
+
13
+ MIME_TYPES = %r{\b(application|text)/(.+\+)?xml\b}.freeze
14
+
15
+ class Encoder
16
+ def initialize(xml)
17
+ @raw = xml
18
+ end
19
+
20
+ def content_type
21
+ charset = @raw.respond_to?(:encoding) ? @raw.encoding.to_s.downcase : "utf-8"
22
+ "application/xml; charset=#{charset}"
23
+ end
24
+
25
+ def bytesize
26
+ @raw.to_s.bytesize
27
+ end
28
+
29
+ def to_s
30
+ @raw.to_s
31
+ end
32
+ end
33
+
34
+ def encode(xml)
35
+ Encoder.new(xml)
36
+ end
37
+
38
+ begin
39
+ require "nokogiri"
40
+
41
+ # rubocop:disable Lint/DuplicateMethods
42
+ def decode(response)
43
+ content_type = response.content_type.mime_type
44
+
45
+ raise HTTPX::Error, "invalid form mime type (#{content_type})" unless MIME_TYPES.match?(content_type)
46
+
47
+ Nokogiri::XML.method(:parse)
48
+ end
49
+ rescue LoadError
50
+ def decode(_response)
51
+ raise HTTPX::Error, "\"nokogiri\" is required in order to decode XML"
52
+ end
53
+ end
54
+ # rubocop:enable Lint/DuplicateMethods
55
+ end
56
+ register "xml", Xml
57
+ end
@@ -90,4 +90,5 @@ end
90
90
  require "httpx/transcoder/body"
91
91
  require "httpx/transcoder/form"
92
92
  require "httpx/transcoder/json"
93
+ require "httpx/transcoder/xml"
93
94
  require "httpx/transcoder/chunker"
data/lib/httpx/version.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module HTTPX
4
- VERSION = "0.20.5"
4
+ VERSION = "0.21.0"
5
5
  end
data/sig/buffer.rbs CHANGED
@@ -15,7 +15,7 @@ module HTTPX
15
15
  # delegated
16
16
  def <<: (string data) -> String
17
17
  def empty?: () -> bool
18
- def bytesize: () -> Integer
18
+ def bytesize: () -> (Integer | Float)
19
19
  def clear: () -> void
20
20
  def replace: (string) -> void
21
21
 
data/sig/chainable.rbs CHANGED
@@ -33,6 +33,7 @@ module HTTPX
33
33
  | (:aws_sigv4, ?options) -> Plugins::awsSigV4Session
34
34
  | (:grpc, ?options) -> Plugins::grpcSession
35
35
  | (:response_cache, ?options) -> Plugins::sessionResponseCache
36
+ | (:circuit_breaker, ?options) -> Plugins::sessionCircuitBreaker
36
37
  | (Symbol | Module, ?options) { (Class) -> void } -> Session
37
38
  | (Symbol | Module, ?options) -> Session
38
39
 
data/sig/connection.rbs CHANGED
@@ -28,7 +28,7 @@ module HTTPX
28
28
  attr_reader options: Options
29
29
  attr_writer timers: Timers
30
30
 
31
- @origins: Array[URI::Generic]
31
+ @type: io_type
32
32
  @window_size: Integer
33
33
  @read_buffer: Buffer
34
34
  @write_buffer: Buffer
@@ -40,7 +40,7 @@ module HTTPX
40
40
 
41
41
  def addresses=: (Array[ipaddr]) -> void
42
42
 
43
- def match?: (URI::Generic, options) -> bool
43
+ def match?: (URI::Generic uri, Options options) -> bool
44
44
 
45
45
  def mergeable?: (Connection) -> bool
46
46
 
@@ -54,13 +54,15 @@ module HTTPX
54
54
 
55
55
  def match_altsvcs?: (URI::Generic uri) -> bool
56
56
 
57
+ def match_altsvc_options?: (URI::Generic uri, Options options) -> bool
58
+
57
59
  def connecting?: () -> bool
58
60
 
59
61
  def inflight?: () -> boolish
60
62
 
61
63
  def interests: () -> io_interests?
62
64
 
63
- def to_io: () -> IO
65
+ def to_io: () -> ::IO
64
66
 
65
67
  def call: () -> void
66
68
 
@@ -77,7 +79,7 @@ module HTTPX
77
79
 
78
80
  private
79
81
 
80
- def initialize: (String, URI::Generic, options) -> untyped
82
+ def initialize: (io_type, URI::Generic, options) -> untyped
81
83
 
82
84
  def connect: () -> void
83
85
 
@@ -103,5 +105,11 @@ module HTTPX
103
105
  def handle_error: (StandardError) -> void
104
106
 
105
107
  def purge_after_closed: () -> void
108
+
109
+ def set_request_timeouts: (Request request) -> void
110
+
111
+ def write_timeout_callback: (Request request, Numeric write_timeout) -> void
112
+
113
+ def read_timeout_callback: (Request request, Numeric read_timeout, ?singleton(RequestTimeoutError) error_type) -> void
106
114
  end
107
115
  end
data/sig/errors.rbs CHANGED
@@ -23,6 +23,19 @@ module HTTPX
23
23
  class ResolveTimeoutError < TimeoutError
24
24
  end
25
25
 
26
+ class RequestTimeoutError < TimeoutError
27
+ attr_reader request: Request
28
+ attr_reader response: response?
29
+
30
+ def initialize: (Request request, response? response, Numeric timeout) -> void
31
+ end
32
+
33
+ class ReadTimeoutError < RequestTimeoutError
34
+ end
35
+
36
+ class WriteTimeoutError < RequestTimeoutError
37
+ end
38
+
26
39
  class ResolveError < Error
27
40
  end
28
41
 
data/sig/io.rbs ADDED
@@ -0,0 +1,6 @@
1
+ module HTTPX
2
+ type io_type = "udp" | "tcp" | "ssl" | "unix"
3
+
4
+ module IO
5
+ end
6
+ end
data/sig/options.rbs CHANGED
@@ -10,7 +10,7 @@ module HTTPX
10
10
  SETTINGS_TIMEOUT: Integer
11
11
  DEFAULT_OPTIONS: Hash[Symbol, untyped]
12
12
 
13
- type timeout_type = :connect_timeout | :settings_timeout | :operation_timeout | :keep_alive_timeout | :total_timeout
13
+ type timeout_type = :connect_timeout | :settings_timeout | :operation_timeout | :keep_alive_timeout | :total_timeout | :read_timeout | :write_timeout | :request_timeout
14
14
  type timeout = Hash[timeout_type, Numeric]
15
15
 
16
16
  def self.new: (?options) -> instance
@@ -65,6 +65,9 @@ module HTTPX
65
65
  # body
66
66
  attr_reader origin: URI::Generic?
67
67
 
68
+ # base_path
69
+ attr_reader base_path: String?
70
+
68
71
  # ssl
69
72
 
70
73
  # http2_settings
@@ -0,0 +1,61 @@
1
+ module HTTPX
2
+ module Plugins
3
+ module CircuitBreaker
4
+
5
+ class CircuitStore
6
+ @circuits: Hash[String, Circuit]
7
+
8
+ def try_open: (generic_uri uri, response response) -> void
9
+
10
+ def try_respond: (Request request) -> response?
11
+
12
+ private
13
+
14
+ def get_circuit_for_uri: (generic_uri uri) -> Circuit
15
+
16
+ def initialize: (Options & _CircuitOptions options) -> void
17
+ end
18
+
19
+ class Circuit
20
+ @state: :closed | :open | :half_open
21
+ @max_attempts: Integer
22
+ @reset_attempts_in: Float
23
+ @break_in: Float
24
+ @circuit_breaker_half_open_drip_rate: Float
25
+ @attempts: Integer
26
+
27
+ @response: response?
28
+ @opened_at: Float?
29
+ @attempted_at: Float?
30
+
31
+ def respond: () -> response?
32
+
33
+ def try_open: (response) -> void
34
+
35
+ def try_close: () -> void
36
+
37
+ private
38
+
39
+ def initialize: (Integer max_attempts, Float reset_attempts_in, Float break_in, Float circuit_breaker_half_open_drip_rate) -> void
40
+ end
41
+
42
+ interface _CircuitOptions
43
+ def circuit_breaker_max_attempts: () -> Integer
44
+ def circuit_breaker_reset_attempts_in: () -> Float
45
+ def circuit_breaker_break_in: () -> Float
46
+ def circuit_breaker_half_open_drip_rate: () -> Float
47
+ def circuit_breaker_break_on: () -> (^(Response) -> boolish | nil)
48
+ end
49
+
50
+ def self.load_dependencies: (singleton(Session)) -> void
51
+ def self.extra_options: (Options) -> (Options & _CircuitOptions)
52
+
53
+ module InstanceMethods
54
+ @circuit_store: CircuitStore
55
+ end
56
+
57
+ end
58
+
59
+ type sessionCircuitBreaker = Session & CircuitBreaker::InstanceMethods
60
+ end
61
+ end
@@ -6,7 +6,7 @@ module HTTPX
6
6
  def self.configure: (singleton(Session)) -> void
7
7
 
8
8
  def self?.deflater: () -> _Deflater
9
- def self?.decoder: (Numeric bytesize) -> Inflater
9
+ def self?.decoder: (Integer | Float bytesize) -> Inflater
10
10
 
11
11
  module Deflater
12
12
  extend _Deflater
@@ -6,7 +6,7 @@ module HTTPX
6
6
  def self.configure: (singleton(Session)) -> void
7
7
 
8
8
  def self?.deflater: () -> _Deflater
9
- def self?.inflater: (Numeric bytesize) -> GZIP::Inflater
9
+ def self?.inflater: (Integer | Float bytesize) -> GZIP::Inflater
10
10
 
11
11
  module Deflater
12
12
  extend _Deflater
@@ -6,15 +6,15 @@ module HTTPX
6
6
  def self.configure: (singleton(Session)) -> void
7
7
 
8
8
  def self?.deflater: () -> _Deflater
9
- def self?.inflater: (Numeric bytesize) -> Inflater
9
+ def self?.inflater: (Integer | Float bytesize) -> Inflater
10
10
 
11
11
  class Deflater
12
12
  include _Deflater
13
13
 
14
14
  @compressed_chunk: String
15
-
15
+
16
16
  private
17
-
17
+
18
18
  def initialize: () -> untyped
19
19
  def write: (string) -> void
20
20
  def compressed_chunk: () -> String
@@ -13,7 +13,7 @@ module HTTPX
13
13
  interface _Inflater
14
14
  def inflate: (string) -> String
15
15
 
16
- def initialize: (Numeric bytesize) -> untyped
16
+ def initialize: (Integer | Float bytesize) -> untyped
17
17
  end
18
18
 
19
19
  def self.configure: (singleton(Session)) -> void
@@ -61,7 +61,7 @@ module HTTPX
61
61
  @boundary: String
62
62
  @intermediate_boundary: String
63
63
 
64
- def call: (Response response, untyped) -> Hash[String, untyped]
64
+ def call: (Response response, *untyped) -> Hash[String, untyped]
65
65
 
66
66
  private
67
67
 
@@ -4,14 +4,15 @@ module HTTPX
4
4
  module Plugins
5
5
  module Proxy
6
6
  module Socks5
7
-
7
+ VERSION: Integer
8
+
8
9
  module ConnectionMethods
9
10
  def __socks5_proxy_connect: () -> void
10
11
  def __socks5_on_packet: (String packet) -> void
11
12
  def __socks5_check_version: (int) -> void
12
13
  def __on_socks5_error: (string) -> void
13
14
  end
14
-
15
+
15
16
  class SocksParser
16
17
  include Callbacks
17
18