googleauth 0.5.1 → 0.11.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 (69) hide show
  1. checksums.yaml +5 -5
  2. data/{CONTRIBUTING.md → .github/CONTRIBUTING.md} +5 -4
  3. data/.github/ISSUE_TEMPLATE/bug_report.md +36 -0
  4. data/.github/ISSUE_TEMPLATE/feature_request.md +21 -0
  5. data/.github/ISSUE_TEMPLATE/support_request.md +7 -0
  6. data/.kokoro/build.bat +16 -0
  7. data/.kokoro/build.sh +4 -0
  8. data/.kokoro/continuous/common.cfg +24 -0
  9. data/.kokoro/continuous/linux.cfg +25 -0
  10. data/.kokoro/continuous/osx.cfg +8 -0
  11. data/.kokoro/continuous/post.cfg +30 -0
  12. data/.kokoro/continuous/windows.cfg +29 -0
  13. data/.kokoro/osx.sh +4 -0
  14. data/.kokoro/presubmit/common.cfg +24 -0
  15. data/.kokoro/presubmit/linux.cfg +24 -0
  16. data/.kokoro/presubmit/osx.cfg +8 -0
  17. data/.kokoro/presubmit/windows.cfg +29 -0
  18. data/.kokoro/release.cfg +94 -0
  19. data/.kokoro/trampoline.bat +10 -0
  20. data/.kokoro/trampoline.sh +4 -0
  21. data/.repo-metadata.json +5 -0
  22. data/.rubocop.yml +17 -1
  23. data/CHANGELOG.md +90 -19
  24. data/CODE_OF_CONDUCT.md +43 -0
  25. data/Gemfile +16 -13
  26. data/README.md +58 -18
  27. data/Rakefile +106 -10
  28. data/googleauth.gemspec +27 -25
  29. data/lib/googleauth/application_default.rb +81 -0
  30. data/lib/googleauth/client_id.rb +21 -19
  31. data/lib/googleauth/compute_engine.rb +40 -43
  32. data/lib/googleauth/credentials.rb +375 -0
  33. data/lib/googleauth/credentials_loader.rb +117 -43
  34. data/lib/googleauth/default_credentials.rb +93 -0
  35. data/lib/googleauth/iam.rb +11 -11
  36. data/lib/googleauth/json_key_reader.rb +46 -0
  37. data/lib/googleauth/scope_util.rb +12 -12
  38. data/lib/googleauth/service_account.rb +64 -62
  39. data/lib/googleauth/signet.rb +53 -12
  40. data/lib/googleauth/stores/file_token_store.rb +8 -8
  41. data/lib/googleauth/stores/redis_token_store.rb +22 -22
  42. data/lib/googleauth/token_store.rb +6 -6
  43. data/lib/googleauth/user_authorizer.rb +80 -68
  44. data/lib/googleauth/user_refresh.rb +44 -35
  45. data/lib/googleauth/version.rb +1 -1
  46. data/lib/googleauth/web_user_authorizer.rb +77 -68
  47. data/lib/googleauth.rb +6 -96
  48. data/rakelib/devsite_builder.rb +45 -0
  49. data/rakelib/link_checker.rb +64 -0
  50. data/rakelib/repo_metadata.rb +59 -0
  51. data/spec/googleauth/apply_auth_examples.rb +47 -46
  52. data/spec/googleauth/client_id_spec.rb +75 -55
  53. data/spec/googleauth/compute_engine_spec.rb +60 -43
  54. data/spec/googleauth/credentials_spec.rb +467 -0
  55. data/spec/googleauth/get_application_default_spec.rb +149 -111
  56. data/spec/googleauth/iam_spec.rb +25 -25
  57. data/spec/googleauth/scope_util_spec.rb +26 -24
  58. data/spec/googleauth/service_account_spec.rb +261 -143
  59. data/spec/googleauth/signet_spec.rb +93 -30
  60. data/spec/googleauth/stores/file_token_store_spec.rb +12 -13
  61. data/spec/googleauth/stores/redis_token_store_spec.rb +11 -11
  62. data/spec/googleauth/stores/store_examples.rb +16 -16
  63. data/spec/googleauth/user_authorizer_spec.rb +153 -124
  64. data/spec/googleauth/user_refresh_spec.rb +186 -121
  65. data/spec/googleauth/web_user_authorizer_spec.rb +82 -69
  66. data/spec/spec_helper.rb +21 -19
  67. metadata +75 -32
  68. data/.rubocop_todo.yml +0 -32
  69. data/.travis.yml +0 -37
