http 0.8.14 → 0.9.0.pre

Sign up to get free protection for your applications and to get access to all the features.
@@ -55,7 +55,6 @@ RSpec.describe HTTP::Options, "merge" do
55
55
  :socket_class => described_class.default_socket_class,
56
56
  :ssl_socket_class => described_class.default_ssl_socket_class,
57
57
  :ssl_context => nil,
58
- :cache => described_class.default_cache,
59
58
  :cookies => {})
60
59
  end
61
60
  end
@@ -133,19 +133,14 @@ RSpec.describe HTTP::Request do
133
133
  end
134
134
  end
135
135
 
136
- describe "#caching" do
137
- subject { request.caching }
138
- it { is_expected.to be_a HTTP::Request::Caching }
139
- end
140
-
141
136
  describe "#headline" do
142
137
  subject { request.headline }
143
138
 
144
- it { is_expected.to eq "GET /foo?bar=baz HTTP/1.1" }
139
+ it { is_expected.to eq "GET /foo?bar=baz#moo HTTP/1.1" }
145
140
 
146
141
  context "with proxy" do
147
142
  let(:proxy) { {:user => "user", :pass => "pass"} }
148
- it { is_expected.to eq "GET http://example.com/foo?bar=baz HTTP/1.1" }
143
+ it { is_expected.to eq "GET http://example.com/foo?bar=baz#moo HTTP/1.1" }
149
144
  end
150
145
  end
151
146
  end
@@ -109,11 +109,6 @@ RSpec.describe HTTP::Response do
109
109
  end
110
110
  end
111
111
 
112
- describe "#caching" do
113
- subject { response.caching }
114
- it { is_expected.to be_a HTTP::Response::Caching }
115
- end
116
-
117
112
  describe "#cookies" do
118
113
  let(:cookies) { ["a=1", "b=2; domain=example.com", "c=3; domain=bad.org"] }
119
114
  let(:headers) { {"Set-Cookie" => cookies} }
@@ -204,14 +204,6 @@ RSpec.describe HTTP do
204
204
  end
205
205
  end
206
206
 
207
- describe ".cache" do
208
- it "sets cache option" do
209
- cache = double(:cache, :perform => nil)
210
- client = HTTP.cache cache
211
- expect(client.default_options[:cache]).to eq cache
212
- end
213
- end
214
-
215
207
  describe ".persistent" do
216
208
  let(:host) { "https://api.github.com" }
217
209
 
@@ -17,6 +17,11 @@ require "http"
17
17
  require "rspec/its"
18
18
  require "support/capture_warning"
19
19
 
20
+ # Are we in a flaky environment?
21
+ def flaky_env?
22
+ defined?(JRUBY_VERSION) && ENV["CI"]
23
+ end
24
+
20
25
  # See http://rubydoc.info/gems/rspec-core/RSpec/Core/Configuration
21
26
  RSpec.configure do |config|
22
27
  config.expect_with :rspec do |expectations|
@@ -42,6 +42,8 @@ RSpec.shared_context "handles shared connections" do
42
42
 
43
43
  context "with a socket issue" do
44
44
  it "transparently reopens" do
45
+ skip "flaky environment" if flaky_env?
46
+
45
47
  first_socket = client.get("#{server.endpoint}/socket").body.to_s
46
48
  expect(first_socket).to_not eq("")
47
49
 
@@ -50,6 +50,7 @@ RSpec.shared_context "HTTP handling" do
50
50
  let(:read_timeout) { 0 }
51
51
 
52
52
  it "times out" do
53
+ skip "flaky environment" if flaky_env?
53
54
  expect { response }.to raise_error(HTTP::TimeoutError, /Read/i)
54
55
  end
55
56
  end
@@ -123,6 +124,8 @@ RSpec.shared_context "HTTP handling" do
123
124
 
124
125
  context "on a mixed state" do
125
126
  it "re-opens the connection" do
127
+ skip "flaky environment" if flaky_env?
128
+
126
129
  first_socket_id = client.get("#{server.endpoint}/socket/1").body.to_s
127
130
 
128
131
  client.instance_variable_set(:@state, :dirty)
@@ -154,6 +157,8 @@ RSpec.shared_context "HTTP handling" do
154
157
 
155
158
  context "with a socket issue" do
156
159
  it "transparently reopens" do
160
+ skip "flaky environment" if flaky_env?
161
+
157
162
  first_socket_id = client.get("#{server.endpoint}/socket").body.to_s
158
163
  expect(first_socket_id).to_not eq("")
