From 90c586f68c4ba11735188cc218fc4add2af4c680 Mon Sep 17 00:00:00 2001 From: GitLab Bot Date: Tue, 1 Sep 2020 22:42:58 +0000 Subject: [PATCH] Add latest changes from gitlab-org/security/gitlab@13-1-stable-ee --- app/services/applications/create_service.rb | 11 ++++++++- ...ity-add-presence-validation-oauth-apps.yml | 5 ++++ .../admin/applications_controller_spec.rb | 16 +++++++++++-- .../oauth/applications_controller_spec.rb | 23 +++++++++++++++++-- .../admin/admin_manage_applications_spec.rb | 18 ++++++++++++++- .../user_manages_applications_spec.rb | 13 +++++++++++ .../applications/create_service_spec.rb | 19 +++++++++++++-- 7 files changed, 97 insertions(+), 8 deletions(-) create mode 100644 changelogs/unreleased/security-add-presence-validation-oauth-apps.yml diff --git a/app/services/applications/create_service.rb b/app/services/applications/create_service.rb index 500db1e172a..92500fbc254 100644 --- a/app/services/applications/create_service.rb +++ b/app/services/applications/create_service.rb @@ -11,7 +11,16 @@ module Applications # EE would override and use `request` arg def execute(request) - Doorkeeper::Application.create(params) + @application = Doorkeeper::Application.new(params) + + unless params[:scopes].present? + @application.errors.add(:base, _("Scopes can't be blank")) + + return @application + end + + @application.save + @application end end end diff --git a/changelogs/unreleased/security-add-presence-validation-oauth-apps.yml b/changelogs/unreleased/security-add-presence-validation-oauth-apps.yml new file mode 100644 index 00000000000..01f6a825679 --- /dev/null +++ b/changelogs/unreleased/security-add-presence-validation-oauth-apps.yml @@ -0,0 +1,5 @@ +--- +title: Add scope presence validation to OAuth Application creation +merge_request: +author: +type: security diff --git a/spec/controllers/admin/applications_controller_spec.rb b/spec/controllers/admin/applications_controller_spec.rb index 732d20666cb..6c423097e70 100644 --- a/spec/controllers/admin/applications_controller_spec.rb +++ b/spec/controllers/admin/applications_controller_spec.rb @@ -40,7 +40,7 @@ RSpec.describe Admin::ApplicationsController do describe 'POST #create' do it 'creates the application' do - create_params = attributes_for(:application, trusted: true, confidential: false) + create_params = attributes_for(:application, trusted: true, confidential: false, scopes: ['api']) expect do post :create, params: { doorkeeper_application: create_params } @@ -63,7 +63,7 @@ RSpec.describe Admin::ApplicationsController do context 'when the params are for a confidential application' do it 'creates a confidential application' do - create_params = attributes_for(:application, confidential: true) + create_params = attributes_for(:application, confidential: true, scopes: ['read_user']) expect do post :create, params: { doorkeeper_application: create_params } @@ -75,6 +75,18 @@ RSpec.describe Admin::ApplicationsController do expect(application).to have_attributes(create_params.except(:uid, :owner_type)) end end + + context 'when scopes are not present' do + it 'renders the application form on errors' do + create_params = attributes_for(:application, trusted: true, confidential: false) + + expect do + post :create, params: { doorkeeper_application: create_params } + end.not_to change { Doorkeeper::Application.count } + + expect(response).to render_template :new + end + end end describe 'PATCH #update' do diff --git a/spec/controllers/oauth/applications_controller_spec.rb b/spec/controllers/oauth/applications_controller_spec.rb index 33349037260..42c56d7fe64 100644 --- a/spec/controllers/oauth/applications_controller_spec.rb +++ b/spec/controllers/oauth/applications_controller_spec.rb @@ -123,7 +123,8 @@ RSpec.describe Oauth::ApplicationsController do invalid_uri_params = { doorkeeper_application: { name: 'foo', - redirect_uri: 'javascript://alert()' + redirect_uri: 'javascript://alert()', + scopes: ['api'] } } @@ -133,6 +134,23 @@ RSpec.describe Oauth::ApplicationsController do end end + context 'when scopes are not present' do + render_views + + it 'shows an error for blank scopes' do + invalid_uri_params = { + doorkeeper_application: { + name: 'foo', + redirect_uri: 'http://example.org' + } + } + + post :create, params: invalid_uri_params + + expect(response.body).to include 'Scopes can't be blank' + end + end + it_behaves_like 'redirects to login page when the user is not signed in' it_behaves_like 'redirects to 2fa setup page when the user requires it' end @@ -156,7 +174,8 @@ RSpec.describe Oauth::ApplicationsController do { doorkeeper_application: { name: 'foo', - redirect_uri: 'http://example.org' + redirect_uri: 'http://example.org', + scopes: ['api'] } } end diff --git a/spec/features/admin/admin_manage_applications_spec.rb b/spec/features/admin/admin_manage_applications_spec.rb index 3f3d71e842c..7a9a6f2ccb8 100644 --- a/spec/features/admin/admin_manage_applications_spec.rb +++ b/spec/features/admin/admin_manage_applications_spec.rb @@ -7,7 +7,7 @@ RSpec.describe 'admin manage applications' do sign_in(create(:admin)) end - it do + it 'creates new oauth application' do visit admin_applications_path click_on 'New application' @@ -16,6 +16,7 @@ RSpec.describe 'admin manage applications' do fill_in :doorkeeper_application_name, with: 'test' fill_in :doorkeeper_application_redirect_uri, with: 'https://test.com' check :doorkeeper_application_trusted + check :doorkeeper_application_scopes_read_user click_on 'Submit' expect(page).to have_content('Application: test') expect(page).to have_content('Application ID') @@ -43,4 +44,19 @@ RSpec.describe 'admin manage applications' do end expect(page.find('.oauth-applications')).not_to have_content('test_changed') end + + context 'when scopes are blank' do + it 'returns an error' do + visit admin_applications_path + + click_on 'New application' + expect(page).to have_content('New application') + + fill_in :doorkeeper_application_name, with: 'test' + fill_in :doorkeeper_application_redirect_uri, with: 'https://test.com' + click_on 'Submit' + + expect(page).to have_content("Scopes can't be blank") + end + end end diff --git a/spec/features/profiles/user_manages_applications_spec.rb b/spec/features/profiles/user_manages_applications_spec.rb index d65365db880..22eed748c00 100644 --- a/spec/features/profiles/user_manages_applications_spec.rb +++ b/spec/features/profiles/user_manages_applications_spec.rb @@ -15,6 +15,7 @@ RSpec.describe 'User manages applications' do fill_in :doorkeeper_application_name, with: 'test' fill_in :doorkeeper_application_redirect_uri, with: 'https://test.com' + check :doorkeeper_application_scopes_read_user click_on 'Save application' expect(page).to have_content 'Application: test' @@ -41,4 +42,16 @@ RSpec.describe 'User manages applications' do end expect(page.find('.oauth-applications')).not_to have_content 'test_changed' end + + context 'when scopes are blank' do + it 'returns an error' do + expect(page).to have_content 'Add new application' + + fill_in :doorkeeper_application_name, with: 'test' + fill_in :doorkeeper_application_redirect_uri, with: 'https://test.com' + click_on 'Save application' + + expect(page).to have_content("Scopes can't be blank") + end + end end diff --git a/spec/services/applications/create_service_spec.rb b/spec/services/applications/create_service_spec.rb index c8134087fa1..a34c5b10457 100644 --- a/spec/services/applications/create_service_spec.rb +++ b/spec/services/applications/create_service_spec.rb @@ -6,9 +6,24 @@ describe ::Applications::CreateService do include TestRequestHelpers let(:user) { create(:user) } - let(:params) { attributes_for(:application) } subject { described_class.new(user, params) } - it { expect { subject.execute(test_request) }.to change { Doorkeeper::Application.count }.by(1) } + context 'when scopes are present' do + let(:params) { attributes_for(:application, scopes: ['read_user']) } + + it { expect { subject.execute(test_request) }.to change { Doorkeeper::Application.count }.by(1) } + end + + context 'when scopes are missing' do + let(:params) { attributes_for(:application) } + + it { expect { subject.execute(test_request) }.not_to change { Doorkeeper::Application.count } } + + it 'includes blank scopes error message' do + application = subject.execute(test_request) + + expect(application.errors.full_messages).to include "Scopes can't be blank" + end + end end -- GitLab