@@ -27,45 +27,108 @@
27
27
  # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28
28
  # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29
29
 
30
- spec_dir = File.expand_path(File.join(File.dirname(__FILE__)))
31
- $LOAD_PATH.unshift(spec_dir)
30
+ spec_dir = File.expand_path File.join(File.dirname(__FILE__))
31
+ $LOAD_PATH.unshift spec_dir
32
32
  $LOAD_PATH.uniq!
33
33
 
34
- require 'apply_auth_examples'
35
- require 'googleauth/signet'
36
- require 'jwt'
37
- require 'openssl'
38
- require 'spec_helper'
34
+ require "apply_auth_examples"
35
+ require "googleauth/signet"
36
+ require "jwt"
37
+ require "openssl"
38
+ require "spec_helper"
39
39
 
40
40
  describe Signet::OAuth2::Client do
41
- before(:example) do
42
- @key = OpenSSL::PKey::RSA.new(2048)
41
+ before :example do
42
+ @key = OpenSSL::PKey::RSA.new 2048
43
43
  @client = Signet::OAuth2::Client.new(
44
- token_credential_uri: 'https://accounts.google.com/o/oauth2/token',
45
- scope: 'https://www.googleapis.com/auth/userinfo.profile',
46
- issuer: 'app@example.com',
47
- audience: 'https://accounts.google.com/o/oauth2/token',
48
- signing_key: @key)
44
+ token_credential_uri: "https://oauth2.googleapis.com/token",
45
+ scope: "https://www.googleapis.com/auth/userinfo.profile",
46
+ issuer: "app@example.com",
47
+ audience: "https://oauth2.googleapis.com/token",
48
+ signing_key: @key
49
+ )
49
50
  end
50
51
 
51
- def make_auth_stubs(opts)
52
- access_token = opts[:access_token] || ''
53
- body = MultiJson.dump('access_token' => access_token,
54
- 'token_type' => 'Bearer',
55
- 'expires_in' => 3600)
52
+ def make_auth_stubs opts
53
+ access_token = opts[:access_token] || ""
54
+ body = MultiJson.dump("access_token" => access_token,
55
+ "token_type" => "Bearer",
56
+ "expires_in" => 3600)
56
57
  blk = proc do |request|
57
- params = Addressable::URI.form_unencode(request.body)
58
- _claim, _header = JWT.decode(params.assoc('assertion').last,
59
- @key.public_key)
58
+ params = Addressable::URI.form_unencode request.body
59
+ _claim, _header = JWT.decode(params.assoc("assertion").last,
60
+ @key.public_key, true,
61
+ algorithm: "RS256")
60
62
  end
61
- stub_request(:post, 'https://accounts.google.com/o/oauth2/token')
62
- .with(body: hash_including(
63
- 'grant_type' => 'urn:ietf:params:oauth:grant-type:jwt-bearer'),
64
- &blk)
65
- .to_return(body: body,
66
- status: 200,
67
- headers: { 'Content-Type' => 'application/json' })
63
+ with_params = { body: hash_including(
64
+ "grant_type" => "urn:ietf:params:oauth:grant-type:jwt-bearer"
65
+ ) }
66
+ with_params[:headers] = { "User-Agent" => opts[:user_agent] } if opts[:user_agent]
67
+ stub_request(:post, "https://oauth2.googleapis.com/token")
68
+ .with(with_params, &blk)
69
+ .to_return(body: body,
70
+ status: 200,
71
+ headers: { "Content-Type" => "application/json" })
68
72
  end
69
73
 
