httpx 0.6.7 → 0.9.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 (70) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +7 -5
  3. data/doc/release_notes/0_0_1.md +7 -0
  4. data/doc/release_notes/0_0_2.md +9 -0
  5. data/doc/release_notes/0_0_3.md +9 -0
  6. data/doc/release_notes/0_0_4.md +7 -0
  7. data/doc/release_notes/0_0_5.md +5 -0
  8. data/doc/release_notes/0_1_0.md +9 -0
  9. data/doc/release_notes/0_2_0.md +5 -0
  10. data/doc/release_notes/0_2_1.md +16 -0
  11. data/doc/release_notes/0_3_0.md +12 -0
  12. data/doc/release_notes/0_3_1.md +6 -0
  13. data/doc/release_notes/0_4_0.md +51 -0
  14. data/doc/release_notes/0_4_1.md +3 -0
  15. data/doc/release_notes/0_5_0.md +15 -0
  16. data/doc/release_notes/0_5_1.md +14 -0
  17. data/doc/release_notes/0_6_0.md +5 -0
  18. data/doc/release_notes/0_6_1.md +6 -0
  19. data/doc/release_notes/0_6_2.md +6 -0
  20. data/doc/release_notes/0_6_3.md +13 -0
  21. data/doc/release_notes/0_6_4.md +21 -0
  22. data/doc/release_notes/0_6_5.md +22 -0
  23. data/doc/release_notes/0_6_6.md +19 -0
  24. data/doc/release_notes/0_6_7.md +5 -0
  25. data/doc/release_notes/0_7_0.md +46 -0
  26. data/doc/release_notes/0_8_0.md +27 -0
  27. data/doc/release_notes/0_8_1.md +8 -0
  28. data/doc/release_notes/0_8_2.md +7 -0
  29. data/doc/release_notes/0_9_0.md +38 -0
  30. data/lib/httpx/adapters/faraday.rb +2 -2
  31. data/lib/httpx/altsvc.rb +18 -2
  32. data/lib/httpx/chainable.rb +27 -9
  33. data/lib/httpx/connection.rb +215 -65
  34. data/lib/httpx/connection/http1.rb +54 -18
  35. data/lib/httpx/connection/http2.rb +100 -37
  36. data/lib/httpx/extensions.rb +2 -2
  37. data/lib/httpx/headers.rb +2 -2
  38. data/lib/httpx/io/ssl.rb +11 -3
  39. data/lib/httpx/io/tcp.rb +12 -2
  40. data/lib/httpx/loggable.rb +6 -6
  41. data/lib/httpx/options.rb +43 -28
  42. data/lib/httpx/plugins/authentication.rb +1 -1
  43. data/lib/httpx/plugins/compression.rb +28 -8
  44. data/lib/httpx/plugins/compression/gzip.rb +22 -12
  45. data/lib/httpx/plugins/cookies.rb +12 -8
  46. data/lib/httpx/plugins/digest_authentication.rb +2 -0
  47. data/lib/httpx/plugins/expect.rb +79 -0
  48. data/lib/httpx/plugins/follow_redirects.rb +1 -2
  49. data/lib/httpx/plugins/h2c.rb +0 -1
  50. data/lib/httpx/plugins/proxy.rb +23 -20
  51. data/lib/httpx/plugins/proxy/http.rb +9 -6
  52. data/lib/httpx/plugins/proxy/socks4.rb +1 -1
  53. data/lib/httpx/plugins/proxy/socks5.rb +5 -1
  54. data/lib/httpx/plugins/proxy/ssh.rb +0 -4
  55. data/lib/httpx/plugins/push_promise.rb +2 -2
  56. data/lib/httpx/plugins/retries.rb +32 -29
  57. data/lib/httpx/pool.rb +15 -10
  58. data/lib/httpx/registry.rb +2 -1
  59. data/lib/httpx/request.rb +8 -6
  60. data/lib/httpx/resolver.rb +7 -8
  61. data/lib/httpx/resolver/https.rb +15 -3
  62. data/lib/httpx/resolver/native.rb +22 -32
  63. data/lib/httpx/resolver/options.rb +2 -2
  64. data/lib/httpx/resolver/resolver_mixin.rb +1 -1
  65. data/lib/httpx/response.rb +17 -3
  66. data/lib/httpx/selector.rb +96 -95
  67. data/lib/httpx/session.rb +33 -34
  68. data/lib/httpx/timeout.rb +7 -1
  69. data/lib/httpx/version.rb +1 -1
  70. metadata +77 -20
@@ -5,7 +5,9 @@ module HTTPX
5
5
  include Loggable
6
6
  include Chainable
7
7
 
8
- def initialize(options = {}, &blk)
8
+ EMPTY_HASH = {}.freeze
9
+
10
+ def initialize(options = EMPTY_HASH, &blk)
9
11
  @options = self.class.default_options.merge(options)