159
164
  # Kill off the sockets we used
@@ -184,6 +189,8 @@ RSpec.shared_context "HTTP handling" do
184
189
  let(:options) { {} }
185
190
 
186
191
  it "opens new sockets" do
192
+ skip "flaky environment" if flaky_env?
193
+
187
194
  expect(sockets_used).to_not include("")
188
195
  expect(sockets_used.uniq.length).to eq(2)
189
196
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: http
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.8.14
4
+ version: 0.9.0.pre
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tony Arcieri
@@ -11,7 +11,7 @@ authors:
11
11
  autorequire:
12
12
  bindir: bin
13
13
  cert_chain: []
14
- date: 2015-08-19 00:00:00.000000000 Z
14
+ date: 2015-07-22 00:00:00.000000000 Z
15
15
  dependencies:
16
16
  - !ruby/object:Gem::Dependency
17
17
  name: http_parser.rb
@@ -107,9 +107,6 @@ files:
107
107
  - examples/parallel_requests_with_celluloid.rb
108
108
  - http.gemspec
109
109
  - lib/http.rb
110
- - lib/http/cache.rb
111
- - lib/http/cache/headers.rb
112
- - lib/http/cache/null_cache.rb
113
110
  - lib/http/chainable.rb
114
111
  - lib/http/client.rb
115
112
  - lib/http/connection.rb
@@ -124,24 +121,18 @@ files:
124
121
  - lib/http/options.rb
125
122
  - lib/http/redirector.rb
126
123
  - lib/http/request.rb
127
- - lib/http/request/caching.rb
128
124
  - lib/http/request/writer.rb
129
125
  - lib/http/response.rb
130
126
  - lib/http/response/body.rb
131
- - lib/http/response/caching.rb
132
- - lib/http/response/io_body.rb
133
127
  - lib/http/response/parser.rb
134
128
  - lib/http/response/status.rb
135
129
  - lib/http/response/status/reasons.rb
136
- - lib/http/response/string_body.rb
137
130
  - lib/http/timeout/global.rb
138
131
  - lib/http/timeout/null.rb
139
132
  - lib/http/timeout/per_operation.rb
140
133
  - lib/http/uri.rb
141
134
  - lib/http/version.rb
142
135
  - logo.png
143
- - spec/lib/http/cache/headers_spec.rb
144
- - spec/lib/http/cache_spec.rb
145
136
  - spec/lib/http/client_spec.rb
146
137
  - spec/lib/http/content_type_spec.rb
147
138
  - spec/lib/http/headers/mixin_spec.rb
@@ -155,14 +146,10 @@ files:
155
146
  - spec/lib/http/options/proxy_spec.rb
156
147
  - spec/lib/http/options_spec.rb
157
148
  - spec/lib/http/redirector_spec.rb
158
- - spec/lib/http/request/caching_spec.rb
159
149
  - spec/lib/http/request/writer_spec.rb
160
150
  - spec/lib/http/request_spec.rb
161
151
  - spec/lib/http/response/body_spec.rb
162
- - spec/lib/http/response/caching_spec.rb
163
- - spec/lib/http/response/io_body_spec.rb
164
152
  - spec/lib/http/response/status_spec.rb
165
- - spec/lib/http/response/string_body_spec.rb
166
153
  - spec/lib/http/response_spec.rb
167
154
  - spec/lib/http_spec.rb
168
155
  - spec/spec_helper.rb
@@ -191,14 +178,44 @@ required_ruby_version: !ruby/object:Gem::Requirement
191
178
  version: '0'
192
179
  required_rubygems_version: !ruby/object:Gem::Requirement
193
180
  requirements:
194
- - - ">="
181
+ - - ">"
195
182
  - !ruby/object:Gem::Version
196
- version: '0'
183
+ version: 1.3.1
197
184
  requirements: []
198
185
  rubyforge_project:
199
- rubygems_version: 2.2.3
186
+ rubygems_version: 2.4.6
200
187
  signing_key:
201
188
  specification_version: 4
202
189
  summary: HTTP should be easy
