Skip to content

Commit

Permalink
Support oauth2 v2.0.6+ (#429)
Browse files Browse the repository at this point in the history
* update relevant gems to support up to Oauth2 v2.0.4

* Update to support OAuth2 v2.0.5+

 - apply changes to test suite for new parameters in  OAuth::Client and AccessToken
 - update access_token['id_token'] to access_token.token in strategies/google_oauth2.rb
 - alter access_token.token.nil? to nil_or_empty() due to aforementioned changes

* Update testsuite and gemspec to support OAuth2 v2.0.6+

 - alter test "...when the access token is empty or nil"
 - v2.0.6 fixed regression in v2.0.5 so test client is now initialized with refresh_token

* update google_oauth2_spec.rb

 - update test "...when the access token is empty or nil"
 - remove redundant "let(:client) do" declaration

* Update google_oauth2_spec.rb

 - allow OAuth::Client initializations to raise error flags

* Clean up google_oauth2_spec.rb

 - convert unnecessary "let(:client) do" to instance variable

* Correct gem description OmniAuth version error
  • Loading branch information
JacobMarq authored Sep 4, 2022
1 parent d7e862c commit 08ac691
Show file tree
Hide file tree
Showing 3 changed files with 45 additions and 14 deletions.
10 changes: 7 additions & 3 deletions lib/omniauth/strategies/google_oauth2.rb
Original file line number Diff line number Diff line change
Expand Up @@ -69,9 +69,9 @@ def authorize_params

extra do
hash = {}
hash[:id_token] = access_token['id_token']
if !options[:skip_jwt] && !access_token['id_token'].nil?
decoded = ::JWT.decode(access_token['id_token'], nil, false).first
hash[:id_token] = access_token.token
if !options[:skip_jwt] && !nil_or_empty(access_token.token)
decoded = ::JWT.decode(access_token.token, nil, false).first

# We have to manually verify the claims because the third parameter to
# JWT.decode is false since no verification key is provided.
Expand Down Expand Up @@ -108,6 +108,10 @@ def custom_build_access_token

private

def nil_or_empty(obj)
obj.is_a?(String) ? obj.empty? : obj.nil?
end

def callback_url
options[:redirect_uri] || (full_host + callback_path)
end
Expand Down
4 changes: 2 additions & 2 deletions omniauth-google-oauth2.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -21,9 +21,9 @@ Gem::Specification.new do |gem|
gem.required_ruby_version = '>= 2.2'

gem.add_runtime_dependency 'jwt', '>= 2.0'
gem.add_runtime_dependency 'oauth2', '~> 1.1'
gem.add_runtime_dependency 'oauth2', '~> 2.0.6'
gem.add_runtime_dependency 'omniauth', '~> 2.0'
gem.add_runtime_dependency 'omniauth-oauth2', '~> 1.7.1'
gem.add_runtime_dependency 'omniauth-oauth2', '~> 1.8.0'

gem.add_development_dependency 'rake', '~> 12.0'
gem.add_development_dependency 'rspec', '~> 3.6'
Expand Down
45 changes: 36 additions & 9 deletions spec/omniauth/strategies/google_oauth2_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -339,7 +339,7 @@
end
end
end
let(:access_token) { OAuth2::AccessToken.from_hash(client, {}) }
let(:access_token) { OAuth2::AccessToken.from_hash(client, { 'access_token' => 'a' }) }
before { allow(subject).to receive(:access_token).and_return(access_token) }

context 'with verified email' do
Expand Down Expand Up @@ -405,8 +405,6 @@
end
end
end
let(:access_token) { OAuth2::AccessToken.from_hash(client, {}) }

before { allow(subject).to receive(:access_token).and_return(access_token) }

describe 'id_token' do
Expand Down Expand Up @@ -467,7 +465,10 @@
end
end

context 'when the id_token is missing' do
context 'when the access token is empty or nil' do
let(:access_token) { OAuth2::AccessToken.new(client, nil, { 'refresh_token' => 'foo' }) }
before { allow(subject.extra).to receive(:access_token).and_return(access_token) }

it 'should not include id_token' do
expect(subject.extra).not_to have_key(:id_token)
end
Expand All @@ -479,6 +480,19 @@
end

describe 'raw_info' do
let(:token_info) do
{
'abc' => 'xyz',
'exp' => Time.now.to_i + 3600,
'nbf' => Time.now.to_i - 60,
'iat' => Time.now.to_i,
'aud' => 'appid',
'iss' => 'accounts.google.com'
}
end
let(:id_token) { JWT.encode(token_info, 'secret') }
let(:access_token) { OAuth2::AccessToken.from_hash(client, 'id_token' => id_token) }

context 'when skip_info is true' do
before { subject.options[:skip_info] = true }

Expand Down Expand Up @@ -663,15 +677,22 @@
end

it 'should read access_token from hash if this is not an AJAX request with a code parameter' do
client = OAuth2::Client.new('abc', 'def') do |builder|
builder.request :url_encoded
builder.adapter :test do |stub|
stub.get('/oauth2/v3/userinfo') { [200, { 'content-type' => 'application/json' }, '{"sub": "12345"}'] }
end
end

allow(request).to receive(:xhr?).and_return(false)
allow(request).to receive(:params).and_return('access_token' => 'valid_access_token')
expect(subject).to receive(:verify_token).with('valid_access_token').and_return true
expect(subject).to receive(:client).and_return(:client)
expect(subject).to receive(:client).and_return(client)

token = subject.build_access_token
expect(token).to be_instance_of(::OAuth2::AccessToken)
expect(token.token).to eq('valid_access_token')
expect(token.client).to eq(:client)
expect(token.client).to eq(client)
end

it 'reads the code from a json request body' do
Expand Down Expand Up @@ -708,18 +729,24 @@

it 'reads the access token from a json request body' do
body = StringIO.new(%({"access_token":"valid_access_token"}))
client = OAuth2::Client.new('abc', 'def') do |builder|
builder.request :url_encoded
builder.adapter :test do |stub|
stub.get('/oauth2/v3/userinfo') { [200, { 'content-type' => 'application/json' }, '{"sub": "12345"}'] }
end
end

allow(request).to receive(:xhr?).and_return(false)
allow(request).to receive(:content_type).and_return('application/json')
allow(request).to receive(:body).and_return(body)
expect(subject).to receive(:client).and_return(:client)
expect(subject).to receive(:client).and_return(client)

expect(subject).to receive(:verify_token).with('valid_access_token').and_return true

token = subject.build_access_token
expect(token).to be_instance_of(::OAuth2::AccessToken)
expect(token.token).to eq('valid_access_token')
expect(token.client).to eq(:client)
expect(token.client).to eq(client)
end

it 'should use callback_url without query_string if this is not an AJAX request' do
Expand Down Expand Up @@ -795,7 +822,7 @@
end
end
end
let(:access_token) { OAuth2::AccessToken.from_hash(client, {}) }
let(:access_token) { OAuth2::AccessToken.from_hash(client, { 'access_token' => 'foo' }) }

context 'when domain is nil' do
let(:client) do
Expand Down

0 comments on commit 08ac691

Please sign in to comment.