diff options
Diffstat (limited to 'spec/support/shared_examples/requests')
12 files changed, 592 insertions, 64 deletions
diff --git a/spec/support/shared_examples/requests/api/composer_packages_shared_examples.rb b/spec/support/shared_examples/requests/api/composer_packages_shared_examples.rb index 5c122b4b5d6..4b5299cebec 100644 --- a/spec/support/shared_examples/requests/api/composer_packages_shared_examples.rb +++ b/spec/support/shared_examples/requests/api/composer_packages_shared_examples.rb @@ -75,7 +75,7 @@ RSpec.shared_examples 'Composer package creation' do |user_type, status, add_mem expect(response).to have_gitlab_http_status(status) end - it_behaves_like 'a gitlab tracking event', described_class.name, 'push_package' + it_behaves_like 'a package tracking event', described_class.name, 'push_package' end end diff --git a/spec/support/shared_examples/requests/api/container_repositories_shared_examples.rb b/spec/support/shared_examples/requests/api/container_repositories_shared_examples.rb index 3e058838773..e776cf13217 100644 --- a/spec/support/shared_examples/requests/api/container_repositories_shared_examples.rb +++ b/spec/support/shared_examples/requests/api/container_repositories_shared_examples.rb @@ -79,11 +79,3 @@ RSpec.shared_examples 'returns repositories for allowed users' do |user_type, sc end end end - -RSpec.shared_examples 'a gitlab tracking event' do |category, action| - it "creates a gitlab tracking event #{action}" do - expect(Gitlab::Tracking).to receive(:event).with(category, action, {}) - - subject - end -end diff --git a/spec/support/shared_examples/requests/api/debian_packages_shared_examples.rb b/spec/support/shared_examples/requests/api/debian_packages_shared_examples.rb new file mode 100644 index 00000000000..ec32cb4b2ff --- /dev/null +++ b/spec/support/shared_examples/requests/api/debian_packages_shared_examples.rb @@ -0,0 +1,309 @@ +# frozen_string_literal: true + +RSpec.shared_context 'Debian repository shared context' do |object_type| + before do + stub_feature_flags(debian_packages: true) + end + + if object_type == :project + let(:project) { create(:project, :public) } + elsif object_type == :group + let(:group) { create(:group, :public) } + end + + let(:user) { create(:user) } + let(:personal_access_token) { create(:personal_access_token, user: user) } + + let(:distribution) { 'bullseye' } + let(:component) { 'main' } + let(:architecture) { 'amd64' } + let(:source_package) { 'sample' } + let(:letter) { source_package[0..2] == 'lib' ? source_package[0..3] : source_package[0] } + let(:package_name) { 'libsample0' } + let(:package_version) { '1.2.3~alpha2-1' } + let(:file_name) { "#{package_name}_#{package_version}_#{architecture}.deb" } + + let(:method) { :get } + + let(:workhorse_params) do + if method == :put + file_upload = fixture_file_upload("spec/fixtures/packages/debian/#{file_name}") + { file: file_upload } + else + {} + end + end + + let(:params) { workhorse_params } + + let(:auth_headers) { {} } + let(:workhorse_headers) do + if method == :put + workhorse_token = JWT.encode({ 'iss' => 'gitlab-workhorse' }, Gitlab::Workhorse.secret, 'HS256') + { 'GitLab-Workhorse' => '1.0', Gitlab::Workhorse::INTERNAL_API_REQUEST_HEADER => workhorse_token } + else + {} + end + end + + let(:headers) { auth_headers.merge(workhorse_headers) } + + let(:send_rewritten_field) { true } + + subject do + if method == :put + workhorse_finalize( + api(url), + method: method, + file_key: :file, + params: params, + headers: headers, + send_rewritten_field: send_rewritten_field + ) + else + send method, api(url), headers: headers, params: params + end + end +end + +RSpec.shared_context 'Debian repository auth headers' do |user_role, user_token, auth_method = :token| + let(:token) { user_token ? personal_access_token.token : 'wrong' } + + let(:auth_headers) do + if user_role == :anonymous + {} + elsif auth_method == :token + { 'Private-Token' => token } + else + basic_auth_header(user.username, token) + end + end +end + +RSpec.shared_context 'Debian repository project access' do |project_visibility_level, user_role, user_token, auth_method| + include_context 'Debian repository auth headers', user_role, user_token, auth_method do + before do + project.update_column(:visibility_level, Gitlab::VisibilityLevel.const_get(project_visibility_level, false)) + end + end +end + +RSpec.shared_examples 'Debian project repository GET request' do |user_role, add_member, status, body| + context "for user type #{user_role}" do + before do + project.send("add_#{user_role}", user) if add_member && user_role != :anonymous + end + + and_body = body.nil? ? '' : ' and expected body' + + it "returns #{status}#{and_body}" do + subject + + expect(response).to have_gitlab_http_status(status) + + unless body.nil? + expect(response.body).to eq(body) + end + end + end +end + +RSpec.shared_examples 'Debian project repository PUT request' do |user_role, add_member, status, body| + context "for user type #{user_role}" do + before do + project.send("add_#{user_role}", user) if add_member && user_role != :anonymous + end + + and_body = body.nil? ? '' : ' and expected body' + + if status == :created + it 'creates package files' do + pending "Debian package creation not implemented" + expect { subject } + .to change { project.packages.debian.count }.by(1) + + expect(response).to have_gitlab_http_status(status) + + unless body.nil? + expect(response.body).to eq(body) + end + end + it_behaves_like 'a package tracking event', described_class.name, 'push_package' + else + it "returns #{status}#{and_body}" do + subject + + expect(response).to have_gitlab_http_status(status) + + unless body.nil? + expect(response.body).to eq(body) + end + end + end + end +end + +RSpec.shared_examples 'rejects Debian access with unknown project id' do + context 'with an unknown project' do + let(:project) { double(id: non_existing_record_id) } + + context 'as anonymous' do + it_behaves_like 'Debian project repository GET request', :anonymous, true, :not_found, nil + end + + context 'as authenticated user' do + subject { get api(url), headers: basic_auth_header(user.username, personal_access_token.token) } + + it_behaves_like 'Debian project repository GET request', :anonymous, true, :not_found, nil + end + end +end + +RSpec.shared_examples 'Debian project repository GET endpoint' do |success_status, success_body| + context 'with valid project' do + using RSpec::Parameterized::TableSyntax + + where(:project_visibility_level, :user_role, :member, :user_token, :expected_status, :expected_body) do + 'PUBLIC' | :developer | true | true | success_status | success_body + 'PUBLIC' | :guest | true | true | success_status | success_body + 'PUBLIC' | :developer | true | false | success_status | success_body + 'PUBLIC' | :guest | true | false | success_status | success_body + 'PUBLIC' | :developer | false | true | success_status | success_body + 'PUBLIC' | :guest | false | true | success_status | success_body + 'PUBLIC' | :developer | false | false | success_status | success_body + 'PUBLIC' | :guest | false | false | success_status | success_body + 'PUBLIC' | :anonymous | false | true | success_status | success_body + 'PRIVATE' | :developer | true | true | success_status | success_body + 'PRIVATE' | :guest | true | true | :forbidden | nil + 'PRIVATE' | :developer | true | false | :not_found | nil + 'PRIVATE' | :guest | true | false | :not_found | nil + 'PRIVATE' | :developer | false | true | :not_found | nil + 'PRIVATE' | :guest | false | true | :not_found | nil + 'PRIVATE' | :developer | false | false | :not_found | nil + 'PRIVATE' | :guest | false | false | :not_found | nil + 'PRIVATE' | :anonymous | false | true | :not_found | nil + end + + with_them do + include_context 'Debian repository project access', params[:project_visibility_level], params[:user_role], params[:user_token], :basic do + it_behaves_like 'Debian project repository GET request', params[:user_role], params[:member], params[:expected_status], params[:expected_body] + end + end + end + + it_behaves_like 'rejects Debian access with unknown project id' +end + +RSpec.shared_examples 'Debian project repository PUT endpoint' do |success_status, success_body| + context 'with valid project' do + using RSpec::Parameterized::TableSyntax + + where(:project_visibility_level, :user_role, :member, :user_token, :expected_status, :expected_body) do + 'PUBLIC' | :developer | true | true | success_status | nil + 'PUBLIC' | :guest | true | true | :forbidden | nil + 'PUBLIC' | :developer | true | false | :unauthorized | nil + 'PUBLIC' | :guest | true | false | :unauthorized | nil + 'PUBLIC' | :developer | false | true | :forbidden | nil + 'PUBLIC' | :guest | false | true | :forbidden | nil + 'PUBLIC' | :developer | false | false | :unauthorized | nil + 'PUBLIC' | :guest | false | false | :unauthorized | nil + 'PUBLIC' | :anonymous | false | true | :unauthorized | nil + 'PRIVATE' | :developer | true | true | success_status | nil + 'PRIVATE' | :guest | true | true | :forbidden | nil + 'PRIVATE' | :developer | true | false | :not_found | nil + 'PRIVATE' | :guest | true | false | :not_found | nil + 'PRIVATE' | :developer | false | true | :not_found | nil + 'PRIVATE' | :guest | false | true | :not_found | nil + 'PRIVATE' | :developer | false | false | :not_found | nil + 'PRIVATE' | :guest | false | false | :not_found | nil + 'PRIVATE' | :anonymous | false | true | :not_found | nil + end + + with_them do + include_context 'Debian repository project access', params[:project_visibility_level], params[:user_role], params[:user_token], :basic do + it_behaves_like 'Debian project repository PUT request', params[:user_role], params[:member], params[:expected_status], params[:expected_body] + end + end + end + + it_behaves_like 'rejects Debian access with unknown project id' +end + +RSpec.shared_context 'Debian repository group access' do |group_visibility_level, user_role, user_token, auth_method| + include_context 'Debian repository auth headers', user_role, user_token, auth_method do + before do + group.update_column(:visibility_level, Gitlab::VisibilityLevel.const_get(group_visibility_level, false)) + end + end +end + +RSpec.shared_examples 'Debian group repository GET request' do |user_role, add_member, status, body| + context "for user type #{user_role}" do + before do + group.send("add_#{user_role}", user) if add_member && user_role != :anonymous + end + + and_body = body.nil? ? '' : ' and expected body' + + it "returns #{status}#{and_body}" do + subject + + expect(response).to have_gitlab_http_status(status) + + unless body.nil? + expect(response.body).to eq(body) + end + end + end +end + +RSpec.shared_examples 'rejects Debian access with unknown group id' do + context 'with an unknown group' do + let(:group) { double(id: non_existing_record_id) } + + context 'as anonymous' do + it_behaves_like 'Debian group repository GET request', :anonymous, true, :not_found, nil + end + + context 'as authenticated user' do + subject { get api(url), headers: basic_auth_header(user.username, personal_access_token.token) } + + it_behaves_like 'Debian group repository GET request', :anonymous, true, :not_found, nil + end + end +end + +RSpec.shared_examples 'Debian group repository GET endpoint' do |success_status, success_body| + context 'with valid group' do + using RSpec::Parameterized::TableSyntax + + where(:group_visibility_level, :user_role, :member, :user_token, :expected_status, :expected_body) do + 'PUBLIC' | :developer | true | true | success_status | success_body + 'PUBLIC' | :guest | true | true | success_status | success_body + 'PUBLIC' | :developer | true | false | success_status | success_body + 'PUBLIC' | :guest | true | false | success_status | success_body + 'PUBLIC' | :developer | false | true | success_status | success_body + 'PUBLIC' | :guest | false | true | success_status | success_body + 'PUBLIC' | :developer | false | false | success_status | success_body + 'PUBLIC' | :guest | false | false | success_status | success_body + 'PUBLIC' | :anonymous | false | true | success_status | success_body + 'PRIVATE' | :developer | true | true | success_status | success_body + 'PRIVATE' | :guest | true | true | :forbidden | nil + 'PRIVATE' | :developer | true | false | :not_found | nil + 'PRIVATE' | :guest | true | false | :not_found | nil + 'PRIVATE' | :developer | false | true | :not_found | nil + 'PRIVATE' | :guest | false | true | :not_found | nil + 'PRIVATE' | :developer | false | false | :not_found | nil + 'PRIVATE' | :guest | false | false | :not_found | nil + 'PRIVATE' | :anonymous | false | true | :not_found | nil + end + + with_them do + include_context 'Debian repository group access', params[:group_visibility_level], params[:user_role], params[:user_token], :basic do + it_behaves_like 'Debian group repository GET request', params[:user_role], params[:member], params[:expected_status], params[:expected_body] + end + end + end + + it_behaves_like 'rejects Debian access with unknown group id' +end diff --git a/spec/support/shared_examples/requests/api/graphql/group_and_project_boards_query_shared_examples.rb b/spec/support/shared_examples/requests/api/graphql/group_and_project_boards_query_shared_examples.rb index f26af6cb766..5145880ef9a 100644 --- a/spec/support/shared_examples/requests/api/graphql/group_and_project_boards_query_shared_examples.rb +++ b/spec/support/shared_examples/requests/api/graphql/group_and_project_boards_query_shared_examples.rb @@ -90,7 +90,7 @@ RSpec.shared_examples 'group and project boards query' do it_behaves_like 'a working graphql query' do before do - post_graphql(query_single_board, current_user: current_user) + post_graphql(query_single_board("id: \"gid://gitlab/Board/1\""), current_user: current_user) end end diff --git a/spec/support/shared_examples/requests/api/nuget_packages_shared_examples.rb b/spec/support/shared_examples/requests/api/nuget_packages_shared_examples.rb index 6aac51a5903..58e99776fd9 100644 --- a/spec/support/shared_examples/requests/api/nuget_packages_shared_examples.rb +++ b/spec/support/shared_examples/requests/api/nuget_packages_shared_examples.rb @@ -26,7 +26,7 @@ RSpec.shared_examples 'process nuget service index request' do |user_type, statu it_behaves_like 'returning response status', status - it_behaves_like 'a gitlab tracking event', described_class.name, 'nuget_service_index' + it_behaves_like 'a package tracking event', described_class.name, 'cli_metadata' it 'returns a valid json response' do subject @@ -169,7 +169,7 @@ RSpec.shared_examples 'process nuget upload' do |user_type, status, add_member = context 'with correct params' do it_behaves_like 'package workhorse uploads' it_behaves_like 'creates nuget package files' - it_behaves_like 'a gitlab tracking event', described_class.name, 'push_package' + it_behaves_like 'a package tracking event', described_class.name, 'push_package' end end @@ -286,7 +286,7 @@ RSpec.shared_examples 'process nuget download content request' do |user_type, st it_behaves_like 'returning response status', status - it_behaves_like 'a gitlab tracking event', described_class.name, 'pull_package' + it_behaves_like 'a package tracking event', described_class.name, 'pull_package' it 'returns a valid package archive' do subject @@ -336,7 +336,7 @@ RSpec.shared_examples 'process nuget search request' do |user_type, status, add_ it_behaves_like 'returns a valid json search response', status, 4, [1, 5, 5, 1] - it_behaves_like 'a gitlab tracking event', described_class.name, 'search_package' + it_behaves_like 'a package tracking event', described_class.name, 'search_package' context 'with skip set to 2' do let(:skip) { 2 } diff --git a/spec/support/shared_examples/requests/api/packages_shared_examples.rb b/spec/support/shared_examples/requests/api/packages_shared_examples.rb index c9a33701161..d730ed53109 100644 --- a/spec/support/shared_examples/requests/api/packages_shared_examples.rb +++ b/spec/support/shared_examples/requests/api/packages_shared_examples.rb @@ -126,3 +126,11 @@ RSpec.shared_examples 'job token for package uploads' do end end end + +RSpec.shared_examples 'a package tracking event' do |category, action| + it "creates a gitlab tracking event #{action}" do + expect(Gitlab::Tracking).to receive(:event).with(category, action, {}) + + expect { subject }.to change { Packages::Event.count }.by(1) + end +end diff --git a/spec/support/shared_examples/requests/api/pypi_packages_shared_examples.rb b/spec/support/shared_examples/requests/api/pypi_packages_shared_examples.rb index 715c494840e..bbcf856350d 100644 --- a/spec/support/shared_examples/requests/api/pypi_packages_shared_examples.rb +++ b/spec/support/shared_examples/requests/api/pypi_packages_shared_examples.rb @@ -1,6 +1,6 @@ # frozen_string_literal: true -RSpec.shared_examples 'PyPi package creation' do |user_type, status, add_member = true| +RSpec.shared_examples 'PyPI package creation' do |user_type, status, add_member = true| RSpec.shared_examples 'creating pypi package files' do it 'creates package files' do expect { subject } @@ -52,7 +52,7 @@ RSpec.shared_examples 'PyPi package creation' do |user_type, status, add_member context 'with correct params' do it_behaves_like 'package workhorse uploads' it_behaves_like 'creating pypi package files' - it_behaves_like 'a gitlab tracking event', described_class.name, 'push_package' + it_behaves_like 'a package tracking event', described_class.name, 'push_package' end end @@ -106,7 +106,7 @@ RSpec.shared_examples 'PyPi package creation' do |user_type, status, add_member end end -RSpec.shared_examples 'PyPi package versions' do |user_type, status, add_member = true| +RSpec.shared_examples 'PyPI package versions' do |user_type, status, add_member = true| context "for user type #{user_type}" do before do project.send("add_#{user_type}", user) if add_member && user_type != :anonymous @@ -119,11 +119,11 @@ RSpec.shared_examples 'PyPi package versions' do |user_type, status, add_member end it_behaves_like 'returning response status', status - it_behaves_like 'a gitlab tracking event', described_class.name, 'list_package' + it_behaves_like 'a package tracking event', described_class.name, 'list_package' end end -RSpec.shared_examples 'PyPi package download' do |user_type, status, add_member = true| +RSpec.shared_examples 'PyPI package download' do |user_type, status, add_member = true| context "for user type #{user_type}" do before do project.send("add_#{user_type}", user) if add_member && user_type != :anonymous @@ -136,11 +136,11 @@ RSpec.shared_examples 'PyPi package download' do |user_type, status, add_member end it_behaves_like 'returning response status', status - it_behaves_like 'a gitlab tracking event', described_class.name, 'pull_package' + it_behaves_like 'a package tracking event', described_class.name, 'pull_package' end end -RSpec.shared_examples 'process PyPi api request' do |user_type, status, add_member = true| +RSpec.shared_examples 'process PyPI api request' do |user_type, status, add_member = true| context "for user type #{user_type}" do before do project.send("add_#{user_type}", user) if add_member && user_type != :anonymous @@ -155,13 +155,13 @@ RSpec.shared_examples 'rejects PyPI access with unknown project id' do let(:project) { OpenStruct.new(id: 1234567890) } context 'as anonymous' do - it_behaves_like 'process PyPi api request', :anonymous, :not_found + it_behaves_like 'process PyPI api request', :anonymous, :not_found end context 'as authenticated user' do subject { get api(url), headers: basic_auth_header(user.username, personal_access_token.token) } - it_behaves_like 'process PyPi api request', :anonymous, :not_found + it_behaves_like 'process PyPI api request', :anonymous, :not_found end end end diff --git a/spec/support/shared_examples/requests/api/snippets_shared_examples.rb b/spec/support/shared_examples/requests/api/snippets_shared_examples.rb index 051367fbe96..2b72c69cb37 100644 --- a/spec/support/shared_examples/requests/api/snippets_shared_examples.rb +++ b/spec/support/shared_examples/requests/api/snippets_shared_examples.rb @@ -1,46 +1,30 @@ # frozen_string_literal: true RSpec.shared_examples 'raw snippet files' do - let_it_be(:unauthorized_user) { create(:user) } + let_it_be(:user_token) { create(:personal_access_token, user: snippet.author) } let(:snippet_id) { snippet.id } let(:user) { snippet.author } let(:file_path) { '%2Egitattributes' } let(:ref) { 'master' } - context 'with no user' do - it 'requires authentication' do - get api(api_path) + subject { get api(api_path, personal_access_token: user_token) } - expect(response).to have_gitlab_http_status(:unauthorized) - end - end + context 'with an invalid snippet ID' do + let(:snippet_id) { non_existing_record_id } - shared_examples 'not found' do it 'returns 404' do - get api(api_path, user) + subject expect(response).to have_gitlab_http_status(:not_found) expect(json_response['message']).to eq('404 Snippet Not Found') end end - context 'when not authorized' do - let(:user) { unauthorized_user } - - it_behaves_like 'not found' - end - - context 'with an invalid snippet ID' do - let(:snippet_id) { 'invalid' } - - it_behaves_like 'not found' - end - context 'with valid params' do it 'returns the raw file info' do expect(Gitlab::Workhorse).to receive(:send_git_blob).and_call_original - get api(api_path, user) + subject aggregate_failures do expect(response).to have_gitlab_http_status(:ok) @@ -52,6 +36,17 @@ RSpec.shared_examples 'raw snippet files' do end end + context 'with unauthorized user' do + let(:user_token) { create(:personal_access_token) } + + it 'returns 404' do + subject + + expect(response).to have_gitlab_http_status(:not_found) + expect(json_response['message']).to eq('404 Snippet Not Found') + end + end + context 'with invalid params' do using RSpec::Parameterized::TableSyntax @@ -68,12 +63,12 @@ RSpec.shared_examples 'raw snippet files' do end with_them do - before do - get api(api_path, user) - end + it 'returns the proper response code and message' do + subject - it { expect(response).to have_gitlab_http_status(status) } - it { expect(json_response[key]).to eq(message) } + expect(response).to have_gitlab_http_status(status) + expect(json_response[key]).to eq(message) + end end end end @@ -216,3 +211,133 @@ RSpec.shared_examples 'invalid snippet updates' do expect(json_response['error']).to eq 'title is empty' end end + +RSpec.shared_examples 'snippet access with different users' do + using RSpec::Parameterized::TableSyntax + + where(:requester, :visibility, :status) do + :admin | :public | :ok + :admin | :private | :ok + :admin | :internal | :ok + :author | :public | :ok + :author | :private | :ok + :author | :internal | :ok + :other | :public | :ok + :other | :private | :not_found + :other | :internal | :ok + nil | :public | :ok + nil | :private | :not_found + nil | :internal | :not_found + end + + with_them do + let(:snippet) { snippet_for(visibility) } + + it 'returns the correct response' do + request_user = user_for(requester) + + get api(path, request_user) + + expect(response).to have_gitlab_http_status(status) + end + end + + def user_for(user_type) + case user_type + when :author + user + when :other + other_user + when :admin + admin + else + nil + end + end + + def snippet_for(snippet_type) + case snippet_type + when :private + private_snippet + when :internal + internal_snippet + when :public + public_snippet + end + end +end + +RSpec.shared_examples 'expected response status' do + it 'returns the correct response' do + get api(path, personal_access_token: user_token) + + expect(response).to have_gitlab_http_status(status) + end +end + +RSpec.shared_examples 'unauthenticated project snippet access' do + using RSpec::Parameterized::TableSyntax + + let(:user_token) { nil } + + where(:project_visibility, :snippet_visibility, :status) do + :public | :public | :ok + :public | :private | :not_found + :public | :internal | :not_found + :internal | :public | :not_found + :private | :public | :not_found + end + + with_them do + it_behaves_like 'expected response status' + end +end + +RSpec.shared_examples 'non-member project snippet access' do + using RSpec::Parameterized::TableSyntax + + where(:project_visibility, :snippet_visibility, :status) do + :public | :public | :ok + :public | :internal | :ok + :internal | :public | :ok + :public | :private | :not_found + :private | :public | :not_found + end + + with_them do + it_behaves_like 'expected response status' + end +end + +RSpec.shared_examples 'member project snippet access' do + using RSpec::Parameterized::TableSyntax + + before do + project.add_guest(user) + end + + where(:project_visibility, :snippet_visibility, :status) do + :public | :public | :ok + :public | :internal | :ok + :internal | :public | :ok + :public | :private | :ok + :private | :public | :ok + end + + with_them do + it_behaves_like 'expected response status' + end +end + +RSpec.shared_examples 'project snippet access levels' do + let_it_be(:user_token) { create(:personal_access_token, user: user) } + + let(:project) { create(:project, project_visibility) } + let(:snippet) { create(:project_snippet, :repository, snippet_visibility, project: project) } + + it_behaves_like 'unauthenticated project snippet access' + + it_behaves_like 'non-member project snippet access' + + it_behaves_like 'member project snippet access' +end diff --git a/spec/support/shared_examples/requests/api/tracking_shared_examples.rb b/spec/support/shared_examples/requests/api/tracking_shared_examples.rb new file mode 100644 index 00000000000..2e6feae3f98 --- /dev/null +++ b/spec/support/shared_examples/requests/api/tracking_shared_examples.rb @@ -0,0 +1,9 @@ +# frozen_string_literal: true + +RSpec.shared_examples 'a gitlab tracking event' do |category, action| + it "creates a gitlab tracking event #{action}" do + expect(Gitlab::Tracking).to receive(:event).with(category, action, {}) + + subject + end +end diff --git a/spec/support/shared_examples/requests/rack_attack_shared_examples.rb b/spec/support/shared_examples/requests/rack_attack_shared_examples.rb index 08ccbd4a9c1..730df4dc5ab 100644 --- a/spec/support/shared_examples/requests/rack_attack_shared_examples.rb +++ b/spec/support/shared_examples/requests/rack_attack_shared_examples.rb @@ -48,7 +48,7 @@ RSpec.shared_examples 'rate-limited token-authenticated requests' do expect_rejection { make_request(request_args) } - Timecop.travel(period.from_now) do + travel_to(period.from_now) do requests_per_period.times do make_request(request_args) expect(response).not_to have_gitlab_http_status(:too_many_requests) @@ -175,7 +175,7 @@ RSpec.shared_examples 'rate-limited web authenticated requests' do expect_rejection { request_authenticated_web_url } - Timecop.travel(period.from_now) do + travel_to(period.from_now) do requests_per_period.times do request_authenticated_web_url expect(response).not_to have_gitlab_http_status(:too_many_requests) diff --git a/spec/support/shared_examples/requests/snippet_shared_examples.rb b/spec/support/shared_examples/requests/snippet_shared_examples.rb index 84ef7723b9b..dae3a3e74be 100644 --- a/spec/support/shared_examples/requests/snippet_shared_examples.rb +++ b/spec/support/shared_examples/requests/snippet_shared_examples.rb @@ -99,18 +99,6 @@ RSpec.shared_examples 'snippet blob content' do end end -RSpec.shared_examples 'snippet_multiple_files feature disabled' do - before do - stub_feature_flags(snippet_multiple_files: false) - - subject - end - - it 'does not return files attributes' do - expect(json_response).not_to have_key('files') - end -end - RSpec.shared_examples 'snippet creation with files parameter' do using RSpec::Parameterized::TableSyntax diff --git a/spec/support/shared_examples/requests/user_activity_shared_examples.rb b/spec/support/shared_examples/requests/user_activity_shared_examples.rb new file mode 100644 index 00000000000..37da1ce5c63 --- /dev/null +++ b/spec/support/shared_examples/requests/user_activity_shared_examples.rb @@ -0,0 +1,97 @@ +# frozen_string_literal: true + +RSpec.shared_examples 'updating of user activity' do |paths_to_visit| + let(:user) { create(:user, last_activity_on: nil) } + + before do + group = create(:group, name: 'group') + project = create(:project, :public, namespace: group, name: 'project') + + create(:issue, project: project, iid: 10) + create(:merge_request, source_project: project, iid: 15) + + project.add_maintainer(user) + end + + context 'without an authenticated user' do + it 'does not set the last activity cookie' do + get "/group/project" + + expect(response.cookies['user_last_activity_on']).to be_nil + end + end + + context 'with an authenticated user' do + before do + login_as(user) + end + + context 'with a POST request' do + it 'does not set the last activity cookie' do + post "/group/project/archive" + + expect(response.cookies['user_last_activity_on']).to be_nil + end + end + + paths_to_visit.each do |path| + context "on GET to #{path}" do + it 'updates the last activity date' do + expect(Users::ActivityService).to receive(:new).and_call_original + + get path + + expect(user.last_activity_on).to eq(Date.today) + end + + context 'when calling it twice' do + it 'updates last_activity_on just once' do + expect(Users::ActivityService).to receive(:new).once.and_call_original + + 2.times do + get path + end + end + end + + context 'when last_activity_on is nil' do + before do + user.update_attribute(:last_activity_on, nil) + end + + it 'updates the last activity date' do + expect(user.last_activity_on).to be_nil + + get path + + expect(user.last_activity_on).to eq(Date.today) + end + end + + context 'when last_activity_on is stale' do + before do + user.update_attribute(:last_activity_on, 2.days.ago.to_date) + end + + it 'updates the last activity date' do + get path + + expect(user.last_activity_on).to eq(Date.today) + end + end + + context 'when last_activity_on is up to date' do + before do + user.update_attribute(:last_activity_on, Date.today) + end + + it 'does not try to update it' do + expect(Users::ActivityService).not_to receive(:new) + + get path + end + end + end + end + end +end |