diff --git a/config/settings.yml b/config/settings.yml index 87b6326..c83e826 100644 --- a/config/settings.yml +++ b/config/settings.yml @@ -23,6 +23,7 @@ login: oauth2_json_username_path: '' oauth2_json_name_path: '' oauth2_json_email_path: '' + oauth2_json_avatar_path: '' oauth2_email_verified: false oauth2_send_auth_header: true oauth2_debug_auth: false diff --git a/plugin.rb b/plugin.rb index 38dcd5d..10b3d4b 100644 --- a/plugin.rb +++ b/plugin.rb @@ -99,6 +99,7 @@ class OAuth2BasicAuthenticator < ::Auth::OAuth2Authenticator json_walk(result, user_json, :username) json_walk(result, user_json, :name) json_walk(result, user_json, :email) + json_walk(result, user_json, :avatar) end result @@ -115,6 +116,7 @@ class OAuth2BasicAuthenticator < ::Auth::OAuth2Authenticator result.username = user_details[:username] result.email = user_details[:email] result.email_valid = result.email.present? && SiteSetting.oauth2_email_verified? + avatar_url = user_details[:avatar] current_info = ::PluginStore.get("oauth2_basic", "oauth2_basic_user_#{user_details[:user_id]}") if current_info @@ -126,6 +128,12 @@ class OAuth2BasicAuthenticator < ::Auth::OAuth2Authenticator end end + Jobs.enqueue(:download_avatar_from_url, + url: avatar_url, + user_id: result.user.id, + override_gravatar: SiteSetting.sso_overrides_avatar + ) if result.user && avatar_url.present? + result.extra_data = { oauth2_basic_user_id: user_details[:user_id] } result end diff --git a/spec/plugin_spec.rb b/spec/plugin_spec.rb index 4ecf4f7..8812009 100644 --- a/spec/plugin_spec.rb +++ b/spec/plugin_spec.rb @@ -27,19 +27,51 @@ require_relative '../plugin.rb' describe OAuth2BasicAuthenticator do context 'after_authenticate' do - it 'finds user by email' do - authenticator = OAuth2BasicAuthenticator.new('oauth2_basic') - user = Fabricate(:user) - authenticator.expects(:fetch_user_details).returns(email: user.email) + let(:user) { Fabricate(:user) } + let(:authenticator) { OAuth2BasicAuthenticator.new('oauth2_basic') } + + let(:auth) do + { 'credentials' => { 'token': 'token' }, + 'info' => { id: 'id' }, + 'extra' => {} } + end + + before(:each) do SiteSetting.oauth2_email_verified = true - auth = { 'credentials' => { 'token': 'token' }, - 'info' => { id: 'id' }, - 'extra' => {} } + end + it 'finds user by email' do + authenticator.expects(:fetch_user_details).returns(email: user.email) result = authenticator.after_authenticate(auth) - expect(result.user).to eq(user) end + + context 'avatar downloading' do + before { SiteSetting.queue_jobs = true } + + let(:job_klass) { Jobs::DownloadAvatarFromUrl } + + before do + png = Base64.decode64("R0lGODlhAQABALMAAAAAAIAAAACAAICAAAAAgIAAgACAgMDAwICAgP8AAAD/AP//AAAA//8A/wD//wBiZCH5BAEAAA8ALAAAAAABAAEAAAQC8EUAOw==") + stub_request(:get, "http://avatar.example.com/avatar.png").to_return(body: png, headers: { "Content-Type" => "image/png" }) + end + + it 'enqueues a download_avatar_from_url job' do + authenticator.expects(:fetch_user_details).returns( + email: user.email, + avatar: 'http://avatar.example.com/avatar.png' + ) + expect { + authenticator.after_authenticate(auth) + }.to change { job_klass.jobs.count }.by(1) + + job_args = job_klass.jobs.last['args'].first + + expect(job_args['url']).to eq("http://avatar.example.com/avatar.png") + expect(job_args['user_id']).to eq(user.id) + expect(job_args['override_gravatar']).to eq(false) + end + end end it 'can walk json' do @@ -69,4 +101,12 @@ describe OAuth2BasicAuthenticator do expect(result).to eq nil end + it 'can walk json and download avatar' do + authenticator = OAuth2BasicAuthenticator.new('oauth2_basic') + json_string = '{"user":{"avatar":"http://example.com/1.png"}}' + SiteSetting.oauth2_json_avatar_path = 'user.avatar' + result = authenticator.json_walk({}, JSON.parse(json_string), :avatar) + + expect(result).to eq 'http://example.com/1.png' + end end