70
- it_behaves_like 'apply/apply! are OK'
74
+ it_behaves_like "apply/apply! are OK"
75
+
76
+ describe "#configure_connection" do
77
+ it "honors default_connection" do
78
+ token = "1/abcdef1234567890"
79
+ stub = make_auth_stubs access_token: token, user_agent: "RubyRocks/1.0"
80
+ conn = Faraday.new headers: { "User-Agent" => "RubyRocks/1.0" }
81
+ @client.configure_connection default_connection: conn
82
+ md = { foo: "bar" }
83
+ @client.apply! md
84
+ want = { foo: "bar", authorization: "Bearer #{token}" }
85
+ expect(md).to eq(want)
86
+ expect(stub).to have_been_requested
87
+ end
88
+
89
+ it "honors connection_builder" do
90
+ token = "1/abcdef1234567890"
91
+ stub = make_auth_stubs access_token: token, user_agent: "RubyRocks/2.0"
92
+ connection_builder = proc do
93
+ Faraday.new headers: { "User-Agent" => "RubyRocks/2.0" }
94
+ end
95
+ @client.configure_connection connection_builder: connection_builder
96
+ md = { foo: "bar" }
97
+ @client.apply! md
98
+ want = { foo: "bar", authorization: "Bearer #{token}" }
99
+ expect(md).to eq(want)
100
+ expect(stub).to have_been_requested
101
+ end
102
+ end
103
+
104
+ describe "#fetch_access_token!" do
105
+ it "retries when orig_fetch_access_token! raises Signet::RemoteServerError" do
106
+ mocked_responses = [:raise, :raise, "success"]
107
+ allow(@client).to receive(:orig_fetch_access_token!).exactly(3).times do
108
+ response = mocked_responses.shift
109
+ response == :raise ? raise(Signet::RemoteServerError) : response
110
+ end
111
+ expect(@client.fetch_access_token!).to eq("success")
112
+ end
113
+
114
+ it "raises when the max retry count is exceeded" do
115
+ mocked_responses = [:raise, :raise, :raise, :raise, :raise, :raise, "success"]
116
+ allow(@client).to receive(:orig_fetch_access_token!).exactly(6).times do
117
+ response = mocked_responses.shift
118
+ response == :raise ? raise(Signet::RemoteServerError) : response
119
+ end
120
+ expect { @client.fetch_access_token! }.to raise_error Signet::AuthorizationError
121
+ end
122
+
123
+ it "does not retry and raises right away if it encounters a Signet::AuthorizationError" do
124
+ allow(@client).to receive(:orig_fetch_access_token!).at_most(:once)
125
+ .and_raise(Signet::AuthorizationError.new("Some Message"))
126
+ expect { @client.fetch_access_token! }.to raise_error Signet::AuthorizationError
127
+ end
128
+
129
+ it "does not retry and raises right away if it encounters a Signet::ParseError" do
130
+ allow(@client).to receive(:orig_fetch_access_token!).at_most(:once).and_raise(Signet::ParseError)
131
+ expect { @client.fetch_access_token! }.to raise_error Signet::ParseError
132
+ end
133
+ end
71
134
  end
@@ -27,32 +27,31 @@
27
27
  # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28
28
  # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29
29
 
30
- spec_dir = File.expand_path(File.join(File.dirname(__FILE__)))
31
- $LOAD_PATH.unshift(spec_dir)
30
+ spec_dir = File.expand_path File.join(File.dirname(__FILE__))
31
+ $LOAD_PATH.unshift spec_dir
32
32
  $LOAD_PATH.uniq!
33
33
 
34
- require 'googleauth'
35
- require 'googleauth/stores/file_token_store'
36
- require 'spec_helper'
37
- require 'fakefs/safe'
38
- require 'fakefs/spec_helpers'
39
- require 'googleauth/stores/store_examples'
34
+ require "googleauth"
35
+ require "googleauth/stores/file_token_store"
36
+ require "spec_helper"
37
+ require "fakefs/safe"
38
+ require "fakefs/spec_helpers"
39
+ require "googleauth/stores/store_examples"
40
40
 