203
- test_files: []
190
+ test_files:
191
+ - spec/lib/http/client_spec.rb
192
+ - spec/lib/http/content_type_spec.rb
193
+ - spec/lib/http/headers/mixin_spec.rb
194
+ - spec/lib/http/headers_spec.rb
195
+ - spec/lib/http/options/body_spec.rb
196
+ - spec/lib/http/options/form_spec.rb
197
+ - spec/lib/http/options/headers_spec.rb
198
+ - spec/lib/http/options/json_spec.rb
199
+ - spec/lib/http/options/merge_spec.rb
200
+ - spec/lib/http/options/new_spec.rb
201
+ - spec/lib/http/options/proxy_spec.rb
202
+ - spec/lib/http/options_spec.rb
203
+ - spec/lib/http/redirector_spec.rb
204
+ - spec/lib/http/request/writer_spec.rb
205
+ - spec/lib/http/request_spec.rb
206
+ - spec/lib/http/response/body_spec.rb
207
+ - spec/lib/http/response/status_spec.rb
208
+ - spec/lib/http/response_spec.rb
209
+ - spec/lib/http_spec.rb
210
+ - spec/spec_helper.rb
211
+ - spec/support/black_hole.rb
212
+ - spec/support/capture_warning.rb
213
+ - spec/support/connection_reuse_shared.rb
214
+ - spec/support/dummy_server.rb
215
+ - spec/support/dummy_server/servlet.rb
216
+ - spec/support/http_handling_shared.rb
217
+ - spec/support/proxy_server.rb
218
+ - spec/support/servers/config.rb
219
+ - spec/support/servers/runner.rb
220
+ - spec/support/ssl_helper.rb
204
221
  has_rdoc:
@@ -1,146 +0,0 @@
1
- require "time"
2
- require "rack-cache"
3
-
4
- module HTTP
5
- class Cache
6
- # NoOp logger.
7
- class NullLogger
8
- def error(_msg = nil)
9
- end
10
-
11
- def debug(_msg = nil)
12
- end
13
-
14
- def info(_msg = nil)
15
- end
16
-
17
- def warn(_msg = nil)
18
- end
19
- end
20
-
21
- # @return [Response] a cached response that is valid for the request or
22
- # the result of executing the provided block
23
- #
24
- # @yield [request, options] on cache miss so that an actual
25
- # request can be made
26
- def perform(request, options, &request_performer)
27
- req = request.caching
28
-
29
- invalidate_cache(req) if req.invalidates_cache?
30
-
31
- get_response(req, options, request_performer)
32
- end
33
-
34
- protected
35
-
36
- # @return [Response] the response to the request, either from the
37
- # cache or by actually making the request
38
- def get_response(req, options, request_performer)
39
- cached_resp = cache_lookup(req)
40
- return cached_resp if cached_resp && !cached_resp.stale?
41
-
42
- # cache miss
43
- logger.debug { "Cache miss for <#{req.uri}>, making request" }
44
- actual_req = if cached_resp
45
- req.conditional_on_changes_to(cached_resp)
46
- else
47
- req
48
- end
49
- actual_resp = make_request(actual_req, options, request_performer)
50
-
51
- handle_response(cached_resp, actual_resp, req)
52
- end
53
-
54
- # @return [Response] the most useful of the responses after
55
- # updating the cache as appropriate
56
- def handle_response(cached_resp, actual_resp, req)
57
- if actual_resp.status.not_modified? && cached_resp
58
- logger.debug { "<#{req.uri}> not modified, using cached version." }
59
- cached_resp.validated!(actual_resp)
60
- store_in_cache(req, cached_resp)
61
- return cached_resp
62
-
63
- elsif req.cacheable? && actual_resp.cacheable?
64
- store_in_cache(req, actual_resp)
65
- return actual_resp
66
-
67
- else
68
- return actual_resp
69
- end
70
- end
71
-
72
- # @return [HTTP::Response::Caching] the actual response returned
73
- # by request_performer
74
- def make_request(req, options, request_performer)
75
- req.sent_at = Time.now
76
-
77
- request_performer.call(req, options).caching.tap do |res|
78
- res.received_at = Time.now
79
- res.requested_at = req.sent_at
80
- end
81
- end
82
-
83
- # @return [HTTP::Response::Caching, nil] the cached response for the request
84
- def cache_lookup(request)
85
- return nil if request.skips_cache?
86
-
87
- rack_resp = metastore.lookup(request, entitystore)
88
- return if rack_resp.nil?
89
-
90
- HTTP::Response.new(
91
- rack_resp.status, "1.1", rack_resp.headers, stringify(rack_resp.body)
92
- ).caching
93
- end
94
-
95
- # Store response in cache
96
- #
97
- # @return [nil]
98
- #
99
- # ---
100
- #
101
- # We have to convert the response body in to a string body so
102
- # that the cache store reading the body will not prevent the
103
- # original requester from doing so.
104
- def store_in_cache(request, response)
105
- response.body = response.body.to_s
106
- metastore.store(request, response, entitystore)
107
- nil
108
- end
109
-
110
- # Invalidate all response from the requested resource
111
- #
112
- # @return [nil]
113
- def invalidate_cache(request)
114
- metastore.invalidate(request, entitystore)
115
- end
116
-
117
- # Inits a new instance
118
- #
119
- # @option opts [String] :metastore URL to the metastore location
120
- # @option opts [String] :entitystore URL to the entitystore location
121
- # @option opts [Logger] :logger logger to use
122
- def initialize(opts)
123
- @metastore = storage.resolve_metastore_uri(opts.fetch(:metastore))
124
- @entitystore = storage.resolve_entitystore_uri(opts.fetch(:entitystore))
125
- @logger = opts.fetch(:logger) { NullLogger.new }
126
- end
127
-
128
- attr_reader :metastore, :entitystore, :logger
129
-
130
- def storage
131
- @@storage ||= Rack::Cache::Storage.new # rubocop:disable Style/ClassVars
132
- end
133
-
134
- def stringify(body)
135
- if body.respond_to?(:each)
136
- "".tap do |buf|
137
- body.each do |part|
138
- buf << part
139
- end
140
- end
141
- else
142
- body.to_s
143
- end
144
- end
145
- end
146
- end
@@ -1,100 +0,0 @@
1
- require "delegate"
2
-
3
- require "http/errors"
4
- require "http/headers"
5
-
6
- module HTTP
7
- class Cache
8
- # Convenience methods around cache control headers.
9
- class Headers < ::SimpleDelegator
10
- def initialize(headers)
11
- if headers.is_a? HTTP::Headers
12
- super headers
13
- else
14
- super HTTP::Headers.coerce headers
15
- end
16
- end
17
-
18
- # @return [Boolean] does this message force revalidation
19
- def forces_revalidation?
20
- must_revalidate? || max_age == 0
21
- end
22
-
23
- # @return [Boolean] does the cache control include 'must-revalidate'
24
- def must_revalidate?
25
- matches?(/\bmust-revalidate\b/i)
26
- end
27
-
28
- # @return [Boolean] does the cache control include 'no-cache'
29
- def no_cache?
30
- matches?(/\bno-cache\b/i)
31
- end
32
-
33
- # @return [Boolean] does the cache control include 'no-stor'
34
- def no_store?
35
- matches?(/\bno-store\b/i)
36
- end
37
-
38
- # @return [Boolean] does the cache control include 'public'
39
- def public?
40
- matches?(/\bpublic\b/i)
41
- end
42
-
43
- # @return [Boolean] does the cache control include 'private'
44
- def private?
45
- matches?(/\bprivate\b/i)
46
- end
47
-
48
- # @return [Numeric] the max number of seconds this message is
49
- # considered fresh.
50
- def max_age
51
- explicit_max_age || seconds_til_expires || Float::INFINITY
52
- end
53
-
54
- # @return [Boolean] is the vary header set to '*'
55
- def vary_star?
56
- get(HTTP::Headers::VARY).any? { |v| "*" == v.strip }
57
- end
58
-
59
- private
60
-
61
- # @return [Boolean] true when cache-control header matches the pattern
62
- def matches?(pattern)
63
- get(HTTP::Headers::CACHE_CONTROL).any? { |v| v =~ pattern }
64
- end
65
-
66
- # @return [Numeric] number of seconds until the time in the
67
- # expires header is reached.
68
- #
69
- # ---
70
- # Some servers send a "Expires: -1" header which must be treated as expired
71
- def seconds_til_expires
72
- get(HTTP::Headers::EXPIRES).
73
- map { |e| http_date_to_ttl(e) }.
74
- max
75
- end
76
-
77
- def http_date_to_ttl(t_str)
78
- ttl = to_time_or_epoch(t_str) - Time.now
79
-
80
- ttl < 0 ? 0 : ttl
81
- end
82
-
83
- # @return [Time] parses t_str at a time; if that fails returns epoch time
84
- def to_time_or_epoch(t_str)
85
- Time.httpdate(t_str)
86
- rescue ArgumentError
87
- Time.at(0)
88
- end
89
-
90
- # @return [Numeric] the value of the max-age component of cache control
91
- def explicit_max_age
92
- get(HTTP::Headers::CACHE_CONTROL).
93
- map { |v| (/max-age=(\d+)/i).match(v) }.
94
- compact.
95
- map { |m| m[1].to_i }.
96
- max
97
- end
98
- end
99
- end
100
- end