Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP

Loading…

Extracted request into a method object. #283

Closed
wants to merge 5 commits into from

4 participants

@steveklabnik

This will open the door for much more change in the future.

Currently a work in progress. I want to break up a few more things, add move persistance of connections back outside of the Request object, and name it better. But it's a start.

:heart: :heart: :heart: @evanphx :heart: :heart: :heart:

(Originally pull #282, till I did some silly git shit.)

@steveklabnik

Why is GitHub so silly? Uuuuuugh.

steveklabnik added some commits
@steveklabnik steveklabnik Made get_proxy_from_env private.
We never use this publcially, so it shouldn't be part of the
public interface. It's sorta akward to leave in, but
there wasn't any other code it fit in with, and I wasn't sure
that it was worth adding a whole second class just for
this one method.
4d37fdc
@steveklabnik steveklabnik Extracted Gem::UriFormatter.
There were a bunch of utility methods inside of RemoteFetcher that
didn't really belong there, so I pulled them out into a little class.
6b9f0c0
@steveklabnik steveklabnik Extracted request into a method object.
This will open the door for much more change in the future.

More things could be pulled into this object, but I'm not
ready to fight with all the tests such things break yet.
Basically, #user_agent and the @proxy_uri variable are
only used within this method, but there are a bunch of
tests that hack at their internal state.
589ae51
@steveklabnik steveklabnik Extracted user_agent into Request class. 3760004
@steveklabnik

Fixed! rock. Silly rebase... I screwed it up.

@zenspider zenspider was assigned
@drbrain drbrain was assigned
@zenspider
Owner

I was just going to try to merge/patch this in, but @drbrain said he needs to do some work on some HTTPS stuff first, so I'm assigning to him. Hopefully this'll go in immediately afterwards.

@steveklabnik

Cool. I have some more work I'm in the middle of too, I just haven't gotten a minute to work on it in a bit, I had all four of my wisdom teeth removed last week. o_O

@steveklabnik

With that said, I can always make those changes after, so do feel free to merge this whenever you want. I'm going to continue to try and improve this portion of the codebase regardless.

@rogerleite

Is there a reason why initialize is not a hash options? You could avoid this nil parameters and "fetch" default values on initialize.

@rogerleite

Great work! Left my suggestion on steveklabnik@3760004
About "move persistance of connections back outside of the Request object", you could build a ConnectionPool, something like https://github.com/mperham/connection_pool from Mike Perham.

@drbrain drbrain referenced this pull request from a commit
@drbrain drbrain Update history for #283 99fb9a0
@drbrain
Owner

Applied as @cb6d2e2 @d645e17 @9aa1148 @a175e5a @d5bfe9a with modifications due to bit rot in the patch.

@drbrain drbrain closed this
@drbrain drbrain referenced this pull request from a commit
@drbrain drbrain Move some Gem::Request tests to test_gem_request
While #283 moved features over to Gem::Request it did not move the
corresponding tests.  This follows up that work by moving over more of
the tests.
c6680d0
@drbrain drbrain referenced this pull request from a commit
@drbrain drbrain Restore -V following #283 0b1b844
@drbrain drbrain referenced this pull request from a commit
@drbrain drbrain Restore block behavior for RemoteFetcher#request
Before #283 was merged RemoteRequest#request would yield the request
object to a block for customization.  This behavior lacked tests so it
was accidentally removed.

Now the behavior has been restored and a test has been added.

Fixes #602
5355973
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Commits on Feb 22, 2012
  1. @steveklabnik

    Made get_proxy_from_env private.

    steveklabnik authored
    We never use this publcially, so it shouldn't be part of the
    public interface. It's sorta akward to leave in, but
    there wasn't any other code it fit in with, and I wasn't sure
    that it was worth adding a whole second class just for
    this one method.
  2. @steveklabnik

    Extracted Gem::UriFormatter.

    steveklabnik authored
    There were a bunch of utility methods inside of RemoteFetcher that
    didn't really belong there, so I pulled them out into a little class.
  3. @steveklabnik

    Extracted request into a method object.

    steveklabnik authored
    This will open the door for much more change in the future.
    
    More things could be pulled into this object, but I'm not
    ready to fight with all the tests such things break yet.
    Basically, #user_agent and the @proxy_uri variable are
    only used within this method, but there are a bunch of
    tests that hack at their internal state.
  4. @steveklabnik
  5. @steveklabnik
This page is out of date. Refresh to see the latest.
View
214 lib/rubygems/remote_fetcher.rb
@@ -1,6 +1,8 @@
require 'rubygems'
require 'rubygems/user_interaction'
+require 'rubygems/request'
require 'uri'
+require 'rubygems/uri_formatter'
##
# RemoteFetcher handles the details of fetching gems and gem information from
@@ -67,16 +69,7 @@ def initialize(proxy = nil)
Socket.do_not_reverse_lookup = true
- @connections = {}
- @requests = Hash.new 0
- @proxy_uri =
- case proxy
- when :no_proxy then nil
- when nil then get_proxy_from_env
- when URI::HTTP then proxy
- else URI.parse(proxy)
- end
- @user_agent = user_agent
+ @proxy = proxy
end
##
@@ -178,7 +171,7 @@ def download(spec, source_uri, install_dir = Gem.dir)
source_uri.path
end
- source_path = unescape source_path
+ source_path = Gem::UriFormatter.new(source_path).unescape
begin
FileUtils.cp source_path, local_gem_path unless
@@ -292,83 +285,6 @@ def fetch_size(uri) # TODO: phase this out
response['content-length'].to_i
end
- def escape(str)
- return unless str
- @uri_parser ||= uri_escaper
- @uri_parser.escape str
- end
-
- def unescape(str)
- return unless str
- @uri_parser ||= uri_escaper
- @uri_parser.unescape str
- end
-
- def uri_escaper
- URI::Parser.new
- rescue NameError
- URI
- end
-
- ##
- # Returns an HTTP proxy URI if one is set in the environment variables.
-
- def get_proxy_from_env
- env_proxy = ENV['http_proxy'] || ENV['HTTP_PROXY']
-
- return nil if env_proxy.nil? or env_proxy.empty?
-
- uri = URI.parse(normalize_uri(env_proxy))
-
- if uri and uri.user.nil? and uri.password.nil? then
- # Probably we have http_proxy_* variables?
- uri.user = escape(ENV['http_proxy_user'] || ENV['HTTP_PROXY_USER'])
- uri.password = escape(ENV['http_proxy_pass'] || ENV['HTTP_PROXY_PASS'])
- end
-
- uri
- end
-
- ##
- # Normalize the URI by adding "http://" if it is missing.
-
- def normalize_uri(uri)
- (uri =~ /^(https?|ftp|file):/) ? uri : "http://#{uri}"
- end
-
- ##
- # Creates or an HTTP connection based on +uri+, or retrieves an existing
- # connection, using a proxy if needed.
-
- def connection_for(uri)
- net_http_args = [uri.host, uri.port]
-
- if @proxy_uri then
- net_http_args += [
- @proxy_uri.host,
- @proxy_uri.port,
- @proxy_uri.user,
- @proxy_uri.password
- ]
- end
-
- connection_id = [Thread.current.object_id, *net_http_args].join ':'
- @connections[connection_id] ||= Net::HTTP.new(*net_http_args)
- connection = @connections[connection_id]
-
- if uri.scheme == 'https' and not connection.started? then
- require 'net/https'
- connection.use_ssl = true
- connection.verify_mode = OpenSSL::SSL::VERIFY_NONE
- end
-
- connection.start unless connection.started?
-
- connection
- rescue Errno::EHOSTDOWN => e
- raise FetchError.new(e.message, uri)
- end
-
def correct_for_windows_path(path)
if path[0].chr == '/' && path[1].chr =~ /[a-z]/i && path[2].chr == ':'
path = path[1..-1]
@@ -377,128 +293,8 @@ def correct_for_windows_path(path)
end
end
- ##
- # Performs a Net::HTTP request of type +request_class+ on +uri+ returning
- # a Net::HTTP response object. request maintains a table of persistent
- # connections to reduce connect overhead.
-
def request(uri, request_class, last_modified = nil)
- request = request_class.new uri.request_uri
-
- unless uri.nil? || uri.user.nil? || uri.user.empty? then
- request.basic_auth uri.user, uri.password
- end
-
- request.add_field 'User-Agent', @user_agent
- request.add_field 'Connection', 'keep-alive'
- request.add_field 'Keep-Alive', '30'
-
- if last_modified then
- last_modified = last_modified.utc
- request.add_field 'If-Modified-Since', last_modified.rfc2822
- end
-
- yield request if block_given?
-
- connection = connection_for uri
-
- retried = false
- bad_response = false
-
- begin
- @requests[connection.object_id] += 1
-
- say "#{request.method} #{uri}" if
- Gem.configuration.really_verbose
-
- file_name = File.basename(uri.path)
- # perform download progress reporter only for gems
- if request.response_body_permitted? && file_name =~ /\.gem$/
- reporter = ui.download_reporter
- response = connection.request(request) do |incomplete_response|
- if Net::HTTPOK === incomplete_response
- reporter.fetch(file_name, incomplete_response.content_length)
- downloaded = 0
- data = ''
-
- incomplete_response.read_body do |segment|
- data << segment
- downloaded += segment.length
- reporter.update(downloaded)
- end
- reporter.done
- if incomplete_response.respond_to? :body=
- incomplete_response.body = data
- else
- incomplete_response.instance_variable_set(:@body, data)
- end
- end
- end
- else
- response = connection.request request
- end
-
- say "#{response.code} #{response.message}" if
- Gem.configuration.really_verbose
-
- rescue Net::HTTPBadResponse
- say "bad response" if Gem.configuration.really_verbose
-
- reset connection
-
- raise FetchError.new('too many bad responses', uri) if bad_response
-
- bad_response = true
- retry
- # HACK work around EOFError bug in Net::HTTP
- # NOTE Errno::ECONNABORTED raised a lot on Windows, and make impossible
- # to install gems.
- rescue EOFError, Timeout::Error,
- Errno::ECONNABORTED, Errno::ECONNRESET, Errno::EPIPE
-
- requests = @requests[connection.object_id]
- say "connection reset after #{requests} requests, retrying" if
- Gem.configuration.really_verbose
-
- raise FetchError.new('too many connection resets', uri) if retried
-
- reset connection
-
- retried = true
- retry
- end
-
- response
- end
-
- ##
- # Resets HTTP connection +connection+.
-
- def reset(connection)
- @requests.delete connection.object_id
-
- connection.finish
- connection.start
+ Gem::Request.new(uri, request_class, last_modified, @proxy).fetch
end
-
- def user_agent
- ua = "RubyGems/#{Gem::VERSION} #{Gem::Platform.local}"
-
- ruby_version = RUBY_VERSION
- ruby_version += 'dev' if RUBY_PATCHLEVEL == -1
-
- ua << " Ruby/#{ruby_version} (#{RUBY_RELEASE_DATE}"
- if RUBY_PATCHLEVEL >= 0 then
- ua << " patchlevel #{RUBY_PATCHLEVEL}"
- elsif defined?(RUBY_REVISION) then
- ua << " revision #{RUBY_REVISION}"
- end
- ua << ")"
-
- ua << " #{RUBY_ENGINE}" if defined?(RUBY_ENGINE) and RUBY_ENGINE != 'ruby'
-
- ua
- end
-
end
View
208 lib/rubygems/request.rb
@@ -0,0 +1,208 @@
+class Gem::Request
+ def initialize(uri, request_class, last_modified, proxy)
+ @uri = uri
+ @request_class = request_class
+ @last_modified = last_modified
+ @requests = Hash.new 0
+ @connections = {}
+ @user_agent = user_agent
+
+ @proxy_uri =
+ case proxy
+ when :no_proxy then nil
+ when nil then get_proxy_from_env
+ when URI::HTTP then proxy
+ else URI.parse(proxy)
+ end
+ end
+
+ def fetch
+ request = @request_class.new @uri.request_uri
+
+ unless @uri.nil? || @uri.user.nil? || @uri.user.empty? then
+ request.basic_auth @uri.user, @uri.password
+ end
+
+ request.add_field 'User-Agent', @user_agent
+ request.add_field 'Connection', 'keep-alive'
+ request.add_field 'Keep-Alive', '30'
+
+ if @last_modified then
+ @last_modified = @last_modified.utc
+ request.add_field 'If-Modified-Since', @last_modified.rfc2822
+ end
+
+ yield request if block_given?
+
+ connection = connection_for @uri
+
+ retried = false
+ bad_response = false
+
+ begin
+ @requests[connection.object_id] += 1
+
+ say "#{request.method} #{@uri}" if
+ Gem.configuration.really_verbose
+
+ file_name = File.basename(@uri.path)
+ # perform download progress reporter only for gems
+ if request.response_body_permitted? && file_name =~ /\.gem$/
+ reporter = ui.download_reporter
+ response = connection.request(request) do |incomplete_response|
+ if Net::HTTPOK === incomplete_response
+ reporter.fetch(file_name, incomplete_response.content_length)
+ downloaded = 0
+ data = ''
+
+ incomplete_response.read_body do |segment|
+ data << segment
+ downloaded += segment.length
+ reporter.update(downloaded)
+ end
+ reporter.done
+ if incomplete_response.respond_to? :body=
+ incomplete_response.body = data
+ else
+ incomplete_response.instance_variable_set(:@body, data)
+ end
+ end
+ end
+ else
+ response = connection.request request
+ end
+
+ say "#{response.code} #{response.message}" if
+ Gem.configuration.really_verbose
+
+ rescue Net::HTTPBadResponse
+ say "bad response" if Gem.configuration.really_verbose
+
+ reset connection
+
+ raise Gem::RemoteFetcher::FetchError.new('too many bad responses', @uri) if bad_response
+
+ bad_response = true
+ retry
+ # HACK work around EOFError bug in Net::HTTP
+ # NOTE Errno::ECONNABORTED raised a lot on Windows, and make impossible
+ # to install gems.
+ rescue EOFError, Timeout::Error,
+ Errno::ECONNABORTED, Errno::ECONNRESET, Errno::EPIPE
+
+ requests = @requests[connection.object_id]
+ say "connection reset after #{requests} requests, retrying" if
+ Gem.configuration.really_verbose
+
+ raise Gem::RemoteFetcher::FetchError.new('too many connection resets', @uri) if retried
+
+ reset connection
+
+ retried = true
+ retry
+ end
+
+ response
+ end
+
+ ##
+ # Resets HTTP connection +connection+.
+
+ def reset(connection)
+ @requests.delete connection.object_id
+
+ connection.finish
+ connection.start
+ end
+
+ ##
+ # Creates or an HTTP connection based on +uri+, or retrieves an existing
+ # connection, using a proxy if needed.
+
+ def connection_for(uri)
+ net_http_args = [uri.host, uri.port]
+
+ if @proxy_uri then
+ net_http_args += [
+ @proxy_uri.host,
+ @proxy_uri.port,
+ @proxy_uri.user,
+ @proxy_uri.password
+ ]
+ end
+
+ connection_id = [Thread.current.object_id, *net_http_args].join ':'
+ @connections[connection_id] ||= Net::HTTP.new(*net_http_args)
+ connection = @connections[connection_id]
+
+ if uri.scheme == 'https' and not connection.started? then
+ require 'net/https'
+ connection.use_ssl = true
+ connection.verify_mode = OpenSSL::SSL::VERIFY_NONE
+ end
+
+ connection.start unless connection.started?
+
+ connection
+ rescue Errno::EHOSTDOWN => e
+ raise Gem::RemoteFetcher::FetchError.new(e.message, uri)
+ end
+
+ def user_agent
+ ua = "RubyGems/#{Gem::VERSION} #{Gem::Platform.local}"
+
+ ruby_version = RUBY_VERSION
+ ruby_version += 'dev' if RUBY_PATCHLEVEL == -1
+
+ ua << " Ruby/#{ruby_version} (#{RUBY_RELEASE_DATE}"
+ if RUBY_PATCHLEVEL >= 0 then
+ ua << " patchlevel #{RUBY_PATCHLEVEL}"
+ elsif defined?(RUBY_REVISION) then
+ ua << " revision #{RUBY_REVISION}"
+ end
+ ua << ")"
+
+ ua << " #{RUBY_ENGINE}" if defined?(RUBY_ENGINE) and RUBY_ENGINE != 'ruby'
+
+ ua
+ end
+
+ ##
+ # Returns an HTTP proxy URI if one is set in the environment variables.
+
+ def get_proxy_from_env
+ env_proxy = ENV['http_proxy'] || ENV['HTTP_PROXY']
+
+ return nil if env_proxy.nil? or env_proxy.empty?
+
+ uri = URI.parse(normalize_uri(env_proxy))
+
+ if uri and uri.user.nil? and uri.password.nil? then
+ # Probably we have http_proxy_* variables?
+ uri.user = escape(ENV['http_proxy_user'] || ENV['HTTP_PROXY_USER'])
+ uri.password = escape(ENV['http_proxy_pass'] || ENV['HTTP_PROXY_PASS'])
+ end
+
+ uri
+ end
+
+ ##
+ # Normalize the URI by adding "http://" if it is missing.
+
+ def normalize_uri(uri)
+ (uri =~ /^(https?|ftp|file):/) ? uri : "http://#{uri}"
+ end
+
+ def escape(str)
+ return unless str
+ @uri_parser ||= uri_escaper
+ @uri_parser.escape str
+ end
+
+ def uri_escaper
+ URI::Parser.new
+ rescue NameError
+ URI
+ end
+
+end
View
34 lib/rubygems/uri_formatter.rb
@@ -0,0 +1,34 @@
+class Gem::UriFormatter
+ attr_reader :uri
+
+ def initialize(uri)
+ @uri = uri
+ end
+
+ def escape
+ return unless uri
+ @uri_parser ||= escaper
+ @uri_parser.escape uri
+ end
+
+ def unescape
+ return unless uri
+ @uri_parser ||= escaper
+ @uri_parser.unescape uri
+ end
+
+ ##
+ # Normalize the URI by adding "http://" if it is missing.
+
+ def normalize
+ (uri =~ /^(https?|ftp|file):/) ? uri : "http://#{uri}"
+ end
+
+ private
+
+ def escaper
+ URI::Parser.new
+ rescue NameError
+ URI
+ end
+end
View
72 test/rubygems/test_gem_remote_fetcher.rb
@@ -125,7 +125,7 @@ def test_self_fetcher_with_proxy
refute_nil fetcher
assert_kind_of Gem::RemoteFetcher, fetcher
- assert_equal proxy_uri, fetcher.instance_variable_get(:@proxy_uri).to_s
+ assert_equal proxy_uri, Gem::Request.new(nil, nil, nil, proxy_uri).instance_variable_get(:@proxy_uri).to_s
end
def test_self_fetcher_with_proxy_URI
@@ -137,7 +137,7 @@ def test_self_fetcher_with_proxy_URI
refute_nil fetcher
assert_kind_of Gem::RemoteFetcher, fetcher
- assert_equal proxy_uri, fetcher.instance_variable_get(:@proxy_uri)
+ assert_equal proxy_uri, Gem::Request.new(nil, nil, nil, proxy_uri).instance_variable_get(:@proxy_uri)
end
def test_fetch_size_bad_uri
@@ -152,7 +152,7 @@ def test_fetch_size_bad_uri
def test_fetch_size_socket_error
fetcher = Gem::RemoteFetcher.new nil
- def fetcher.connection_for(uri)
+ def fetcher.request(uri, request_class, last_modified = nil)
raise SocketError, "tarded"
end
@@ -383,7 +383,7 @@ def test_explicit_proxy_with_user_auth
uri = URI.parse @proxy_uri
uri.user, uri.password = 'foo', 'bar'
fetcher = Gem::RemoteFetcher.new uri.to_s
- proxy = fetcher.instance_variable_get("@proxy_uri")
+ proxy = Gem::Request.new(nil, nil, nil, uri).instance_variable_get("@proxy_uri")
assert_equal 'foo', proxy.user
assert_equal 'bar', proxy.password
assert_data_from_proxy fetcher.fetch_path(@server_uri)
@@ -393,8 +393,8 @@ def test_explicit_proxy_with_user_auth
uri = URI.parse @proxy_uri
uri.user, uri.password = 'domain%5Cuser', 'bar'
fetcher = Gem::RemoteFetcher.new uri.to_s
- proxy = fetcher.instance_variable_get("@proxy_uri")
- assert_equal 'domain\user', fetcher.unescape(proxy.user)
+ proxy = Gem::Request.new(nil, nil, nil, uri.to_s).instance_variable_get("@proxy_uri")
+ assert_equal 'domain\user', Gem::UriFormatter.new(proxy.user).unescape
assert_equal 'bar', proxy.password
assert_data_from_proxy fetcher.fetch_path(@server_uri)
end
@@ -403,9 +403,9 @@ def test_explicit_proxy_with_user_auth
uri = URI.parse @proxy_uri
uri.user, uri.password = 'user', 'my%20pass'
fetcher = Gem::RemoteFetcher.new uri.to_s
- proxy = fetcher.instance_variable_get("@proxy_uri")
+ proxy = Gem::Request.new(nil, nil, nil, uri.to_s).instance_variable_get("@proxy_uri")
assert_equal 'user', proxy.user
- assert_equal 'my pass', fetcher.unescape(proxy.password)
+ assert_equal 'my pass', Gem::UriFormatter.new(proxy.password).unescape
assert_data_from_proxy fetcher.fetch_path(@server_uri)
end
end
@@ -416,7 +416,7 @@ def test_explicit_proxy_with_user_auth_in_env
ENV['http_proxy_user'] = 'foo'
ENV['http_proxy_pass'] = 'bar'
fetcher = Gem::RemoteFetcher.new nil
- proxy = fetcher.instance_variable_get("@proxy_uri")
+ proxy = Gem::Request.new(nil, nil, nil, nil).instance_variable_get("@proxy_uri")
assert_equal 'foo', proxy.user
assert_equal 'bar', proxy.password
assert_data_from_proxy fetcher.fetch_path(@server_uri)
@@ -427,9 +427,9 @@ def test_explicit_proxy_with_user_auth_in_env
ENV['http_proxy_user'] = 'foo\user'
ENV['http_proxy_pass'] = 'my bar'
fetcher = Gem::RemoteFetcher.new nil
- proxy = fetcher.instance_variable_get("@proxy_uri")
- assert_equal 'foo\user', fetcher.unescape(proxy.user)
- assert_equal 'my bar', fetcher.unescape(proxy.password)
+ proxy = Gem::Request.new(nil, nil, nil, nil).instance_variable_get("@proxy_uri")
+ assert_equal 'foo\user', Gem::UriFormatter.new(proxy.user).unescape
+ assert_equal 'my bar', Gem::UriFormatter.new(proxy.password).unescape
assert_data_from_proxy fetcher.fetch_path(@server_uri)
end
end
@@ -520,7 +520,7 @@ def test_get_proxy_from_env_auto_normalizes
fetcher = Gem::RemoteFetcher.new(nil)
ENV['HTTP_PROXY'] = 'fakeurl:12345'
- assert_equal('http://fakeurl:12345', fetcher.get_proxy_from_env.to_s)
+ assert_equal('http://fakeurl:12345', Gem::Request.new(nil, nil, nil, nil).get_proxy_from_env.to_s)
end
def test_get_proxy_from_env_empty
@@ -532,7 +532,7 @@ def test_get_proxy_from_env_empty
fetcher = Gem::RemoteFetcher.new nil
- assert_equal nil, fetcher.send(:get_proxy_from_env)
+ assert_equal nil, Gem::Request.new(nil, nil, nil, nil).get_proxy_from_env
ensure
orig_env_HTTP_PROXY.nil? ? ENV.delete('HTTP_PROXY') :
@@ -576,9 +576,7 @@ def test_fetch_http
fetcher = Gem::RemoteFetcher.new nil
url = 'http://gems.example.com/redirect'
- conn = Object.new
- def conn.started?() true end
- def conn.request(req)
+ def fetcher.request(uri, request_class, last_modified = nil)
url = 'http://gems.example.com/redirect'
unless defined? @requested then
@requested = true
@@ -592,9 +590,6 @@ def res.body() 'real_path' end
end
end
- conn = { "#{Thread.current.object_id}:gems.example.com:80" => conn }
- fetcher.instance_variable_set :@connections, conn
-
data = fetcher.fetch_http URI.parse(url)
assert_equal 'real_path', data
@@ -604,18 +599,13 @@ def test_fetch_http_redirects
fetcher = Gem::RemoteFetcher.new nil
url = 'http://gems.example.com/redirect'
- conn = Object.new
- def conn.started?() true end
- def conn.request(req)
+ def fetcher.request(uri, request_class, last_modified = nil)
url = 'http://gems.example.com/redirect'
res = Net::HTTPMovedPermanently.new nil, 301, nil
res.add_field 'Location', url
res
end
- conn = { "#{Thread.current.object_id}:gems.example.com:80" => conn }
- fetcher.instance_variable_set :@connections, conn
-
e = assert_raises Gem::RemoteFetcher::FetchError do
fetcher.fetch_http URI.parse(url)
end
@@ -625,9 +615,10 @@ def conn.request(req)
def test_request
uri = URI.parse "#{@gem_repo}/specs.#{Gem.marshal_version}"
+ @request = Gem::Request.new(uri, Net::HTTP::Get, nil, nil)
util_stub_connection_for :body => :junk, :code => 200
- response = @fetcher.request uri, Net::HTTP::Get
+ response = @request.fetch
assert_equal 200, response.code
assert_equal :junk, response.body
@@ -635,8 +626,10 @@ def test_request
def test_request_head
uri = URI.parse "#{@gem_repo}/specs.#{Gem.marshal_version}"
+ @request = Gem::Request.new(uri, Net::HTTP::Get, nil, nil)
util_stub_connection_for :body => '', :code => 200
- response = @fetcher.request uri, Net::HTTP::Head
+
+ response = @request.fetch
assert_equal 200, response.code
assert_equal '', response.body
@@ -644,10 +637,11 @@ def test_request_head
def test_request_unmodified
uri = URI.parse "#{@gem_repo}/specs.#{Gem.marshal_version}"
+ t = Time.now
+ @request = Gem::Request.new(uri, Net::HTTP::Get, t, nil)
conn = util_stub_connection_for :body => '', :code => 304
- t = Time.now
- response = @fetcher.request uri, Net::HTTP::Head, t
+ response = @request.fetch
assert_equal 304, response.code
assert_equal '', response.body
@@ -656,7 +650,7 @@ def test_request_unmodified
end
def test_user_agent
- ua = @fetcher.user_agent
+ ua = Gem::Request.new(nil, nil, nil, nil).user_agent
assert_match %r%^RubyGems/\S+ \S+ Ruby/\S+ \(.*?\)%, ua
assert_match %r%RubyGems/#{Regexp.escape Gem::VERSION}%, ua
@@ -671,7 +665,7 @@ def test_user_agent_engine
Object.send :remove_const, :RUBY_ENGINE if defined?(RUBY_ENGINE)
Object.send :const_set, :RUBY_ENGINE, 'vroom'
- ua = @fetcher.user_agent
+ ua = Gem::Request.new(nil, nil, nil, nil).user_agent
assert_match %r%\) vroom%, ua
ensure
@@ -684,7 +678,7 @@ def test_user_agent_engine_ruby
Object.send :remove_const, :RUBY_ENGINE if defined?(RUBY_ENGINE)
Object.send :const_set, :RUBY_ENGINE, 'ruby'
- ua = @fetcher.user_agent
+ ua = Gem::Request.new(nil, nil, nil, nil).user_agent
assert_match %r%\)%, ua
ensure
@@ -697,7 +691,7 @@ def test_user_agent_patchlevel
Object.send :remove_const, :RUBY_PATCHLEVEL
Object.send :const_set, :RUBY_PATCHLEVEL, 5
- ua = @fetcher.user_agent
+ ua = Gem::Request.new(nil, nil, nil, nil).user_agent
assert_match %r% patchlevel 5\)%, ua
ensure
@@ -712,7 +706,7 @@ def test_user_agent_revision
Object.send :remove_const, :RUBY_REVISION if defined?(RUBY_REVISION)
Object.send :const_set, :RUBY_REVISION, 6
- ua = @fetcher.user_agent
+ ua = Gem::Request.new(nil, nil, nil, nil).user_agent
assert_match %r% revision 6\)%, ua
assert_match %r%Ruby/#{Regexp.escape RUBY_VERSION}dev%, ua
@@ -727,7 +721,7 @@ def test_user_agent_revision_missing
Object.send :const_set, :RUBY_PATCHLEVEL, -1
Object.send :remove_const, :RUBY_REVISION if defined?(RUBY_REVISION)
- ua = @fetcher.user_agent
+ ua = Gem::Request.new(nil, nil, nil, nil).user_agent
assert_match %r%\(#{Regexp.escape RUBY_RELEASE_DATE}\)%, ua
ensure
@@ -743,15 +737,15 @@ def test_yaml_error_on_size
end
def util_stub_connection_for hash
- def @fetcher.connection= conn
+ def @request.connection= conn
@conn = conn
end
- def @fetcher.connection_for uri
+ def @request.connection_for uri
@conn
end
- @fetcher.connection = Conn.new OpenStruct.new(hash)
+ @request.connection = Conn.new OpenStruct.new(hash)
end
def assert_error(exception_class=Exception)
Something went wrong with that request. Please try again.