10
12
  @responses = {}
11
13
  @persistent = @options.persistent
@@ -29,13 +31,21 @@ module HTTPX
29
31
  end
30
32
 
31
33
  def request(*args, **options)
32
- requests = build_requests(*args, options)
34
+ requests = args.first.is_a?(Request) ? args : build_requests(*args, options)
33
35
  responses = send_requests(*requests, options)
34
36
  return responses.first if responses.size == 1
35
37
 
36
38
  responses
37
39
  end
38
40
 
41
+ def build_request(verb, uri, options = EMPTY_HASH)
42
+ rklass = @options.request_class
43
+ request = rklass.new(verb, uri, @options.merge(options).merge(persistent: @persistent))
44
+ request.on(:response, &method(:on_response).curry[request])
45
+ request.on(:promise, &method(:on_promise))
46
+ request
47
+ end
48
+
39
49
  private
40
50
 
41
51
  def pool
@@ -47,7 +57,7 @@ module HTTPX
47
57
  end
48
58
 
49
59
  def on_promise(_, stream)
50
- log(level: 2, label: "#{stream.id}: ") { "refusing stream!" }
60
+ log(level: 2) { "#{stream.id}: refusing stream!" }
51
61
  stream.refuse
52
62
  end
53
63
 
@@ -60,22 +70,33 @@ module HTTPX
60
70
  connection = pool.find_connection(uri, options) || build_connection(uri, options)
61
71
  unless connections.nil? || connections.include?(connection)
62
72
  connections << connection
63
- set_connection_callbacks(connection, options)
73
+ set_connection_callbacks(connection, connections, options)
64
74
  end
65
75
  connection
66
76
  end
67
77
 
68
- def set_connection_callbacks(connection, options)
78
+ def set_connection_callbacks(connection, connections, options)
69
79
  connection.on(:uncoalesce) do |uncoalesced_uri|
70
80
  other_connection = build_connection(uncoalesced_uri, options)
81
+ connections << other_connection
71
82
  connection.unmerge(other_connection)
72
83
  end
73
84
  connection.on(:altsvc) do |alt_origin, origin, alt_params|
74
- build_altsvc_connection(connection, alt_origin, origin, alt_params, options)
85
+ other_connection = build_altsvc_connection(connection, connections, alt_origin, origin, alt_params, options)
86
+ connections << other_connection if other_connection
87
+ end
88
+ connection.on(:exhausted) do
89
+ other_connection = connection.create_idle
90
+ other_connection.merge(connection)
91
+ catch(:coalesced) do
92
+ pool.init_connection(other_connection, options)
93
+ end
94
+ set_connection_callbacks(other_connection, connections, options)
95
+ connections << other_connection
75
96
  end
76
97
  end
77
98
 
78
- def build_altsvc_connection(existing_connection, alt_origin, origin, alt_params, options)
99
+ def build_altsvc_connection(existing_connection, connections, alt_origin, origin, alt_params, options)
79
100
  altsvc = AltSvc.cached_altsvc_set(origin, alt_params.merge("origin" => alt_origin))
80
101
 
81
102
  # altsvc already exists, somehow it wasn't advertised, probably noop
@@ -85,7 +106,7 @@ module HTTPX
85
106
  # advertised altsvc is the same origin being used, ignore
86
107
  return if connection == existing_connection
87
108
 
88
- set_connection_callbacks(connection, options)
109
+ set_connection_callbacks(connection, connections, options)
89
110
 
90
111
  log(level: 1) { "#{origin} alt-svc: #{alt_origin}" }
91
112
 
@@ -99,8 +120,10 @@ module HTTPX
99
120
  end
100
121
 
101
122
  connection.merge(existing_connection)
123
+ connection
102
124
  rescue UnsupportedSchemeError
103
125
  altsvc["noop"] = true
126
+ nil
104
127
  end
105
128
 
106
129
  def build_requests(*args, options)
@@ -109,8 +132,8 @@ module HTTPX
109
132
  requests = case args.size
110
133
  when 1
111
134
  reqs = args.first
112
- reqs.map do |verb, uri|
113
- build_request(verb, uri, request_options)
135
+ reqs.map do |verb, uri, opts = EMPTY_HASH|
136
+ build_request(verb, uri, request_options.merge(opts))
114
137
  end
115
138
  when 2, 3
116
139
  verb, uris = args
@@ -155,7 +178,6 @@ module HTTPX
155
178
  error = catch(:resolve_error) do
156
179
  connection = find_connection(request, connections, request_options)
157
180
  connection.send(request)
158
- set_request_timeout(connection, request, request_options)
159
181
  end
160
182
  next unless error.is_a?(ResolveError)
161
183
 
