From 4ba9f7ee6374ec25abb870f769059b162ad7642a Mon Sep 17 00:00:00 2001 From: Andy Brody Date: Thu, 4 May 2017 01:20:00 -0400 Subject: [PATCH] Skip netrc with Authorization header, up/downcase. The fix for the Netrc user/password overriding a user-set Authorization header that was committed in #374 was case-sensitive and does not cover users who pass `:authorization` or `"authorization"` as the header name. Add @processed_headers_lowercase so that case-insensitive tests like this are easier in the future. It would be better if `Request#stringify_headers` normalized both Symbols and Strings. https://github.com/rest-client/rest-client/issues/599 Also add a test for the case-insensitive behavior. Fixes: #524, #550 --- lib/restclient/request.rb | 18 +++++++++++++++++- spec/unit/request_spec.rb | 13 +++++++------ 2 files changed, 24 insertions(+), 7 deletions(-) diff --git a/lib/restclient/request.rb b/lib/restclient/request.rb index 6dbf980..57e9c4f 100644 --- a/lib/restclient/request.rb +++ b/lib/restclient/request.rb @@ -146,6 +146,7 @@ module RestClient @log = args[:log] @max_redirects = args[:max_redirects] || 10 @processed_headers = make_headers headers + @processed_headers_lowercase = Hash[@processed_headers.map {|k, v| [k.downcase, v]}] @args = args @before_execution_proc = args[:before_execution_proc] @@ -368,6 +369,13 @@ module RestClient # - headers from the payload object (e.g. Content-Type, Content-Lenth) # - cookie headers from #make_cookie_header # + # BUG: stringify_headers does not alter the capitalization of headers that + # are passed as strings, it only normalizes those passed as symbols. This + # behavior will probably remain for a while for compatibility, but it means + # that the warnings that attempt to detect accidental header overrides may + # not always work. + # https://github.com/rest-client/rest-client/issues/599 + # # @param [Hash] user_headers User-provided headers to include # # @return [Hash] A hash of HTTP headers => values @@ -536,6 +544,12 @@ module RestClient end # Return a hash of headers whose keys are capitalized strings + # + # BUG: stringify_headers does not fix the capitalization of headers that + # are already Strings. Leaving this behavior as is for now for + # backwards compatibility. + # https://github.com/rest-client/rest-client/issues/599 + # def stringify_headers headers headers.inject({}) do |result, (key, value)| if key.is_a? Symbol @@ -761,7 +775,9 @@ module RestClient end def setup_credentials(req) - req.basic_auth(user, password) if user && !headers.has_key?("Authorization") + if user && !@processed_headers_lowercase.include?('authorization') + req.basic_auth(user, password) + end end def fetch_body_to_tempfile(http_response) diff --git a/spec/unit/request_spec.rb b/spec/unit/request_spec.rb index 47e5299..f69494d 100644 --- a/spec/unit/request_spec.rb +++ b/spec/unit/request_spec.rb @@ -448,12 +448,13 @@ describe RestClient::Request, :include_helpers do end it "does not attempt to send credentials if Authorization header is set" do - @request.headers['Authorization'] = 'Token abc123' - allow(@request).to receive(:user).and_return('joe') - allow(@request).to receive(:password).and_return('mypass') - req = double("request") - expect(req).not_to receive(:basic_auth) - @request.send(:setup_credentials, req) + ['Authorization', 'authorization', 'auTHORization', :authorization].each do |authorization| + headers = {authorization => 'Token abc123'} + request = RestClient::Request.new(method: :get, url: 'http://some/resource', headers: headers, user: 'joe', password: 'mypass') + req = double("net::http request") + expect(req).not_to receive(:basic_auth) + request.send(:setup_credentials, req) + end end end