41
41
  module FakeFS
42
42
  class File
43
43
  # FakeFS doesn't implement. And since we don't need to actually lock,
44
44
  # just stub out...
45
- def flock(*)
46
- end
45
+ def flock *; end
47
46
  end
48
47
  end
49
48
 
50
49
  describe Google::Auth::Stores::FileTokenStore do
51
50
  include FakeFS::SpecHelpers
52
51
 
53
- let(:store) do
54
- Google::Auth::Stores::FileTokenStore.new(file: '/tokens.yaml')
52
+ let :store do
53
+ Google::Auth::Stores::FileTokenStore.new file: "/tokens.yaml"
55
54
  end
56
55
 
57
- it_behaves_like 'token store'
56
+ it_behaves_like "token store"
58
57
  end
@@ -27,24 +27,24 @@
27
27
  # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28
28
  # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29
29
 
30
- spec_dir = File.expand_path(File.join(File.dirname(__FILE__)))
31
- $LOAD_PATH.unshift(spec_dir)
30
+ spec_dir = File.expand_path File.join(File.dirname(__FILE__))
31
+ $LOAD_PATH.unshift spec_dir
32
32
  $LOAD_PATH.uniq!
33
33
 
34
- require 'googleauth'
35
- require 'googleauth/stores/redis_token_store'
36
- require 'spec_helper'
37
- require 'fakeredis/rspec'
38
- require 'googleauth/stores/store_examples'
34
+ require "googleauth"
35
+ require "googleauth/stores/redis_token_store"
36
+ require "spec_helper"
37
+ require "fakeredis/rspec"
38
+ require "googleauth/stores/store_examples"
39
39
 
40
40
  describe Google::Auth::Stores::RedisTokenStore do
41
- let(:redis) do
41
+ let :redis do
42
42
  Redis.new
43
43
  end
44
44
 
45
- let(:store) do
46
- Google::Auth::Stores::RedisTokenStore.new(redis: redis)
45
+ let :store do
46
+ Google::Auth::Stores::RedisTokenStore.new redis: redis
47
47
  end
48
48
 
49
- it_behaves_like 'token store'
49
+ it_behaves_like "token store"
50
50
  end
@@ -27,32 +27,32 @@
27
27
  # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28
28
  # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29
29
 
30
- spec_dir = File.expand_path(File.join(File.dirname(__FILE__)))
31
- $LOAD_PATH.unshift(spec_dir)
30
+ spec_dir = File.expand_path File.join(File.dirname(__FILE__))
31
+ $LOAD_PATH.unshift spec_dir
32
32
  $LOAD_PATH.uniq!
33
33
 
34
- require 'spec_helper'
34
+ require "spec_helper"
35
35
 
36
- shared_examples 'token store' do
37
- before(:each) do
38
- store.store('default', 'test')
36
+ shared_examples "token store" do
37
+ before :each do
38
+ store.store "default", "test"
39
39
  end
40
40
 
41
- it 'should return a stored value' do
42
- expect(store.load('default')).to eq 'test'
41
+ it "should return a stored value" do
42
+ expect(store.load("default")).to eq "test"
43
43
  end
44
44
 
45
- it 'should return nil for missing tokens' do
46
- expect(store.load('notavalidkey')).to be_nil
45
+ it "should return nil for missing tokens" do
46
+ expect(store.load("notavalidkey")).to be_nil
47
47
  end
48
48
 
49
- it 'should return nil for deleted tokens' do
50
- store.delete('default')
51
- expect(store.load('default')).to be_nil
49
+ it "should return nil for deleted tokens" do
50
+ store.delete "default"
51
+ expect(store.load("default")).to be_nil
52
52
  end
53
53
 
54
- it 'should save overwrite values on store' do
55
- store.store('default', 'test2')
56
- expect(store.load('default')).to eq 'test2'
54
+ it "should save overwrite values on store" do
55
+ store.store "default", "test2"
56
+ expect(store.load("default")).to eq "test2"
57
57
  end
58
58
  end