@@ -183,29 +205,6 @@ module HTTPX
183
205
  end
184
206
  end
185
207
 
186
- def build_request(verb, uri, options)
187
- rklass = @options.request_class
188
- request = rklass.new(verb, uri, @options.merge(options))
189
- request.on(:response, &method(:on_response).curry[request])
190
- request.on(:promise, &method(:on_promise))
191
- request
192
- end
193
-
194
- def set_request_timeout(connection, request, options)
195
- total = options.timeout.total_timeout
196
- return unless total
197
-
198
- timer = pool.after(total) do
199
- unless @responses[request]
200
- error = TotalTimeoutError.new(total, "Timed out after #{total} seconds")
201
- response = ErrorResponse.new(request, error, options)
202
- request.emit(:response, response)
203
- connection.reset
204
- end
205
- end
206
- request.timer = timer
207
- end
208
-
209
208
  @default_options = Options.new
210
209
  @default_options.freeze
211
210
  @plugins = []
@@ -6,6 +6,7 @@ module HTTPX
6
6
  class Timeout
7
7
  CONNECT_TIMEOUT = 60
8
8
  OPERATION_TIMEOUT = 60
9
+ KEEP_ALIVE_TIMEOUT = 20
9
10
 
10
11
  def self.new(opts = {})
11
12
  return opts if opts.is_a?(Timeout)
@@ -13,14 +14,16 @@ module HTTPX
13
14
  super(**opts)
14
15
  end
15
16
 
16
- attr_reader :connect_timeout, :operation_timeout, :total_timeout
17
+ attr_reader :connect_timeout, :operation_timeout, :keep_alive_timeout, :total_timeout
17
18
 
18
19
  def initialize(connect_timeout: CONNECT_TIMEOUT,
19
20
  operation_timeout: OPERATION_TIMEOUT,
21
+ keep_alive_timeout: KEEP_ALIVE_TIMEOUT,
20
22
  total_timeout: nil,
21
23
  loop_timeout: nil)
22
24
  @connect_timeout = connect_timeout
23
25
  @operation_timeout = operation_timeout
26
+ @keep_alive_timeout = keep_alive_timeout
24
27
  @total_timeout = total_timeout
25
28
 
26
29
  return unless loop_timeout
@@ -35,6 +38,7 @@ module HTTPX
35
38
  if other.is_a?(Timeout)
36
39
  @connect_timeout == other.instance_variable_get(:@connect_timeout) &&
37
40
  @operation_timeout == other.instance_variable_get(:@operation_timeout) &&
41
+ @keep_alive_timeout == other.instance_variable_get(:@keep_alive_timeout) &&
38
42
  @total_timeout == other.instance_variable_get(:@total_timeout)
39
43
  else
40
44
  super
@@ -49,9 +53,11 @@ module HTTPX
49
53
  when Timeout
50
54
  connect_timeout = other.instance_variable_get(:@connect_timeout) || @connect_timeout
51
55
  operation_timeout = other.instance_variable_get(:@operation_timeout) || @operation_timeout
56
+ keep_alive_timeout = other.instance_variable_get(:@keep_alive_timeout) || @keep_alive_timeout
52
57
  total_timeout = other.instance_variable_get(:@total_timeout) || @total_timeout
53
58
  Timeout.new(connect_timeout: connect_timeout,
54
59
  operation_timeout: operation_timeout,
60
+ keep_alive_timeout: keep_alive_timeout,
55
61
  total_timeout: total_timeout)
56
62
  else
57
63
  raise ArgumentError, "can't merge with #{other.class}"
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module HTTPX
4
- VERSION = "0.6.7"
4
+ VERSION = "0.9.0"
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: httpx
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.7
4
+ version: 0.9.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tiago Cardoso
8
- autorequire:
8
+ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-02-29 00:00:00.000000000 Z
11
+ date: 2020-10-08 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: http-2-next
@@ -38,6 +38,20 @@ dependencies:
38
38
  - - ">="
39
39
  - !ruby/object:Gem::Version
40
40
  version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: http-cookie
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: '1.0'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: '1.0'
41
55
  - !ruby/object:Gem::Dependency
42
56
  name: http-form_data
43
57
  requirement: !ruby/object:Gem::Requirement
@@ -58,29 +72,71 @@ dependencies:
58
72
  - - "<"
59
73
  - !ruby/object:Gem::Version
60
74
  version: '3'
61
- - !ruby/object:Gem::Dependency
62
- name: http-cookie
63
- requirement: !ruby/object:Gem::Requirement
64
- requirements:
65
- - - "~>"
66
- - !ruby/object:Gem::Version
67
- version: '1.0'
68
- type: :development
69
- prerelease: false
70
- version_requirements: !ruby/object:Gem::Requirement
71
- requirements:
72
- - - "~>"
73
- - !ruby/object:Gem::Version
74
- version: '1.0'
75
75
  description: A client library for making HTTP requests from Ruby.
