From 6b3ab5b6160ca3b3da2714821e80f9a2cc13e2a4 Mon Sep 17 00:00:00 2001 From: Theodor Tonum Date: Tue, 21 May 2024 10:33:58 +0200 Subject: [PATCH] Replace RestClient with Faraday --- Gemfile.lock | 10 +- auth0.gemspec | 2 +- lib/auth0/mixins.rb | 1 - lib/auth0/mixins/httpproxy.rb | 59 ++++-- .../api/authentication_endpoints_spec.rb | 48 ++--- spec/lib/auth0/mixins/httpproxy_spec.rb | 189 +++++++++--------- spec/lib/auth0/mixins/initializer_spec.rb | 10 +- .../lib/auth0/mixins/token_management_spec.rb | 10 +- spec/support/dummy_class_for_restclient.rb | 2 - spec/support/stub_response.rb | 2 +- 10 files changed, 181 insertions(+), 152 deletions(-) delete mode 100644 spec/support/dummy_class_for_restclient.rb diff --git a/Gemfile.lock b/Gemfile.lock index 5994c16a..d1a29d3e 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -3,8 +3,8 @@ PATH specs: auth0 (5.18.0) addressable (~> 2.8) + faraday (~> 2.9) jwt (~> 2.7) - rest-client (~> 2.1) retryable (~> 3.0) zache (~> 0.12) @@ -71,6 +71,12 @@ GEM erubi (1.13.0) faker (2.23.0) i18n (>= 1.8.11, < 2) + faraday (2.12.2) + faraday-net_http (>= 2.0, < 3.5) + json + logger + faraday-net_http (3.4.0) + net-http (>= 0.5.0) ffi (1.17.0-aarch64-linux-gnu) ffi (1.17.0-aarch64-linux-musl) ffi (1.17.0-arm-linux-gnu) @@ -129,6 +135,8 @@ GEM minitest (5.25.2) multi_json (1.15.0) nenv (0.3.0) + net-http (0.6.0) + uri netrc (0.11.0) nokogiri (1.16.7-aarch64-linux) racc (~> 1.4) diff --git a/auth0.gemspec b/auth0.gemspec index 2074d027..bf030805 100644 --- a/auth0.gemspec +++ b/auth0.gemspec @@ -16,7 +16,7 @@ Gem::Specification.new do |s| s.executables = `git ls-files -- bin/*`.split("\n").map { |f| File.basename(f) } s.require_paths = ['lib'] - s.add_runtime_dependency 'rest-client', '~> 2.1' + s.add_runtime_dependency 'faraday', '~> 2.9' s.add_runtime_dependency 'jwt', '~> 2.7' s.add_runtime_dependency 'zache', '~> 0.12' s.add_runtime_dependency 'addressable', '~> 2.8' diff --git a/lib/auth0/mixins.rb b/lib/auth0/mixins.rb index e6b40f30..ea50e12a 100644 --- a/lib/auth0/mixins.rb +++ b/lib/auth0/mixins.rb @@ -1,5 +1,4 @@ require 'base64' -require 'rest-client' require 'uri' require 'auth0/mixins/access_token_struct' diff --git a/lib/auth0/mixins/httpproxy.rb b/lib/auth0/mixins/httpproxy.rb index f4446c47..08319eec 100644 --- a/lib/auth0/mixins/httpproxy.rb +++ b/lib/auth0/mixins/httpproxy.rb @@ -1,8 +1,40 @@ require "addressable/uri" +require "faraday" require "retryable" require_relative "../exception.rb" module Auth0 + # Shim for Faraday with interface similar to RestClient + class HttpClient + def self.execute(method:, url:, payload:, headers:, timeout:) + params = headers.delete(:params) + case method + when :get + Faraday.get(url, params, headers) do |req| + req.options[:timeout] = timeout + end + when :post + Faraday.post(url, payload, headers) do |req| + req.options[:timeout] = timeout + end + when :patch + Faraday.patch(url, payload, headers) do |req| + req.options[:timeout] = timeout + end + when :put + Faraday.put(url, payload, headers) do |req| + req.options[:timeout] = timeout + end + when :delete + Faraday.delete(url, params, headers) do |req| + req.options[:timeout] = timeout + end + else + raise 'Unsupported HTTP method' + end + end + end + module Mixins # here's the proxy for Rest calls based on rest-client, we're building all request on that gem # for now, if you want to feel free to use your own http client @@ -95,33 +127,28 @@ def request(method, uri, body = {}, extra_headers = {}) call(method, encode_uri(uri), timeout, headers, body.to_json) end - case result.code + case result.status when 200...226 then safe_parse_json(result.body) - when 400 then raise Auth0::BadRequest.new(result.body, code: result.code, headers: result.headers) - when 401 then raise Auth0::Unauthorized.new(result.body, code: result.code, headers: result.headers) - when 403 then raise Auth0::AccessDenied.new(result.body, code: result.code, headers: result.headers) - when 404 then raise Auth0::NotFound.new(result.body, code: result.code, headers: result.headers) - when 429 then raise Auth0::RateLimitEncountered.new(result.body, code: result.code, headers: result.headers) - when 500 then raise Auth0::ServerError.new(result.body, code: result.code, headers: result.headers) - else raise Auth0::Unsupported.new(result.body, code: result.code, headers: result.headers) + when 400 then raise Auth0::BadRequest.new(result.body, code: result.status, headers: result.headers) + when 401 then raise Auth0::Unauthorized.new(result.body, code: result.status, headers: result.headers) + when 403 then raise Auth0::AccessDenied.new(result.body, code: result.status, headers: result.headers) + when 404 then raise Auth0::NotFound.new(result.body, code: result.status, headers: result.headers) + when 429 then raise Auth0::RateLimitEncountered.new(result.body, code: result.status, headers: result.headers) + when 500 then raise Auth0::ServerError.new(result.body, code: result.status, headers: result.headers) + else raise Auth0::Unsupported.new(result.body, code: result.status, headers: result.headers) end end def call(method, url, timeout, headers, body = nil) - RestClient::Request.execute( + Auth0::HttpClient.execute( method: method, url: url, timeout: timeout, headers: headers, payload: body ) - rescue RestClient::Exception => e - case e - when RestClient::RequestTimeout - raise Auth0::RequestTimeout.new(e.message) - else - return e.response - end + rescue Faraday::RequestTimeoutError => e + raise Auth0::RequestTimeout.new(e.message) end end end diff --git a/spec/lib/auth0/api/authentication_endpoints_spec.rb b/spec/lib/auth0/api/authentication_endpoints_spec.rb index 299184de..005cf3f0 100644 --- a/spec/lib/auth0/api/authentication_endpoints_spec.rb +++ b/spec/lib/auth0/api/authentication_endpoints_spec.rb @@ -49,7 +49,7 @@ context 'AuthenticationEndponts' do context 'api_token' do it 'requests a new token using client_secret' do - expect(RestClient::Request).to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).to receive(:execute).with(hash_including( method: :post, url: 'https://samples.auth0.com/oauth/token', payload: { @@ -76,7 +76,7 @@ end it 'requests a new token using organization' do - expect(RestClient::Request).to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).to receive(:execute).with(hash_including( method: :post, url: 'https://samples.auth0.com/oauth/token', payload: { @@ -103,7 +103,7 @@ end it 'requests a new token using client_assertion' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -135,7 +135,7 @@ context 'exchange_auth_code_for_tokens' do it 'requests a new token using client_secret' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -168,7 +168,7 @@ end it 'requests a new token using client_assertion' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -201,7 +201,7 @@ context 'exchange_refresh_token' do it 'exchanges the refresh token using a client secret' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -233,7 +233,7 @@ end it 'exchanges the refresh token using client_assertion' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -268,7 +268,7 @@ context 'exchange_sms_otp_for_tokens' do it 'requests the tokens using an OTP from SMS' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -304,7 +304,7 @@ end it 'requests the tokens using OTP from SMS, and overrides scope and audience' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -337,7 +337,7 @@ end it 'requests the tokens using an OTP from SMS using client assertion' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -366,7 +366,7 @@ context 'exchange_email_otp_for_tokens' do it 'requests the tokens using email OTP' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -402,7 +402,7 @@ end it 'requests the tokens using OTP from email, and overrides scope and audience' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -430,7 +430,7 @@ end it 'requests the tokens using OTP from email using client assertion' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -462,7 +462,7 @@ context 'login_with_resource_owner' do it 'logs in using a client secret' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -498,7 +498,7 @@ end it 'logs in using a client secret, realm and audience' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -534,7 +534,7 @@ end it 'logs in using client assertion' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -568,7 +568,7 @@ context 'start_passwordless_email_flow' do it 'starts passwordless flow using a client secret' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -592,7 +592,7 @@ end it 'starts passwordless email flow using client assertion' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -615,7 +615,7 @@ context 'start_passwordless_sms_flow' do it 'starts passwordless flow using a client secret' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -637,7 +637,7 @@ end it 'starts passwordless email flow using client assertion' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to match( include( method: :post, @@ -675,7 +675,7 @@ context 'pushed_authorization_request' do it 'sends the request as a form post' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg[:url]).to eq('https://samples.auth0.com/oauth/par') expect(arg[:method]).to eq(:post) @@ -692,7 +692,7 @@ end it 'allows the RestClient to handle the correct header defaults' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg[:headers]).not_to have_key('Content-Type') StubResponse.new({}, true, 200) @@ -703,7 +703,7 @@ end it 'sends the request as a form post with all known overrides' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg[:url]).to eq('https://samples.auth0.com/oauth/par') expect(arg[:method]).to eq(:post) @@ -733,7 +733,7 @@ end it 'sends the request as a form post using client assertion' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg[:url]).to eq('https://samples.auth0.com/oauth/par') expect(arg[:method]).to eq(:post) expect(arg[:payload][:client_secret]).to be_nil diff --git a/spec/lib/auth0/mixins/httpproxy_spec.rb b/spec/lib/auth0/mixins/httpproxy_spec.rb index 40211896..9aecf04d 100644 --- a/spec/lib/auth0/mixins/httpproxy_spec.rb +++ b/spec/lib/auth0/mixins/httpproxy_spec.rb @@ -9,14 +9,13 @@ dummy_instance.retry_count = 0 @instance = dummy_instance - @exception = DummyClassForRestClient.new end %i(get delete).each do |http_method| context ".#{http_method}" do it { expect(@instance).to respond_to(http_method.to_sym) } it "should call send http #{http_method} method to path defined through HTTP" do - expect(RestClient::Request).to receive(:execute).with(method: http_method, + expect(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, @@ -26,7 +25,7 @@ end it 'should not raise exception if data returned not in json format (should be fixed in v2)' do - allow(RestClient::Request).to receive(:execute).with(method: http_method, + allow(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, @@ -38,7 +37,7 @@ it "should raise Auth0::Unauthorized on send http #{http_method} method to path defined through HTTP when 401 status received" do - expect(RestClient::Request).to receive(:execute).with(method: http_method, + expect(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, @@ -49,7 +48,7 @@ it "should raise Auth0::NotFound on send http #{http_method} method to path defined through HTTP when 404 status received" do - expect(RestClient::Request).to receive(:execute).with(method: http_method, + expect(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, @@ -60,7 +59,7 @@ it "should raise Auth0::Unsupported on send http #{http_method} method to path defined through HTTP when 418 or other unknown status received" do - expect(RestClient::Request).to receive(:execute).with(method: http_method, + expect(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, @@ -71,36 +70,34 @@ it "should raise Auth0::RequestTimeout on send http #{http_method} method to path defined through HTTP when RestClient::RequestTimeout received" do - allow(RestClient::Request).to receive(:execute).with(method: http_method, + allow(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, payload: nil) - .and_raise(RestClient::Exceptions::OpenTimeout.new) + .and_raise(Faraday::RequestTimeoutError.new) expect { @instance.send(http_method, '/test') }.to raise_error(Auth0::RequestTimeout) end it "should raise Auth0::BadRequest on send http #{http_method} method to path defined through HTTP when 400 status received" do - @exception.response = StubResponse.new({}, false, 400) - allow(RestClient::Request).to receive(:execute).with(method: http_method, + allow(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, payload: nil) - .and_raise(@exception) + .and_return(StubResponse.new({}, false, 400)) expect { @instance.send(http_method, '/test') }.to raise_error(Auth0::BadRequest) end it "should raise Auth0::AccessDenied on send http #{http_method} method to path defined through HTTP when 403" do - @exception.response = StubResponse.new({}, false, 403) - allow(RestClient::Request).to receive(:execute).with(method: http_method, + allow(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, payload: nil) - .and_raise(@exception) + .and_return(StubResponse.new({}, false, 403)) expect { @instance.send(http_method, '/test') }.to raise_error(Auth0::AccessDenied) end @@ -111,13 +108,13 @@ :x_ratelimit_remaining => 0, :x_ratelimit_reset => 1560564149 } - @exception.response = StubResponse.new({}, false, 429, headers) - allow(RestClient::Request).to receive(:execute).with(method: http_method, + response = StubResponse.new({}, false, 429, headers) + allow(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, payload: nil) - .and_raise(@exception) + .and_return(response) expect { @instance.send(http_method, '/test') }.to raise_error { |error| expect(error).to be_a(Auth0::RateLimitEncountered) expect(error).to have_attributes( @@ -134,18 +131,18 @@ it "should raise Auth0::ServerError on send http #{http_method} method to path defined through HTTP when 500 received" do - @exception.response = StubResponse.new({}, false, 500) - allow(RestClient::Request).to receive(:execute).with(method: http_method, + response = StubResponse.new({}, false, 500) + allow(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, payload: nil) - .and_raise(@exception) + .and_return(response) expect { @instance.send(http_method, '/test') }.to raise_error(Auth0::ServerError) end it 'should normalize path with Addressable::URI' do - expect(RestClient::Request).to receive(:execute).with(method: http_method, + expect(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/te%20st%23test', timeout: nil, headers: { params: {} }, @@ -160,14 +157,14 @@ retry_instance.extend(Auth0::Mixins::HTTPProxy) retry_instance.base_uri = "https://auth0.com" - @exception.response = StubResponse.new({}, false, 429) - allow(RestClient::Request).to receive(:execute).with(method: http_method, + response = StubResponse.new({}, false, 429) + allow(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, payload: nil) - .and_raise(@exception) - expect(RestClient::Request).to receive(:execute).exactly(4).times + .and_return(response) + expect(Auth0::HttpClient).to receive(:execute).exactly(4).times expect { retry_instance.send(http_method, '/test') }.to raise_error { |error| expect(error).to be_a(Auth0::RateLimitEncountered) @@ -180,14 +177,14 @@ retry_instance.base_uri = "https://auth0.com" retry_instance.retry_count = 2 - @exception.response = StubResponse.new({}, false, 429) - allow(RestClient::Request).to receive(:execute).with(method: http_method, + response = StubResponse.new({}, false, 429) + allow(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, payload: nil) - .and_raise(@exception) - expect(RestClient::Request).to receive(:execute).exactly(3).times + .and_return(response) + expect(Auth0::HttpClient).to receive(:execute).exactly(3).times expect { retry_instance.send(http_method, '/test') }.to raise_error { |error| expect(error).to be_a(Auth0::RateLimitEncountered) @@ -200,16 +197,16 @@ retry_instance.base_uri = "https://auth0.com" retry_instance.retry_count = 0 - @exception.response = StubResponse.new({}, false, 429) + response = StubResponse.new({}, false, 429) - allow(RestClient::Request).to receive(:execute).with(method: http_method, + allow(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, payload: nil) - .and_raise(@exception) - - expect(RestClient::Request).to receive(:execute).exactly(1).times + .and_return(response) + + expect(Auth0::HttpClient).to receive(:execute).exactly(1).times expect { retry_instance.send(http_method, '/test') }.to raise_error { |error| expect(error).to be_a(Auth0::RateLimitEncountered) } @@ -223,8 +220,7 @@ time_entries = [] @time_start - @exception.response = StubResponse.new({}, false, 429) - allow(RestClient::Request).to receive(:execute).with(method: http_method, + allow(Auth0::HttpClient).to receive(:execute).with(method: http_method, url: 'https://auth0.com/test', timeout: nil, headers: { params: {} }, @@ -232,7 +228,8 @@ time_entries.push(Time.now.to_f - @time_start.to_f) @time_start = Time.now.to_f # restart the clock - raise @exception + + StubResponse.new({}, false, 429) end @time_start = Time.now.to_f #start the clock @@ -259,7 +256,7 @@ def expected_payload(method, overrides = {}) headers: nil, payload: {} }.merge(overrides) - else + else { method: method, url: 'https://auth0.com/test', @@ -274,13 +271,13 @@ def expected_payload(method, overrides = {}) context ".#{http_method}" do it { expect(@instance).to respond_to(http_method.to_sym) } it "should call send http #{http_method} method to path defined through HTTP"do - expect(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) + expect(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) .and_return(StubResponse.new({}, true, 200)) expect { @instance.send(http_method, '/test') }.not_to raise_error end it 'should not raise exception if data returned not in json format (should be fixed in v2)' do - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) .and_return(StubResponse.new('Some random text here', true, 200)) expect { @instance.send(http_method, '/test') }.not_to raise_error expect(@instance.send(http_method, '/test')).to eql('Some random text here') @@ -288,9 +285,9 @@ def expected_payload(method, overrides = {}) it "should raise Auth0::Unauthorized on send http #{http_method} method to path defined through HTTP when 401 status received" do - @exception.response = StubResponse.new({}, false, 401) - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) - .and_raise(@exception) + response = StubResponse.new({}, false, 401) + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) + .and_return(response) expect { @instance.send(http_method, '/test') }.to raise_error(Auth0::Unauthorized) end @@ -301,9 +298,9 @@ def expected_payload(method, overrides = {}) :x_ratelimit_remaining => 0, :x_ratelimit_reset => 1560564149 } - @exception.response = StubResponse.new({}, false, 429,headers) - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) - .and_raise(@exception) + response = StubResponse.new({}, false, 429,headers) + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) + .and_return(response) expect { @instance.send(http_method, '/test') }.to raise_error { |error| expect(error).to be_a(Auth0::RateLimitEncountered) expect(error).to have_attributes( @@ -320,45 +317,45 @@ def expected_payload(method, overrides = {}) it "should raise Auth0::NotFound on send http #{http_method} method to path defined through HTTP when 404 status received" do - @exception.response = StubResponse.new({}, false, 404) - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) - .and_raise(@exception) + response = StubResponse.new({}, false, 404) + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) + .and_return(response) expect { @instance.send(http_method, '/test') }.to raise_error(Auth0::NotFound) end it "should raise Auth0::Unsupported on send http #{http_method} method to path defined through HTTP when 418 or other unknown status received" do - @exception.response = StubResponse.new({}, false, 418) - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) - .and_raise(@exception) + response = StubResponse.new({}, false, 418) + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) + .and_return(response) expect { @instance.send(http_method, '/test') }.to raise_error(Auth0::Unsupported) end it "should raise Auth0::RequestTimeout on send http #{http_method} method to path defined through HTTP when RestClient::RequestTimeout received" do - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) - .and_raise(RestClient::Exceptions::OpenTimeout.new) + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) + .and_raise(Faraday::RequestTimeoutError.new) expect { @instance.send(http_method, '/test') }.to raise_error(Auth0::RequestTimeout) end it "should raise Auth0::BadRequest on send http #{http_method} method to path defined through HTTP when 400 status received" do - @exception.response = StubResponse.new({}, false, 400) - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) - .and_raise(@exception) + response = StubResponse.new({}, false, 400) + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) + .and_return(response) expect { @instance.send(http_method, '/test') }.to raise_error(Auth0::BadRequest) end it "should raise Auth0::ServerError on send http #{http_method} method to path defined through HTTP when 500 received" do - @exception.response = StubResponse.new({}, false, 500) - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) - .and_raise(@exception) + response = StubResponse.new({}, false, 500) + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) + .and_return(response) expect { @instance.send(http_method, '/test') }.to raise_error(Auth0::ServerError) end it 'should normalize path with Addressable::URI' do - expect(RestClient::Request).to receive(:execute).with(expected_payload(http_method, url: 'https://auth0.com/te%20st')) + expect(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method, url: 'https://auth0.com/te%20st')) .and_return(StubResponse.new({}, true, 200)) expect { @instance.send(http_method, '/te st') }.not_to raise_error end @@ -369,7 +366,7 @@ def expected_payload(method, overrides = {}) 'message' => "Path validation error: 'String does not match pattern ^.+\\|.+$: 3241312' on property id (The user_id of the user to retrieve).", 'errorCode' => 'invalid_uri') - expect(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) + expect(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) .and_return(StubResponse.new(res, true, 404)) expect { @instance.send(http_method, '/test') }.to raise_error(Auth0::NotFound, res) end @@ -380,10 +377,10 @@ def expected_payload(method, overrides = {}) retry_instance.extend(Auth0::Mixins::HTTPProxy) retry_instance.base_uri = "https://auth0.com" - @exception.response = StubResponse.new({}, false, 429) - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) - .and_raise(@exception) - expect(RestClient::Request).to receive(:execute).exactly(4).times + response = StubResponse.new({}, false, 429) + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) + .and_return(response) + expect(Auth0::HttpClient).to receive(:execute).exactly(4).times expect { retry_instance.send(http_method, '/test') }.to raise_error { |error| expect(error).to be_a(Auth0::RateLimitEncountered) @@ -396,10 +393,10 @@ def expected_payload(method, overrides = {}) retry_instance.base_uri = "https://auth0.com" retry_instance.retry_count = 2 - @exception.response = StubResponse.new({}, false, 429) - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) - .and_raise(@exception) - expect(RestClient::Request).to receive(:execute).exactly(3).times + response = StubResponse.new({}, false, 429) + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) + .and_return(response) + expect(Auth0::HttpClient).to receive(:execute).exactly(3).times expect { retry_instance.send(http_method, '/test') }.to raise_error { |error| expect(error).to be_a(Auth0::RateLimitEncountered) @@ -412,12 +409,12 @@ def expected_payload(method, overrides = {}) retry_instance.base_uri = "https://auth0.com" retry_instance.retry_count = 0 - @exception.response = StubResponse.new({}, false, 429) + response = StubResponse.new({}, false, 429) - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) - .and_raise(@exception) - - expect(RestClient::Request).to receive(:execute).exactly(1).times + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) + .and_return(response) + + expect(Auth0::HttpClient).to receive(:execute).exactly(1).times expect { retry_instance.send(http_method, '/test') }.to raise_error { |error| expect(error).to be_a(Auth0::RateLimitEncountered) } @@ -431,12 +428,12 @@ def expected_payload(method, overrides = {}) time_entries = [] @time_start - @exception.response = StubResponse.new({}, false, 429) - allow(RestClient::Request).to receive(:execute).with(expected_payload(http_method)) do + allow(Auth0::HttpClient).to receive(:execute).with(expected_payload(http_method)) do time_entries.push(Time.now.to_f - @time_start.to_f) @time_start = Time.now.to_f # restart the clock - raise @exception + + StubResponse.new({}, false, 429) end @time_start = Time.now.to_f #start the clock @@ -467,16 +464,16 @@ def expected_payload(method, overrides = {}) %i(get delete).each do |http_method| context "for #{http_method}" do it 'should renew the token' do - expect(RestClient::Request).to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).to receive(:execute).with(hash_including( method: :post, url: 'https://auth0.com/oauth/token', - )).and_return(StubResponse.new({ - "access_token" => "access_token", - "expires_in" => 86400}, - true, + )).and_return(StubResponse.new({ + "access_token" => "access_token", + "expires_in" => 86400}, + true, 200)) - expect(RestClient::Request).to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).to receive(:execute).with(hash_including( method: http_method, url: 'https://auth0.com/test' )).and_return(StubResponse.new('Some random text here', true, 200)) @@ -489,16 +486,16 @@ def expected_payload(method, overrides = {}) %i(post put patch).each do |http_method| context "for #{http_method}" do it 'should renew the token' do - expect(RestClient::Request).to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).to receive(:execute).with(hash_including( method: :post, url: 'https://auth0.com/oauth/token', - ) ).and_return(StubResponse.new({ - "access_token" => "access_token", - "expires_in" => 86400}, - true, + ) ).and_return(StubResponse.new({ + "access_token" => "access_token", + "expires_in" => 86400}, + true, 200)) - expect(RestClient::Request).to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).to receive(:execute).with(hash_including( method: http_method, url: 'https://auth0.com/test', headers: hash_including( "Authorization" => "Bearer access_token") @@ -522,12 +519,12 @@ def expected_payload(method, overrides = {}) %i(get delete).each do |http_method| context "for #{http_method}" do it 'should use the cached token' do - expect(RestClient::Request).not_to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).not_to receive(:execute).with(hash_including( method: :post, url: 'https://auth0.com/oauth/token', )) - expect(RestClient::Request).to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).to receive(:execute).with(hash_including( method: http_method, url: 'https://auth0.com/test', headers: hash_including(params: {}, "Authorization" => "Bearer access_token") @@ -541,12 +538,12 @@ def expected_payload(method, overrides = {}) %i(post put patch).each do |http_method| context "for #{http_method}" do it 'should use the cached token' do - expect(RestClient::Request).not_to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).not_to receive(:execute).with(hash_including( method: :post, url: 'https://auth0.com/oauth/token', )) - expect(RestClient::Request).to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).to receive(:execute).with(hash_including( method: http_method, url: 'https://auth0.com/test', headers: hash_including("Authorization" => "Bearer access_token") @@ -573,7 +570,7 @@ def expected_payload(method, overrides = {}) %i(get delete).each do |http_get_delete| %i(post patch put).each do |http_ppp| it "should not bleed :#{http_get_delete} headers/parameters to the subsequent :#{http_ppp} request" do - expect(RestClient::Request).to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).to receive(:execute).with(hash_including( method: http_get_delete, url: "https://auth0.com/test-#{http_get_delete}", headers: hash_including(params: { email: 'test@test.com' }) @@ -581,7 +578,7 @@ def expected_payload(method, overrides = {}) # email: parameter that is sent in the GET request should not appear # as a parameter in the `headers` hash for the subsequent PATCH request. - expect(RestClient::Request).to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).to receive(:execute).with(hash_including( method: http_ppp, url: "https://auth0.com/test-#{http_ppp}", headers: hash_not_including(:params) diff --git a/spec/lib/auth0/mixins/initializer_spec.rb b/spec/lib/auth0/mixins/initializer_spec.rb index 0fc4058a..de51f514 100644 --- a/spec/lib/auth0/mixins/initializer_spec.rb +++ b/spec/lib/auth0/mixins/initializer_spec.rb @@ -68,7 +68,7 @@ class MockClass organization: nil } - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to(match( include( method: :post, @@ -98,7 +98,7 @@ class MockClass params[:api_identifier] = api_identifier = 'test' params[:client_assertion_signing_key] = private_key - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to(match( include( method: :post, @@ -130,7 +130,7 @@ class MockClass it "doesn't get a new token if one was supplied using 'token'" do params[:token] = 'access-token' - expect(RestClient::Request).not_to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).not_to receive(:execute).with(hash_including( method: :post, url: 'https://samples.auth0.com/oauth/token', )) @@ -142,7 +142,7 @@ class MockClass it "doesn't get a new token if one was supplied using 'access_token'" do params[:access_token] = 'access-token' - expect(RestClient::Request).not_to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).not_to receive(:execute).with(hash_including( method: :post, url: 'https://samples.auth0.com/oauth/token', )) @@ -155,7 +155,7 @@ class MockClass params[:token] = 'access-token' params[:token_expires_at] = time_now.to_i + 300 - expect(RestClient::Request).not_to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).not_to receive(:execute).with(hash_including( method: :post, url: 'https://samples.auth0.com/oauth/token', )) diff --git a/spec/lib/auth0/mixins/token_management_spec.rb b/spec/lib/auth0/mixins/token_management_spec.rb index 5e78e411..5a2323aa 100644 --- a/spec/lib/auth0/mixins/token_management_spec.rb +++ b/spec/lib/auth0/mixins/token_management_spec.rb @@ -35,7 +35,7 @@ context 'get_token' do it 'renews the token if there is no token set' do - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to(match( include( method: :post, @@ -61,7 +61,7 @@ params[:token] = 'test-token' params[:token_expires_at] = time_now.to_i + 86400 - expect(RestClient::Request).not_to receive(:execute).with(hash_including( + expect(Auth0::HttpClient).not_to receive(:execute).with(hash_including( method: :post, url: 'https://samples.auth0.com/oauth/token', )) @@ -76,7 +76,7 @@ params[:token] = 'test-token' params[:token_expires_at] = time_now.to_i + 5 - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to(match( include( method: :post, @@ -102,7 +102,7 @@ params[:token] = 'test-token' params[:token_expires_at] = time_now.to_i - 10 - expect(RestClient::Request).to receive(:execute) do |arg| + expect(Auth0::HttpClient).to receive(:execute) do |arg| expect(arg).to(match( include( method: :post, @@ -128,7 +128,7 @@ params[:token] = 'test-token' instance.instance_variable_set '@token_expires_at', nil - expect(RestClient::Request).not_to receive(:execute) + expect(Auth0::HttpClient).not_to receive(:execute) instance.send(:get_token) end diff --git a/spec/support/dummy_class_for_restclient.rb b/spec/support/dummy_class_for_restclient.rb deleted file mode 100644 index ef81d089..00000000 --- a/spec/support/dummy_class_for_restclient.rb +++ /dev/null @@ -1,2 +0,0 @@ -class DummyClassForRestClient < RestClient::Exception -end diff --git a/spec/support/stub_response.rb b/spec/support/stub_response.rb index ffd9dbd2..4713723e 100644 --- a/spec/support/stub_response.rb +++ b/spec/support/stub_response.rb @@ -1 +1 @@ -StubResponse = Struct.new(:body, :success?, :code, :headers) +StubResponse = Struct.new(:body, :success?, :status, :headers)