76
76
  email:
77
77
  - cardoso_tiago@hotmail.com
78
78
  executables: []
79
79
  extensions: []
80
- extra_rdoc_files: []
80
+ extra_rdoc_files:
81
+ - LICENSE.txt
82
+ - README.md
83
+ - doc/release_notes/0_0_1.md
84
+ - doc/release_notes/0_1_0.md
85
+ - doc/release_notes/0_0_5.md
86
+ - doc/release_notes/0_0_4.md
87
+ - doc/release_notes/0_6_5.md
88
+ - doc/release_notes/0_6_1.md
89
+ - doc/release_notes/0_7_0.md
90
+ - doc/release_notes/0_6_0.md
91
+ - doc/release_notes/0_8_2.md
92
+ - doc/release_notes/0_6_4.md
93
+ - doc/release_notes/0_9_0.md
94
+ - doc/release_notes/0_6_3.md
95
+ - doc/release_notes/0_8_1.md
96
+ - doc/release_notes/0_5_0.md
97
+ - doc/release_notes/0_6_7.md
98
+ - doc/release_notes/0_4_1.md
99
+ - doc/release_notes/0_5_1.md
100
+ - doc/release_notes/0_6_6.md
101
+ - doc/release_notes/0_4_0.md
102
+ - doc/release_notes/0_6_2.md
103
+ - doc/release_notes/0_8_0.md
104
+ - doc/release_notes/0_3_0.md
105
+ - doc/release_notes/0_2_1.md
106
+ - doc/release_notes/0_0_3.md
107
+ - doc/release_notes/0_0_2.md
108
+ - doc/release_notes/0_3_1.md
109
+ - doc/release_notes/0_2_0.md
81
110
  files:
82
111
  - LICENSE.txt
83
112
  - README.md
113
+ - doc/release_notes/0_0_1.md
114
+ - doc/release_notes/0_0_2.md
115
+ - doc/release_notes/0_0_3.md
116
+ - doc/release_notes/0_0_4.md
117
+ - doc/release_notes/0_0_5.md
118
+ - doc/release_notes/0_1_0.md
119
+ - doc/release_notes/0_2_0.md
120
+ - doc/release_notes/0_2_1.md
121
+ - doc/release_notes/0_3_0.md
122
+ - doc/release_notes/0_3_1.md
123
+ - doc/release_notes/0_4_0.md
124
+ - doc/release_notes/0_4_1.md
125
+ - doc/release_notes/0_5_0.md
126
+ - doc/release_notes/0_5_1.md
127
+ - doc/release_notes/0_6_0.md
128
+ - doc/release_notes/0_6_1.md
129
+ - doc/release_notes/0_6_2.md
130
+ - doc/release_notes/0_6_3.md
131
+ - doc/release_notes/0_6_4.md
132
+ - doc/release_notes/0_6_5.md
133
+ - doc/release_notes/0_6_6.md
134
+ - doc/release_notes/0_6_7.md
135
+ - doc/release_notes/0_7_0.md
136
+ - doc/release_notes/0_8_0.md
137
+ - doc/release_notes/0_8_1.md
138
+ - doc/release_notes/0_8_2.md
139
+ - doc/release_notes/0_9_0.md
84
140
  - lib/httpx.rb
85
141
  - lib/httpx/adapters/faraday.rb
86
142
  - lib/httpx/altsvc.rb
@@ -109,6 +165,7 @@ files:
109
165
  - lib/httpx/plugins/compression/gzip.rb
110
166
  - lib/httpx/plugins/cookies.rb
111
167
  - lib/httpx/plugins/digest_authentication.rb
168
+ - lib/httpx/plugins/expect.rb
112
169
  - lib/httpx/plugins/follow_redirects.rb
113
170
  - lib/httpx/plugins/h2c.rb
114
171
  - lib/httpx/plugins/multipart.rb
@@ -148,7 +205,7 @@ metadata:
148
205
  changelog_uri: https://honeyryderchuck.gitlab.io/httpx/#release-notes
149
206
  documentation_uri: https://honeyryderchuck.gitlab.io/httpx/rdoc/
150
207
  source_code_uri: https://gitlab.com/honeyryderchuck/httpx
151
- post_install_message:
208
+ post_install_message:
152
209
  rdoc_options: []
153
210
  require_paths:
154
211
  - lib
@@ -164,7 +221,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
164
221
  version: '0'
165
222
  requirements: []
166
223
  rubygems_version: 3.1.2
167
- signing_key:
224
+ signing_key:
168
225
  specification_version: 4
169
226
  summary: HTTPX, to the future, and beyond
170
227
  test_files: []