summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRobert Speicher <rspeicher@gmail.com>2019-03-22 13:07:37 +0000
committerRobert Speicher <rspeicher@gmail.com>2019-03-22 13:07:37 +0000
commit940cd50965fcbb0ec2fc0c2ab9e455a197aa48f0 (patch)
tree13cc74443e568d51b4bcb2e5ae61fd9949c1be87
parent893abc4a3d9ceaf2da4a1739746d478e02757f6c (diff)
downloadgitlab-ce-revert-322c14be.tar.gz
Revert "Merge branch 'ce-6618-extract-ee-specific-files-lines-for-create-spec-finders' into 'master'"revert-322c14be
This reverts merge request !26337
-rw-r--r--spec/finders/group_projects_finder_spec.rb39
-rw-r--r--spec/finders/issues_finder_spec.rb80
-rw-r--r--spec/finders/merge_requests_finder_spec.rb139
-rw-r--r--spec/finders/snippets_finder_spec.rb221
-rw-r--r--spec/finders/users_finder_spec.rb31
-rw-r--r--spec/support/shared_contexts/finders/group_projects_finder_shared_contexts.rb24
-rw-r--r--spec/support/shared_contexts/finders/issues_finder_shared_contexts.rb44
-rw-r--r--spec/support/shared_contexts/finders/merge_requests_finder_shared_contexts.rb65
-rw-r--r--spec/support/shared_contexts/finders/users_finder_shared_contexts.rb8
-rw-r--r--spec/support/shared_examples/snippet_visibility.rb322
-rw-r--r--spec/support/shared_examples/snippet_visibility_shared_examples.rb306
11 files changed, 617 insertions, 662 deletions
diff --git a/spec/finders/group_projects_finder_spec.rb b/spec/finders/group_projects_finder_spec.rb
index f8fcc2d0e40..d6d95906f5e 100644
--- a/spec/finders/group_projects_finder_spec.rb
+++ b/spec/finders/group_projects_finder_spec.rb
@@ -1,7 +1,26 @@
require 'spec_helper'
describe GroupProjectsFinder do
- include_context 'GroupProjectsFinder context'
+ let(:group) { create(:group) }
+ let(:subgroup) { create(:group, parent: group) }
+ let(:current_user) { create(:user) }
+ let(:options) { {} }
+
+ let(:finder) { described_class.new(group: group, current_user: current_user, options: options) }
+
+ let!(:public_project) { create(:project, :public, group: group, path: '1') }
+ let!(:private_project) { create(:project, :private, group: group, path: '2') }
+ let!(:shared_project_1) { create(:project, :public, path: '3') }
+ let!(:shared_project_2) { create(:project, :private, path: '4') }
+ let!(:shared_project_3) { create(:project, :internal, path: '5') }
+ let!(:subgroup_project) { create(:project, :public, path: '6', group: subgroup) }
+ let!(:subgroup_private_project) { create(:project, :private, path: '7', group: subgroup) }
+
+ before do
+ shared_project_1.project_group_links.create(group_access: Gitlab::Access::MAINTAINER, group: group)
+ shared_project_2.project_group_links.create(group_access: Gitlab::Access::MAINTAINER, group: group)
+ shared_project_3.project_group_links.create(group_access: Gitlab::Access::MAINTAINER, group: group)
+ end
subject { finder.execute }
@@ -125,24 +144,6 @@ describe GroupProjectsFinder do
end
end
- describe 'with an admin current user' do
- let(:current_user) { create(:admin) }
-
- context "only shared" do
- let(:options) { { only_shared: true } }
- it { is_expected.to eq([shared_project_3, shared_project_2, shared_project_1]) }
- end
-
- context "only owned" do
- let(:options) { { only_owned: true } }
- it { is_expected.to eq([private_project, public_project]) }
- end
-
- context "all" do
- it { is_expected.to eq([shared_project_3, shared_project_2, shared_project_1, private_project, public_project]) }
- end
- end
-
describe "no user" do
context "only shared" do
let(:options) { { only_shared: true } }
diff --git a/spec/finders/issues_finder_spec.rb b/spec/finders/issues_finder_spec.rb
index 00b6cad1a66..f74eb1364a6 100644
--- a/spec/finders/issues_finder_spec.rb
+++ b/spec/finders/issues_finder_spec.rb
@@ -1,10 +1,45 @@
require 'spec_helper'
describe IssuesFinder do
- include_context 'IssuesFinder context'
+ set(:user) { create(:user) }
+ set(:user2) { create(:user) }
+ set(:group) { create(:group) }
+ set(:subgroup) { create(:group, parent: group) }
+ set(:project1) { create(:project, group: group) }
+ set(:project2) { create(:project) }
+ set(:project3) { create(:project, group: subgroup) }
+ set(:milestone) { create(:milestone, project: project1) }
+ set(:label) { create(:label, project: project2) }
+ set(:issue1) { create(:issue, author: user, assignees: [user], project: project1, milestone: milestone, title: 'gitlab', created_at: 1.week.ago, updated_at: 1.week.ago) }
+ set(:issue2) { create(:issue, author: user, assignees: [user], project: project2, description: 'gitlab', created_at: 1.week.from_now, updated_at: 1.week.from_now) }
+ set(:issue3) { create(:issue, author: user2, assignees: [user2], project: project2, title: 'tanuki', description: 'tanuki', created_at: 2.weeks.from_now, updated_at: 2.weeks.from_now) }
+ set(:issue4) { create(:issue, project: project3) }
+ set(:award_emoji1) { create(:award_emoji, name: 'thumbsup', user: user, awardable: issue1) }
+ set(:award_emoji2) { create(:award_emoji, name: 'thumbsup', user: user2, awardable: issue2) }
+ set(:award_emoji3) { create(:award_emoji, name: 'thumbsdown', user: user, awardable: issue3) }
describe '#execute' do
- include_context 'IssuesFinder#execute context'
+ let!(:closed_issue) { create(:issue, author: user2, assignees: [user2], project: project2, state: 'closed') }
+ let!(:label_link) { create(:label_link, label: label, target: issue2) }
+ let(:search_user) { user }
+ let(:params) { {} }
+ let(:issues) { described_class.new(search_user, params.reverse_merge(scope: scope, state: 'opened')).execute }
+
+ before(:context) do
+ project1.add_maintainer(user)
+ project2.add_developer(user)
+ project2.add_developer(user2)
+ project3.add_developer(user)
+
+ issue1
+ issue2
+ issue3
+ issue4
+
+ award_emoji1
+ award_emoji2
+ award_emoji3
+ end
context 'scope: all' do
let(:scope) { 'all' }
@@ -21,21 +56,6 @@ describe IssuesFinder do
end
end
- context 'filtering by assignee usernames' do
- set(:user3) { create(:user) }
- let(:params) { { assignee_username: [user2.username, user3.username] } }
-
- before do
- project2.add_developer(user3)
-
- issue3.assignees = [user2, user3]
- end
-
- it 'returns issues assigned to those users' do
- expect(issues).to contain_exactly(issue3)
- end
- end
-
context 'filtering by no assignee' do
let(:params) { { assignee_id: 'None' } }
@@ -623,16 +643,6 @@ describe IssuesFinder do
expect(subject).to include(public_issue, confidential_issue)
end
end
-
- context 'for an admin' do
- let(:admin_user) { create(:user, :admin) }
-
- subject { described_class.new(admin_user, params).with_confidentiality_access_check }
-
- it 'returns all issues' do
- expect(subject).to include(public_issue, confidential_issue)
- end
- end
end
context 'when searching within a specific project' do
@@ -700,22 +710,6 @@ describe IssuesFinder do
subject
end
end
-
- context 'for an admin' do
- let(:admin_user) { create(:user, :admin) }
-
- subject { described_class.new(admin_user, params).with_confidentiality_access_check }
-
- it 'returns all issues' do
- expect(subject).to include(public_issue, confidential_issue)
- end
-
- it 'does not filter by confidentiality' do
- expect(Issue).not_to receive(:where).with(a_string_matching('confidential'), anything)
-
- subject
- end
- end
end
end
diff --git a/spec/finders/merge_requests_finder_spec.rb b/spec/finders/merge_requests_finder_spec.rb
index 56136eb84bc..f1178b07eec 100644
--- a/spec/finders/merge_requests_finder_spec.rb
+++ b/spec/finders/merge_requests_finder_spec.rb
@@ -1,24 +1,72 @@
require 'spec_helper'
describe MergeRequestsFinder do
+ include ProjectForksHelper
+
+ # We need to explicitly permit Gitaly N+1s because of the specs that use
+ # :request_store. Gitaly N+1 detection is only enabled when :request_store is,
+ # but we don't care about potential N+1s when we're just creating several
+ # projects in the setup phase.
+ def create_project_without_n_plus_1(*args)
+ Gitlab::GitalyClient.allow_n_plus_1_calls do
+ create(:project, :public, *args)
+ end
+ end
+
context "multiple projects with merge requests" do
- include_context 'MergeRequestsFinder multiple projects with merge requests context'
+ let(:user) { create :user }
+ let(:user2) { create :user }
+
+ let(:group) { create(:group) }
+ let(:subgroup) { create(:group, parent: group) }
+ let(:project1) { create_project_without_n_plus_1(group: group) }
+ let(:project2) do
+ Gitlab::GitalyClient.allow_n_plus_1_calls do
+ fork_project(project1, user)
+ end
+ end
+ let(:project3) do
+ Gitlab::GitalyClient.allow_n_plus_1_calls do
+ p = fork_project(project1, user)
+ p.update!(archived: true)
+ p
+ end
+ end
+ let(:project4) { create_project_without_n_plus_1(:repository, group: subgroup) }
+ let(:project5) { create_project_without_n_plus_1(group: subgroup) }
+ let(:project6) { create_project_without_n_plus_1(group: subgroup) }
+
+ let!(:merge_request1) { create(:merge_request, author: user, source_project: project2, target_project: project1, target_branch: 'merged-target') }
+ let!(:merge_request2) { create(:merge_request, :conflict, author: user, source_project: project2, target_project: project1, state: 'closed') }
+ let!(:merge_request3) { create(:merge_request, :simple, author: user, source_project: project2, target_project: project2, state: 'locked', title: 'thing WIP thing') }
+ let!(:merge_request4) { create(:merge_request, :simple, author: user, source_project: project3, target_project: project3, title: 'WIP thing') }
+ let!(:merge_request5) { create(:merge_request, :simple, author: user, source_project: project4, target_project: project4, title: '[WIP]') }
+ let!(:merge_request6) { create(:merge_request, :simple, author: user, source_project: project5, target_project: project5, title: 'WIP: thing') }
+ let!(:merge_request7) { create(:merge_request, :simple, author: user, source_project: project6, target_project: project6, title: 'wip thing') }
+ let!(:merge_request8) { create(:merge_request, :simple, author: user, source_project: project1, target_project: project1, title: '[wip] thing') }
+ let!(:merge_request9) { create(:merge_request, :simple, author: user, source_project: project1, target_project: project2, title: 'wip: thing') }
+
+ before do
+ project1.add_maintainer(user)
+ project2.add_developer(user)
+ project3.add_developer(user)
+ project2.add_developer(user2)
+ project4.add_developer(user)
+ project5.add_developer(user)
+ project6.add_developer(user)
+ end
describe '#execute' do
it 'filters by scope' do
params = { scope: 'authored', state: 'opened' }
-
merge_requests = described_class.new(user, params).execute
-
- expect(merge_requests).to contain_exactly(merge_request1, merge_request4, merge_request5)
+ expect(merge_requests.size).to eq(7)
end
it 'filters by project' do
params = { project_id: project1.id, scope: 'authored', state: 'opened' }
-
merge_requests = described_class.new(user, params).execute
-
- expect(merge_requests).to contain_exactly(merge_request1)
+ expect(merge_requests.size).to eq(2)
end
it 'filters by commit sha' do
@@ -31,15 +79,24 @@ describe MergeRequestsFinder do
end
context 'filtering by group' do
- it 'includes all merge requests when user has access exceluding merge requests from projects the user does not have access to' do
- private_project = allow_gitaly_n_plus_1 { create(:project, :private, group: group) }
- private_project.add_guest(user)
- create(:merge_request, :simple, author: user, source_project: private_project, target_project: private_project)
+ it 'includes all merge requests when user has access' do
+ params = { group_id: group.id }
+
+ merge_requests = described_class.new(user, params).execute
+
+ expect(merge_requests.size).to eq(3)
+ end
+
+ it 'excludes merge requests from projects the user does not have access to' do
+ private_project = create_project_without_n_plus_1(:private, group: group)
+ private_mr = create(:merge_request, :simple, author: user, source_project: private_project, target_project: private_project)
params = { group_id: group.id }
+ private_project.add_guest(user)
merge_requests = described_class.new(user, params).execute
- expect(merge_requests).to contain_exactly(merge_request1, merge_request2)
+ expect(merge_requests.size).to eq(3)
+ expect(merge_requests).not_to include(private_mr)
end
it 'filters by group including subgroups', :nested_groups do
@@ -47,16 +104,14 @@ describe MergeRequestsFinder do
merge_requests = described_class.new(user, params).execute
- expect(merge_requests).to contain_exactly(merge_request1, merge_request2, merge_request5)
+ expect(merge_requests.size).to eq(6)
end
end
it 'filters by non_archived' do
params = { non_archived: true }
-
merge_requests = described_class.new(user, params).execute
-
- expect(merge_requests).to contain_exactly(merge_request1, merge_request2, merge_request3, merge_request5)
+ expect(merge_requests.size).to eq(8)
end
it 'filters by iid' do
@@ -91,45 +146,41 @@ describe MergeRequestsFinder do
expect(merge_requests).to contain_exactly(merge_request3)
end
- describe 'WIP state' do
- let!(:wip_merge_request1) { create(:merge_request, :simple, author: user, source_project: project5, target_project: project5, title: 'WIP: thing') }
- let!(:wip_merge_request2) { create(:merge_request, :simple, author: user, source_project: project6, target_project: project6, title: 'wip thing') }
- let!(:wip_merge_request3) { create(:merge_request, :simple, author: user, source_project: project1, target_project: project1, title: '[wip] thing') }
- let!(:wip_merge_request4) { create(:merge_request, :simple, author: user, source_project: project1, target_project: project2, title: 'wip: thing') }
-
- it 'filters by wip' do
- params = { wip: 'yes' }
+ it 'filters by wip' do
+ params = { wip: 'yes' }
- merge_requests = described_class.new(user, params).execute
+ merge_requests = described_class.new(user, params).execute
- expect(merge_requests).to contain_exactly(merge_request4, merge_request5, wip_merge_request1, wip_merge_request2, wip_merge_request3, wip_merge_request4)
- end
+ expect(merge_requests).to contain_exactly(merge_request4, merge_request5, merge_request6, merge_request7, merge_request8, merge_request9)
+ end
- it 'filters by not wip' do
- params = { wip: 'no' }
+ it 'filters by not wip' do
+ params = { wip: 'no' }
- merge_requests = described_class.new(user, params).execute
+ merge_requests = described_class.new(user, params).execute
- expect(merge_requests).to contain_exactly(merge_request1, merge_request2, merge_request3)
- end
+ expect(merge_requests).to contain_exactly(merge_request1, merge_request2, merge_request3)
+ end
- it 'returns all items if no valid wip param exists' do
- params = { wip: '' }
+ it 'returns all items if no valid wip param exists' do
+ params = { wip: '' }
- merge_requests = described_class.new(user, params).execute
+ merge_requests = described_class.new(user, params).execute
- expect(merge_requests).to contain_exactly(merge_request1, merge_request2, merge_request3, merge_request4, merge_request5, wip_merge_request1, wip_merge_request2, wip_merge_request3, wip_merge_request4)
- end
+ expect(merge_requests).to contain_exactly(merge_request1, merge_request2, merge_request3, merge_request4, merge_request5, merge_request6, merge_request7, merge_request8, merge_request9)
+ end
- it 'adds wip to scalar params' do
- scalar_params = described_class.scalar_params
+ it 'adds wip to scalar params' do
+ scalar_params = described_class.scalar_params
- expect(scalar_params).to include(:wip, :assignee_id)
- end
+ expect(scalar_params).to include(:wip, :assignee_id)
end
context 'filtering by group milestone' do
+ let!(:group) { create(:group, :public) }
let(:group_milestone) { create(:milestone, group: group) }
+ let!(:group_member) { create(:group_member, group: group, user: user) }
+ let(:params) { { milestone_title: group_milestone.title } }
before do
project2.update(namespace: group)
@@ -137,9 +188,7 @@ describe MergeRequestsFinder do
merge_request3.update(milestone: group_milestone)
end
- it 'returns merge requests assigned to that group milestone' do
- params = { milestone_title: group_milestone.title }
-
+ it 'returns issues assigned to that group milestone' do
merge_requests = described_class.new(user, params).execute
expect(merge_requests).to contain_exactly(merge_request2, merge_request3)
@@ -236,7 +285,7 @@ describe MergeRequestsFinder do
it 'returns the number of rows for the default state' do
finder = described_class.new(user)
- expect(finder.row_count).to eq(3)
+ expect(finder.row_count).to eq(7)
end
it 'returns the number of rows for a given state' do
diff --git a/spec/finders/snippets_finder_spec.rb b/spec/finders/snippets_finder_spec.rb
index 93287f3e9b8..134fb5f2c04 100644
--- a/spec/finders/snippets_finder_spec.rb
+++ b/spec/finders/snippets_finder_spec.rb
@@ -2,6 +2,7 @@ require 'spec_helper'
describe SnippetsFinder do
include Gitlab::Allowable
+ using RSpec::Parameterized::TableSyntax
describe '#initialize' do
it 'raises ArgumentError when a project and author are given' do
@@ -13,142 +14,174 @@ describe SnippetsFinder do
end
end
- describe '#execute' do
- set(:user) { create(:user) }
- set(:private_personal_snippet) { create(:personal_snippet, :private, author: user) }
- set(:internal_personal_snippet) { create(:personal_snippet, :internal, author: user) }
- set(:public_personal_snippet) { create(:personal_snippet, :public, author: user) }
+ context 'filter by scope' do
+ let(:user) { create :user }
+ let!(:snippet1) { create(:personal_snippet, :private, author: user) }
+ let!(:snippet2) { create(:personal_snippet, :internal, author: user) }
+ let!(:snippet3) { create(:personal_snippet, :public, author: user) }
- context 'filter by scope' do
- it "returns all snippets for 'all' scope" do
- snippets = described_class.new(user, scope: :all).execute
+ it "returns all snippets for 'all' scope" do
+ snippets = described_class.new(user, scope: :all).execute
- expect(snippets).to contain_exactly(private_personal_snippet, internal_personal_snippet, public_personal_snippet)
- end
+ expect(snippets).to include(snippet1, snippet2, snippet3)
+ end
- it "returns all snippets for 'are_private' scope" do
- snippets = described_class.new(user, scope: :are_private).execute
+ it "returns all snippets for 'are_private' scope" do
+ snippets = described_class.new(user, scope: :are_private).execute
- expect(snippets).to contain_exactly(private_personal_snippet)
- end
+ expect(snippets).to include(snippet1)
+ expect(snippets).not_to include(snippet2, snippet3)
+ end
- it "returns all snippets for 'are_internal' scope" do
- snippets = described_class.new(user, scope: :are_internal).execute
+ it "returns all snippets for 'are_internal' scope" do
+ snippets = described_class.new(user, scope: :are_internal).execute
- expect(snippets).to contain_exactly(internal_personal_snippet)
- end
+ expect(snippets).to include(snippet2)
+ expect(snippets).not_to include(snippet1, snippet3)
+ end
- it "returns all snippets for 'are_private' scope" do
- snippets = described_class.new(user, scope: :are_public).execute
+ it "returns all snippets for 'are_private' scope" do
+ snippets = described_class.new(user, scope: :are_public).execute
- expect(snippets).to contain_exactly(public_personal_snippet)
- end
+ expect(snippets).to include(snippet3)
+ expect(snippets).not_to include(snippet1, snippet2)
end
+ end
- context 'filter by author' do
- it 'returns all public and internal snippets' do
- snippets = described_class.new(create(:user), author: user).execute
+ context 'filter by author' do
+ let(:user) { create :user }
+ let(:user1) { create :user }
+ let!(:snippet1) { create(:personal_snippet, :private, author: user) }
+ let!(:snippet2) { create(:personal_snippet, :internal, author: user) }
+ let!(:snippet3) { create(:personal_snippet, :public, author: user) }
- expect(snippets).to contain_exactly(internal_personal_snippet, public_personal_snippet)
- end
+ it "returns all public and internal snippets" do
+ snippets = described_class.new(user1, author: user).execute
- it 'returns internal snippets' do
- snippets = described_class.new(user, author: user, scope: :are_internal).execute
+ expect(snippets).to include(snippet2, snippet3)
+ expect(snippets).not_to include(snippet1)
+ end
- expect(snippets).to contain_exactly(internal_personal_snippet)
- end
+ it "returns internal snippets" do
+ snippets = described_class.new(user, author: user, scope: :are_internal).execute
- it 'returns private snippets' do
- snippets = described_class.new(user, author: user, scope: :are_private).execute
+ expect(snippets).to include(snippet2)
+ expect(snippets).not_to include(snippet1, snippet3)
+ end
- expect(snippets).to contain_exactly(private_personal_snippet)
- end
+ it "returns private snippets" do
+ snippets = described_class.new(user, author: user, scope: :are_private).execute
- it 'returns public snippets' do
- snippets = described_class.new(user, author: user, scope: :are_public).execute
+ expect(snippets).to include(snippet1)
+ expect(snippets).not_to include(snippet2, snippet3)
+ end
- expect(snippets).to contain_exactly(public_personal_snippet)
- end
+ it "returns public snippets" do
+ snippets = described_class.new(user, author: user, scope: :are_public).execute
- it 'returns all snippets' do
- snippets = described_class.new(user, author: user).execute
+ expect(snippets).to include(snippet3)
+ expect(snippets).not_to include(snippet1, snippet2)
+ end
- expect(snippets).to contain_exactly(private_personal_snippet, internal_personal_snippet, public_personal_snippet)
- end
+ it "returns all snippets" do
+ snippets = described_class.new(user, author: user).execute
- it 'returns only public snippets if unauthenticated user' do
- snippets = described_class.new(nil, author: user).execute
+ expect(snippets).to include(snippet1, snippet2, snippet3)
+ end
- expect(snippets).to contain_exactly(public_personal_snippet)
- end
+ it "returns only public snippets if unauthenticated user" do
+ snippets = described_class.new(nil, author: user).execute
- it 'returns all snippets for an admin' do
- admin = create(:user, :admin)
- snippets = described_class.new(admin, author: user).execute
+ expect(snippets).to include(snippet3)
+ expect(snippets).not_to include(snippet2, snippet1)
+ end
- expect(snippets).to contain_exactly(private_personal_snippet, internal_personal_snippet, public_personal_snippet)
- end
+ it 'returns all snippets for an admin' do
+ admin = create(:user, :admin)
+ snippets = described_class.new(admin, author: user).execute
+
+ expect(snippets).to include(snippet1, snippet2, snippet3)
end
+ end
- context 'project snippets' do
- let(:group) { create(:group, :public) }
- let(:project) { create(:project, :public, group: group) }
- let!(:private_project_snippet) { create(:project_snippet, :private, project: project) }
- let!(:internal_project_snippet) { create(:project_snippet, :internal, project: project) }
- let!(:public_project_snippet) { create(:project_snippet, :public, project: project) }
+ context 'filter by project' do
+ let(:user) { create :user }
+ let(:group) { create :group, :public }
+ let(:project1) { create(:project, :public, group: group) }
- it 'returns public personal and project snippets for unauthorized user' do
- snippets = described_class.new(nil, project: project).execute
+ before do
+ @snippet1 = create(:project_snippet, :private, project: project1)
+ @snippet2 = create(:project_snippet, :internal, project: project1)
+ @snippet3 = create(:project_snippet, :public, project: project1)
+ end
- expect(snippets).to contain_exactly(public_project_snippet)
- end
+ it "returns public snippets for unauthorized user" do
+ snippets = described_class.new(nil, project: project1).execute
- it 'returns public and internal snippets for non project members' do
- snippets = described_class.new(user, project: project).execute
+ expect(snippets).to include(@snippet3)
+ expect(snippets).not_to include(@snippet1, @snippet2)
+ end
- expect(snippets).to contain_exactly(internal_project_snippet, public_project_snippet)
- end
+ it "returns public and internal snippets for non project members" do
+ snippets = described_class.new(user, project: project1).execute
- it 'returns public snippets for non project members' do
- snippets = described_class.new(user, project: project, scope: :are_public).execute
+ expect(snippets).to include(@snippet2, @snippet3)
+ expect(snippets).not_to include(@snippet1)
+ end
- expect(snippets).to contain_exactly(public_project_snippet)
- end
+ it "returns public snippets for non project members" do
+ snippets = described_class.new(user, project: project1, scope: :are_public).execute
- it 'returns internal snippets for non project members' do
- snippets = described_class.new(user, project: project, scope: :are_internal).execute
+ expect(snippets).to include(@snippet3)
+ expect(snippets).not_to include(@snippet1, @snippet2)
+ end
- expect(snippets).to contain_exactly(internal_project_snippet)
- end
+ it "returns internal snippets for non project members" do
+ snippets = described_class.new(user, project: project1, scope: :are_internal).execute
- it 'does not return private snippets for non project members' do
- snippets = described_class.new(user, project: project, scope: :are_private).execute
+ expect(snippets).to include(@snippet2)
+ expect(snippets).not_to include(@snippet1, @snippet3)
+ end
- expect(snippets).to be_empty
- end
+ it "does not return private snippets for non project members" do
+ snippets = described_class.new(user, project: project1, scope: :are_private).execute
- it 'returns all snippets for project members' do
- project.add_developer(user)
+ expect(snippets).not_to include(@snippet1, @snippet2, @snippet3)
+ end
- snippets = described_class.new(user, project: project).execute
+ it "returns all snippets for project members" do
+ project1.add_developer(user)
- expect(snippets).to contain_exactly(private_project_snippet, internal_project_snippet, public_project_snippet)
- end
+ snippets = described_class.new(user, project: project1).execute
- it 'returns private snippets for project members' do
- project.add_developer(user)
+ expect(snippets).to include(@snippet1, @snippet2, @snippet3)
+ end
- snippets = described_class.new(user, project: project, scope: :are_private).execute
+ it "returns private snippets for project members" do
+ project1.add_developer(user)
- expect(snippets).to contain_exactly(private_project_snippet)
- end
+ snippets = described_class.new(user, project: project1, scope: :are_private).execute
- it 'returns all snippets for an admin' do
- admin = create(:user, :admin)
- snippets = described_class.new(admin, project: project).execute
+ expect(snippets).to include(@snippet1)
+ end
- expect(snippets).to contain_exactly(private_project_snippet, internal_project_snippet, public_project_snippet)
- end
+ it 'returns all snippets for an admin' do
+ admin = create(:user, :admin)
+ snippets = described_class.new(admin, project: project1).execute
+
+ expect(snippets).to include(@snippet1, @snippet2, @snippet3)
+ end
+ end
+
+ describe '#execute' do
+ let(:project) { create(:project, :public) }
+ let!(:project_snippet) { create(:project_snippet, :public, project: project) }
+ let!(:personal_snippet) { create(:personal_snippet, :public) }
+ let(:user) { create(:user) }
+ subject(:finder) { described_class.new(user) }
+
+ it 'returns project- and personal snippets' do
+ expect(finder.execute).to contain_exactly(project_snippet, personal_snippet)
end
context 'when the user cannot read cross project' do
@@ -158,7 +191,7 @@ describe SnippetsFinder do
end
it 'returns only personal snippets when the user cannot read cross project' do
- expect(described_class.new(user).execute).to contain_exactly(private_personal_snippet, internal_personal_snippet, public_personal_snippet)
+ expect(finder.execute).to contain_exactly(personal_snippet)
end
end
end
diff --git a/spec/finders/users_finder_spec.rb b/spec/finders/users_finder_spec.rb
index d71d3c99272..fecf97dc641 100644
--- a/spec/finders/users_finder_spec.rb
+++ b/spec/finders/users_finder_spec.rb
@@ -2,7 +2,10 @@ require 'spec_helper'
describe UsersFinder do
describe '#execute' do
- include_context 'UsersFinder#execute filter by project context'
+ let!(:user1) { create(:user, username: 'johndoe') }
+ let!(:user2) { create(:user, :blocked, username: 'notsorandom') }
+ let!(:external_user) { create(:user, :external) }
+ let!(:omniauth_user) { create(:omniauth_user, provider: 'twitter', extern_uid: '123456') }
context 'with a normal user' do
let(:user) { create(:user) }
@@ -10,43 +13,43 @@ describe UsersFinder do
it 'returns all users' do
users = described_class.new(user).execute
- expect(users).to contain_exactly(user, normal_user, blocked_user, omniauth_user)
+ expect(users).to contain_exactly(user, user1, user2, omniauth_user)
end
it 'filters by username' do
users = described_class.new(user, username: 'johndoe').execute
- expect(users).to contain_exactly(normal_user)
+ expect(users).to contain_exactly(user1)
end
it 'filters by username (case insensitive)' do
users = described_class.new(user, username: 'joHNdoE').execute
- expect(users).to contain_exactly(normal_user)
+ expect(users).to contain_exactly(user1)
end
it 'filters by search' do
users = described_class.new(user, search: 'orando').execute
- expect(users).to contain_exactly(blocked_user)
+ expect(users).to contain_exactly(user2)
end
it 'filters by blocked users' do
users = described_class.new(user, blocked: true).execute
- expect(users).to contain_exactly(blocked_user)
+ expect(users).to contain_exactly(user2)
end
it 'filters by active users' do
users = described_class.new(user, active: true).execute
- expect(users).to contain_exactly(user, normal_user, omniauth_user)
+ expect(users).to contain_exactly(user, user1, omniauth_user)
end
it 'returns no external users' do
users = described_class.new(user, external: true).execute
- expect(users).to contain_exactly(user, normal_user, blocked_user, omniauth_user)
+ expect(users).to contain_exactly(user, user1, user2, omniauth_user)
end
it 'filters by created_at' do
@@ -66,7 +69,7 @@ describe UsersFinder do
custom_attributes: { foo: 'bar' }
).execute
- expect(users).to contain_exactly(user, normal_user, blocked_user, omniauth_user)
+ expect(users).to contain_exactly(user, user1, user2, omniauth_user)
end
end
@@ -82,20 +85,20 @@ describe UsersFinder do
it 'returns all users' do
users = described_class.new(admin).execute
- expect(users).to contain_exactly(admin, normal_user, blocked_user, external_user, omniauth_user)
+ expect(users).to contain_exactly(admin, user1, user2, external_user, omniauth_user)
end
it 'filters by custom attributes' do
- create :user_custom_attribute, user: normal_user, key: 'foo', value: 'foo'
- create :user_custom_attribute, user: normal_user, key: 'bar', value: 'bar'
- create :user_custom_attribute, user: blocked_user, key: 'foo', value: 'foo'
+ create :user_custom_attribute, user: user1, key: 'foo', value: 'foo'
+ create :user_custom_attribute, user: user1, key: 'bar', value: 'bar'
+ create :user_custom_attribute, user: user2, key: 'foo', value: 'foo'
users = described_class.new(
admin,
custom_attributes: { foo: 'foo', bar: 'bar' }
).execute
- expect(users).to contain_exactly(normal_user)
+ expect(users).to contain_exactly(user1)
end
end
end
diff --git a/spec/support/shared_contexts/finders/group_projects_finder_shared_contexts.rb b/spec/support/shared_contexts/finders/group_projects_finder_shared_contexts.rb
deleted file mode 100644
index a0d994c4d8d..00000000000
--- a/spec/support/shared_contexts/finders/group_projects_finder_shared_contexts.rb
+++ /dev/null
@@ -1,24 +0,0 @@
-require 'spec_helper'
-
-RSpec.shared_context 'GroupProjectsFinder context' do
- let(:group) { create(:group) }
- let(:subgroup) { create(:group, parent: group) }
- let(:current_user) { create(:user) }
- let(:options) { {} }
-
- let(:finder) { described_class.new(group: group, current_user: current_user, options: options) }
-
- let!(:public_project) { create(:project, :public, group: group, path: '1') }
- let!(:private_project) { create(:project, :private, group: group, path: '2') }
- let!(:shared_project_1) { create(:project, :public, path: '3') }
- let!(:shared_project_2) { create(:project, :private, path: '4') }
- let!(:shared_project_3) { create(:project, :internal, path: '5') }
- let!(:subgroup_project) { create(:project, :public, path: '6', group: subgroup) }
- let!(:subgroup_private_project) { create(:project, :private, path: '7', group: subgroup) }
-
- before do
- shared_project_1.project_group_links.create(group_access: Gitlab::Access::MAINTAINER, group: group)
- shared_project_2.project_group_links.create(group_access: Gitlab::Access::MAINTAINER, group: group)
- shared_project_3.project_group_links.create(group_access: Gitlab::Access::MAINTAINER, group: group)
- end
-end
diff --git a/spec/support/shared_contexts/finders/issues_finder_shared_contexts.rb b/spec/support/shared_contexts/finders/issues_finder_shared_contexts.rb
deleted file mode 100644
index b8a9554f55f..00000000000
--- a/spec/support/shared_contexts/finders/issues_finder_shared_contexts.rb
+++ /dev/null
@@ -1,44 +0,0 @@
-require 'spec_helper'
-
-RSpec.shared_context 'IssuesFinder context' do
- set(:user) { create(:user) }
- set(:user2) { create(:user) }
- set(:group) { create(:group) }
- set(:subgroup) { create(:group, parent: group) }
- set(:project1) { create(:project, group: group) }
- set(:project2) { create(:project) }
- set(:project3) { create(:project, group: subgroup) }
- set(:milestone) { create(:milestone, project: project1) }
- set(:label) { create(:label, project: project2) }
- set(:issue1) { create(:issue, author: user, assignees: [user], project: project1, milestone: milestone, title: 'gitlab', created_at: 1.week.ago, updated_at: 1.week.ago) }
- set(:issue2) { create(:issue, author: user, assignees: [user], project: project2, description: 'gitlab', created_at: 1.week.from_now, updated_at: 1.week.from_now) }
- set(:issue3) { create(:issue, author: user2, assignees: [user2], project: project2, title: 'tanuki', description: 'tanuki', created_at: 2.weeks.from_now, updated_at: 2.weeks.from_now) }
- set(:issue4) { create(:issue, project: project3) }
- set(:award_emoji1) { create(:award_emoji, name: 'thumbsup', user: user, awardable: issue1) }
- set(:award_emoji2) { create(:award_emoji, name: 'thumbsup', user: user2, awardable: issue2) }
- set(:award_emoji3) { create(:award_emoji, name: 'thumbsdown', user: user, awardable: issue3) }
-end
-
-RSpec.shared_context 'IssuesFinder#execute context' do
- let!(:closed_issue) { create(:issue, author: user2, assignees: [user2], project: project2, state: 'closed') }
- let!(:label_link) { create(:label_link, label: label, target: issue2) }
- let(:search_user) { user }
- let(:params) { {} }
- let(:issues) { described_class.new(search_user, params.reverse_merge(scope: scope, state: 'opened')).execute }
-
- before(:context) do
- project1.add_maintainer(user)
- project2.add_developer(user)
- project2.add_developer(user2)
- project3.add_developer(user)
-
- issue1
- issue2
- issue3
- issue4
-
- award_emoji1
- award_emoji2
- award_emoji3
- end
-end
diff --git a/spec/support/shared_contexts/finders/merge_requests_finder_shared_contexts.rb b/spec/support/shared_contexts/finders/merge_requests_finder_shared_contexts.rb
deleted file mode 100644
index 4df80b4168a..00000000000
--- a/spec/support/shared_contexts/finders/merge_requests_finder_shared_contexts.rb
+++ /dev/null
@@ -1,65 +0,0 @@
-require 'spec_helper'
-
-RSpec.shared_context 'MergeRequestsFinder multiple projects with merge requests context' do
- include ProjectForksHelper
-
- # We need to explicitly permit Gitaly N+1s because of the specs that use
- # :request_store. Gitaly N+1 detection is only enabled when :request_store is,
- # but we don't care about potential N+1s when we're just creating several
- # projects in the setup phase.
- def allow_gitaly_n_plus_1
- Gitlab::GitalyClient.allow_n_plus_1_calls do
- yield
- end
- end
-
- set(:user) { create(:user) }
- set(:user2) { create(:user) }
-
- set(:group) { create(:group) }
- set(:subgroup) { create(:group, parent: group) }
- set(:project1) do
- allow_gitaly_n_plus_1 { create(:project, :public, group: group) }
- end
- # We cannot use `set` here otherwise we get:
- # Failure/Error: allow(RepositoryForkWorker).to receive(:perform_async).and_return(true)
- # The use of doubles or partial doubles from rspec-mocks outside of the per-test lifecycle is not supported.
- let(:project2) do
- allow_gitaly_n_plus_1 do
- fork_project(project1, user)
- end
- end
- let(:project3) do
- allow_gitaly_n_plus_1 do
- fork_project(project1, user).tap do |project|
- project.update!(archived: true)
- end
- end
- end
- set(:project4) do
- allow_gitaly_n_plus_1 { create(:project, :repository, group: subgroup) }
- end
- set(:project5) do
- allow_gitaly_n_plus_1 { create(:project, group: subgroup) }
- end
- set(:project6) do
- allow_gitaly_n_plus_1 { create(:project, group: subgroup) }
- end
-
- let!(:merge_request1) { create(:merge_request, author: user, source_project: project2, target_project: project1, target_branch: 'merged-target') }
- let!(:merge_request2) { create(:merge_request, :conflict, author: user, source_project: project2, target_project: project1, state: 'closed') }
- let!(:merge_request3) { create(:merge_request, :simple, author: user, source_project: project2, target_project: project2, state: 'locked', title: 'thing WIP thing') }
- let!(:merge_request4) { create(:merge_request, :simple, author: user, source_project: project3, target_project: project3, title: 'WIP thing') }
- let!(:merge_request5) { create(:merge_request, :simple, author: user, source_project: project4, target_project: project4, title: '[WIP]') }
-
- before do
- project1.add_maintainer(user)
- project2.add_developer(user)
- project3.add_developer(user)
- project4.add_developer(user)
- project5.add_developer(user)
- project6.add_developer(user)
-
- project2.add_developer(user2)
- end
-end
diff --git a/spec/support/shared_contexts/finders/users_finder_shared_contexts.rb b/spec/support/shared_contexts/finders/users_finder_shared_contexts.rb
deleted file mode 100644
index 9e1f89ee0ed..00000000000
--- a/spec/support/shared_contexts/finders/users_finder_shared_contexts.rb
+++ /dev/null
@@ -1,8 +0,0 @@
-require 'spec_helper'
-
-RSpec.shared_context 'UsersFinder#execute filter by project context' do
- set(:normal_user) { create(:user, username: 'johndoe') }
- set(:blocked_user) { create(:user, :blocked, username: 'notsorandom') }
- set(:external_user) { create(:user, :external) }
- set(:omniauth_user) { create(:omniauth_user, provider: 'twitter', extern_uid: '123456') }
-end
diff --git a/spec/support/shared_examples/snippet_visibility.rb b/spec/support/shared_examples/snippet_visibility.rb
new file mode 100644
index 00000000000..3a7c69b7877
--- /dev/null
+++ b/spec/support/shared_examples/snippet_visibility.rb
@@ -0,0 +1,322 @@
+RSpec.shared_examples 'snippet visibility' do
+ let!(:author) { create(:user) }
+ let!(:member) { create(:user) }
+ let!(:external) { create(:user, :external) }
+
+ let!(:snippet_type_visibilities) do
+ {
+ public: Snippet::PUBLIC,
+ internal: Snippet::INTERNAL,
+ private: Snippet::PRIVATE
+ }
+ end
+
+ context "For project snippets" do
+ let!(:users) do
+ {
+ unauthenticated: nil,
+ external: external,
+ non_member: create(:user),
+ member: member,
+ author: author
+ }
+ end
+
+ let!(:project_type_visibilities) do
+ {
+ public: Gitlab::VisibilityLevel::PUBLIC,
+ internal: Gitlab::VisibilityLevel::INTERNAL,
+ private: Gitlab::VisibilityLevel::PRIVATE
+ }
+ end
+
+ let(:project_feature_visibilities) do
+ {
+ enabled: ProjectFeature::ENABLED,
+ private: ProjectFeature::PRIVATE,
+ disabled: ProjectFeature::DISABLED
+ }
+ end
+
+ where(:project_type, :feature_visibility, :user_type, :snippet_type, :outcome) do
+ [
+ # Public projects
+ [:public, :enabled, :unauthenticated, :public, true],
+ [:public, :enabled, :unauthenticated, :internal, false],
+ [:public, :enabled, :unauthenticated, :private, false],
+
+ [:public, :enabled, :external, :public, true],
+ [:public, :enabled, :external, :internal, false],
+ [:public, :enabled, :external, :private, false],
+
+ [:public, :enabled, :non_member, :public, true],
+ [:public, :enabled, :non_member, :internal, true],
+ [:public, :enabled, :non_member, :private, false],
+
+ [:public, :enabled, :member, :public, true],
+ [:public, :enabled, :member, :internal, true],
+ [:public, :enabled, :member, :private, true],
+
+ [:public, :enabled, :author, :public, true],
+ [:public, :enabled, :author, :internal, true],
+ [:public, :enabled, :author, :private, true],
+
+ [:public, :private, :unauthenticated, :public, false],
+ [:public, :private, :unauthenticated, :internal, false],
+ [:public, :private, :unauthenticated, :private, false],
+
+ [:public, :private, :external, :public, false],
+ [:public, :private, :external, :internal, false],
+ [:public, :private, :external, :private, false],
+
+ [:public, :private, :non_member, :public, false],
+ [:public, :private, :non_member, :internal, false],
+ [:public, :private, :non_member, :private, false],
+
+ [:public, :private, :member, :public, true],
+ [:public, :private, :member, :internal, true],
+ [:public, :private, :member, :private, true],
+
+ [:public, :private, :author, :public, true],
+ [:public, :private, :author, :internal, true],
+ [:public, :private, :author, :private, true],
+
+ [:public, :disabled, :unauthenticated, :public, false],
+ [:public, :disabled, :unauthenticated, :internal, false],
+ [:public, :disabled, :unauthenticated, :private, false],
+
+ [:public, :disabled, :external, :public, false],
+ [:public, :disabled, :external, :internal, false],
+ [:public, :disabled, :external, :private, false],
+
+ [:public, :disabled, :non_member, :public, false],
+ [:public, :disabled, :non_member, :internal, false],
+ [:public, :disabled, :non_member, :private, false],
+
+ [:public, :disabled, :member, :public, false],
+ [:public, :disabled, :member, :internal, false],
+ [:public, :disabled, :member, :private, false],
+
+ [:public, :disabled, :author, :public, false],
+ [:public, :disabled, :author, :internal, false],
+ [:public, :disabled, :author, :private, false],
+
+ # Internal projects
+ [:internal, :enabled, :unauthenticated, :public, false],
+ [:internal, :enabled, :unauthenticated, :internal, false],
+ [:internal, :enabled, :unauthenticated, :private, false],
+
+ [:internal, :enabled, :external, :public, false],
+ [:internal, :enabled, :external, :internal, false],
+ [:internal, :enabled, :external, :private, false],
+
+ [:internal, :enabled, :non_member, :public, true],
+ [:internal, :enabled, :non_member, :internal, true],
+ [:internal, :enabled, :non_member, :private, false],
+
+ [:internal, :enabled, :member, :public, true],
+ [:internal, :enabled, :member, :internal, true],
+ [:internal, :enabled, :member, :private, true],
+
+ [:internal, :enabled, :author, :public, true],
+ [:internal, :enabled, :author, :internal, true],
+ [:internal, :enabled, :author, :private, true],
+
+ [:internal, :private, :unauthenticated, :public, false],
+ [:internal, :private, :unauthenticated, :internal, false],
+ [:internal, :private, :unauthenticated, :private, false],
+
+ [:internal, :private, :external, :public, false],
+ [:internal, :private, :external, :internal, false],
+ [:internal, :private, :external, :private, false],
+
+ [:internal, :private, :non_member, :public, false],
+ [:internal, :private, :non_member, :internal, false],
+ [:internal, :private, :non_member, :private, false],
+
+ [:internal, :private, :member, :public, true],
+ [:internal, :private, :member, :internal, true],
+ [:internal, :private, :member, :private, true],
+
+ [:internal, :private, :author, :public, true],
+ [:internal, :private, :author, :internal, true],
+ [:internal, :private, :author, :private, true],
+
+ [:internal, :disabled, :unauthenticated, :public, false],
+ [:internal, :disabled, :unauthenticated, :internal, false],
+ [:internal, :disabled, :unauthenticated, :private, false],
+
+ [:internal, :disabled, :external, :public, false],
+ [:internal, :disabled, :external, :internal, false],
+ [:internal, :disabled, :external, :private, false],
+
+ [:internal, :disabled, :non_member, :public, false],
+ [:internal, :disabled, :non_member, :internal, false],
+ [:internal, :disabled, :non_member, :private, false],
+
+ [:internal, :disabled, :member, :public, false],
+ [:internal, :disabled, :member, :internal, false],
+ [:internal, :disabled, :member, :private, false],
+
+ [:internal, :disabled, :author, :public, false],
+ [:internal, :disabled, :author, :internal, false],
+ [:internal, :disabled, :author, :private, false],
+
+ # Private projects
+ [:private, :enabled, :unauthenticated, :public, false],
+ [:private, :enabled, :unauthenticated, :internal, false],
+ [:private, :enabled, :unauthenticated, :private, false],
+
+ [:private, :enabled, :external, :public, true],
+ [:private, :enabled, :external, :internal, true],
+ [:private, :enabled, :external, :private, true],
+
+ [:private, :enabled, :non_member, :public, false],
+ [:private, :enabled, :non_member, :internal, false],
+ [:private, :enabled, :non_member, :private, false],
+
+ [:private, :enabled, :member, :public, true],
+ [:private, :enabled, :member, :internal, true],
+ [:private, :enabled, :member, :private, true],
+
+ [:private, :enabled, :author, :public, true],
+ [:private, :enabled, :author, :internal, true],
+ [:private, :enabled, :author, :private, true],
+
+ [:private, :private, :unauthenticated, :public, false],
+ [:private, :private, :unauthenticated, :internal, false],
+ [:private, :private, :unauthenticated, :private, false],
+
+ [:private, :private, :external, :public, true],
+ [:private, :private, :external, :internal, true],
+ [:private, :private, :external, :private, true],
+
+ [:private, :private, :non_member, :public, false],
+ [:private, :private, :non_member, :internal, false],
+ [:private, :private, :non_member, :private, false],
+
+ [:private, :private, :member, :public, true],
+ [:private, :private, :member, :internal, true],
+ [:private, :private, :member, :private, true],
+
+ [:private, :private, :author, :public, true],
+ [:private, :private, :author, :internal, true],
+ [:private, :private, :author, :private, true],
+
+ [:private, :disabled, :unauthenticated, :public, false],
+ [:private, :disabled, :unauthenticated, :internal, false],
+ [:private, :disabled, :unauthenticated, :private, false],
+
+ [:private, :disabled, :external, :public, false],
+ [:private, :disabled, :external, :internal, false],
+ [:private, :disabled, :external, :private, false],
+
+ [:private, :disabled, :non_member, :public, false],
+ [:private, :disabled, :non_member, :internal, false],
+ [:private, :disabled, :non_member, :private, false],
+
+ [:private, :disabled, :member, :public, false],
+ [:private, :disabled, :member, :internal, false],
+ [:private, :disabled, :member, :private, false],
+
+ [:private, :disabled, :author, :public, false],
+ [:private, :disabled, :author, :internal, false],
+ [:private, :disabled, :author, :private, false]
+ ]
+ end
+
+ with_them do
+ let!(:project) { create(:project, visibility_level: project_type_visibilities[project_type]) }
+ let!(:project_feature) { project.project_feature.update_column(:snippets_access_level, project_feature_visibilities[feature_visibility]) }
+ let!(:user) { users[user_type] }
+ let!(:snippet) { create(:project_snippet, visibility_level: snippet_type_visibilities[snippet_type], project: project, author: author) }
+ let!(:members) do
+ project.add_developer(author)
+ project.add_developer(member)
+ project.add_developer(external) if project.private?
+ end
+
+ context "For #{params[:project_type]} project and #{params[:user_type]} users" do
+ it 'should agree with the read_project_snippet policy' do
+ expect(can?(user, :read_project_snippet, snippet)).to eq(outcome)
+ end
+
+ it 'should return proper outcome' do
+ results = described_class.new(user, project: project).execute
+ expect(results.include?(snippet)).to eq(outcome)
+ end
+ end
+
+ context "Without a given project and #{params[:user_type]} users" do
+ it 'should return proper outcome' do
+ results = described_class.new(user).execute
+ expect(results.include?(snippet)).to eq(outcome)
+ end
+
+ it 'returns no snippets when the user cannot read cross project' do
+ allow(Ability).to receive(:allowed?).and_call_original
+ allow(Ability).to receive(:allowed?).with(user, :read_cross_project) { false }
+
+ snippets = described_class.new(user).execute
+
+ expect(snippets).to be_empty
+ end
+ end
+ end
+ end
+
+ context 'For personal snippets' do
+ let!(:users) do
+ {
+ unauthenticated: nil,
+ external: external,
+ non_member: create(:user),
+ author: author
+ }
+ end
+
+ where(:snippet_visibility, :user_type, :outcome) do
+ [
+ [:public, :unauthenticated, true],
+ [:public, :external, true],
+ [:public, :non_member, true],
+ [:public, :author, true],
+
+ [:internal, :unauthenticated, false],
+ [:internal, :external, false],
+ [:internal, :non_member, true],
+ [:internal, :author, true],
+
+ [:private, :unauthenticated, false],
+ [:private, :external, false],
+ [:private, :non_member, false],
+ [:private, :author, true]
+ ]
+ end
+
+ with_them do
+ let!(:user) { users[user_type] }
+ let!(:snippet) { create(:personal_snippet, visibility_level: snippet_type_visibilities[snippet_visibility], author: author) }
+
+ context "For personal and #{params[:snippet_visibility]} snippets with #{params[:user_type]} user" do
+ it 'should agree with read_personal_snippet policy' do
+ expect(can?(user, :read_personal_snippet, snippet)).to eq(outcome)
+ end
+
+ it 'should return proper outcome' do
+ results = described_class.new(user).execute
+ expect(results.include?(snippet)).to eq(outcome)
+ end
+
+ it 'should return personal snippets when the user cannot read cross project' do
+ allow(Ability).to receive(:allowed?).and_call_original
+ allow(Ability).to receive(:allowed?).with(user, :read_cross_project) { false }
+
+ results = described_class.new(user).execute
+
+ expect(results.include?(snippet)).to eq(outcome)
+ end
+ end
+ end
+ end
+end
diff --git a/spec/support/shared_examples/snippet_visibility_shared_examples.rb b/spec/support/shared_examples/snippet_visibility_shared_examples.rb
deleted file mode 100644
index 4f662db2120..00000000000
--- a/spec/support/shared_examples/snippet_visibility_shared_examples.rb
+++ /dev/null
@@ -1,306 +0,0 @@
-RSpec.shared_examples 'snippet visibility' do
- using RSpec::Parameterized::TableSyntax
-
- # Make sure no snippets exist prior to running the test matrix
- before(:context) do
- DatabaseCleaner.clean_with(:truncation)
- end
-
- set(:author) { create(:user) }
- set(:member) { create(:user) }
- set(:external) { create(:user, :external) }
-
- context "For project snippets" do
- let!(:users) do
- {
- unauthenticated: nil,
- external: external,
- non_member: create(:user),
- member: member,
- author: author
- }
- end
-
- where(:project_type, :feature_visibility, :user_type, :snippet_type, :outcome) do
- [
- # Public projects
- [:public, ProjectFeature::ENABLED, :unauthenticated, Snippet::PUBLIC, true],
- [:public, ProjectFeature::ENABLED, :unauthenticated, Snippet::INTERNAL, false],
- [:public, ProjectFeature::ENABLED, :unauthenticated, Snippet::PRIVATE, false],
-
- [:public, ProjectFeature::ENABLED, :external, Snippet::PUBLIC, true],
- [:public, ProjectFeature::ENABLED, :external, Snippet::INTERNAL, false],
- [:public, ProjectFeature::ENABLED, :external, Snippet::PRIVATE, false],
-
- [:public, ProjectFeature::ENABLED, :non_member, Snippet::PUBLIC, true],
- [:public, ProjectFeature::ENABLED, :non_member, Snippet::INTERNAL, true],
- [:public, ProjectFeature::ENABLED, :non_member, Snippet::PRIVATE, false],
-
- [:public, ProjectFeature::ENABLED, :member, Snippet::PUBLIC, true],
- [:public, ProjectFeature::ENABLED, :member, Snippet::INTERNAL, true],
- [:public, ProjectFeature::ENABLED, :member, Snippet::PRIVATE, true],
-
- [:public, ProjectFeature::ENABLED, :author, Snippet::PUBLIC, true],
- [:public, ProjectFeature::ENABLED, :author, Snippet::INTERNAL, true],
- [:public, ProjectFeature::ENABLED, :author, Snippet::PRIVATE, true],
-
- [:public, ProjectFeature::PRIVATE, :unauthenticated, Snippet::PUBLIC, false],
- [:public, ProjectFeature::PRIVATE, :unauthenticated, Snippet::INTERNAL, false],
- [:public, ProjectFeature::PRIVATE, :unauthenticated, Snippet::PRIVATE, false],
-
- [:public, ProjectFeature::PRIVATE, :external, Snippet::PUBLIC, false],
- [:public, ProjectFeature::PRIVATE, :external, Snippet::INTERNAL, false],
- [:public, ProjectFeature::PRIVATE, :external, Snippet::PRIVATE, false],
-
- [:public, ProjectFeature::PRIVATE, :non_member, Snippet::PUBLIC, false],
- [:public, ProjectFeature::PRIVATE, :non_member, Snippet::INTERNAL, false],
- [:public, ProjectFeature::PRIVATE, :non_member, Snippet::PRIVATE, false],
-
- [:public, ProjectFeature::PRIVATE, :member, Snippet::PUBLIC, true],
- [:public, ProjectFeature::PRIVATE, :member, Snippet::INTERNAL, true],
- [:public, ProjectFeature::PRIVATE, :member, Snippet::PRIVATE, true],
-
- [:public, ProjectFeature::PRIVATE, :author, Snippet::PUBLIC, true],
- [:public, ProjectFeature::PRIVATE, :author, Snippet::INTERNAL, true],
- [:public, ProjectFeature::PRIVATE, :author, Snippet::PRIVATE, true],
-
- [:public, ProjectFeature::DISABLED, :unauthenticated, Snippet::PUBLIC, false],
- [:public, ProjectFeature::DISABLED, :unauthenticated, Snippet::INTERNAL, false],
- [:public, ProjectFeature::DISABLED, :unauthenticated, Snippet::PRIVATE, false],
-
- [:public, ProjectFeature::DISABLED, :external, Snippet::PUBLIC, false],
- [:public, ProjectFeature::DISABLED, :external, Snippet::INTERNAL, false],
- [:public, ProjectFeature::DISABLED, :external, Snippet::PRIVATE, false],
-
- [:public, ProjectFeature::DISABLED, :non_member, Snippet::PUBLIC, false],
- [:public, ProjectFeature::DISABLED, :non_member, Snippet::INTERNAL, false],
- [:public, ProjectFeature::DISABLED, :non_member, Snippet::PRIVATE, false],
-
- [:public, ProjectFeature::DISABLED, :member, Snippet::PUBLIC, false],
- [:public, ProjectFeature::DISABLED, :member, Snippet::INTERNAL, false],
- [:public, ProjectFeature::DISABLED, :member, Snippet::PRIVATE, false],
-
- [:public, ProjectFeature::DISABLED, :author, Snippet::PUBLIC, false],
- [:public, ProjectFeature::DISABLED, :author, Snippet::INTERNAL, false],
- [:public, ProjectFeature::DISABLED, :author, Snippet::PRIVATE, false],
-
- # Internal projects
- [:internal, ProjectFeature::ENABLED, :unauthenticated, Snippet::PUBLIC, false],
- [:internal, ProjectFeature::ENABLED, :unauthenticated, Snippet::INTERNAL, false],
- [:internal, ProjectFeature::ENABLED, :unauthenticated, Snippet::PRIVATE, false],
-
- [:internal, ProjectFeature::ENABLED, :external, Snippet::PUBLIC, false],
- [:internal, ProjectFeature::ENABLED, :external, Snippet::INTERNAL, false],
- [:internal, ProjectFeature::ENABLED, :external, Snippet::PRIVATE, false],
-
- [:internal, ProjectFeature::ENABLED, :non_member, Snippet::PUBLIC, true],
- [:internal, ProjectFeature::ENABLED, :non_member, Snippet::INTERNAL, true],
- [:internal, ProjectFeature::ENABLED, :non_member, Snippet::PRIVATE, false],
-
- [:internal, ProjectFeature::ENABLED, :member, Snippet::PUBLIC, true],
- [:internal, ProjectFeature::ENABLED, :member, Snippet::INTERNAL, true],
- [:internal, ProjectFeature::ENABLED, :member, Snippet::PRIVATE, true],
-
- [:internal, ProjectFeature::ENABLED, :author, Snippet::PUBLIC, true],
- [:internal, ProjectFeature::ENABLED, :author, Snippet::INTERNAL, true],
- [:internal, ProjectFeature::ENABLED, :author, Snippet::PRIVATE, true],
-
- [:internal, ProjectFeature::PRIVATE, :unauthenticated, Snippet::PUBLIC, false],
- [:internal, ProjectFeature::PRIVATE, :unauthenticated, Snippet::INTERNAL, false],
- [:internal, ProjectFeature::PRIVATE, :unauthenticated, Snippet::PRIVATE, false],
-
- [:internal, ProjectFeature::PRIVATE, :external, Snippet::PUBLIC, false],
- [:internal, ProjectFeature::PRIVATE, :external, Snippet::INTERNAL, false],
- [:internal, ProjectFeature::PRIVATE, :external, Snippet::PRIVATE, false],
-
- [:internal, ProjectFeature::PRIVATE, :non_member, Snippet::PUBLIC, false],
- [:internal, ProjectFeature::PRIVATE, :non_member, Snippet::INTERNAL, false],
- [:internal, ProjectFeature::PRIVATE, :non_member, Snippet::PRIVATE, false],
-
- [:internal, ProjectFeature::PRIVATE, :member, Snippet::PUBLIC, true],
- [:internal, ProjectFeature::PRIVATE, :member, Snippet::INTERNAL, true],
- [:internal, ProjectFeature::PRIVATE, :member, Snippet::PRIVATE, true],
-
- [:internal, ProjectFeature::PRIVATE, :author, Snippet::PUBLIC, true],
- [:internal, ProjectFeature::PRIVATE, :author, Snippet::INTERNAL, true],
- [:internal, ProjectFeature::PRIVATE, :author, Snippet::PRIVATE, true],
-
- [:internal, ProjectFeature::DISABLED, :unauthenticated, Snippet::PUBLIC, false],
- [:internal, ProjectFeature::DISABLED, :unauthenticated, Snippet::INTERNAL, false],
- [:internal, ProjectFeature::DISABLED, :unauthenticated, Snippet::PRIVATE, false],
-
- [:internal, ProjectFeature::DISABLED, :external, Snippet::PUBLIC, false],
- [:internal, ProjectFeature::DISABLED, :external, Snippet::INTERNAL, false],
- [:internal, ProjectFeature::DISABLED, :external, Snippet::PRIVATE, false],
-
- [:internal, ProjectFeature::DISABLED, :non_member, Snippet::PUBLIC, false],
- [:internal, ProjectFeature::DISABLED, :non_member, Snippet::INTERNAL, false],
- [:internal, ProjectFeature::DISABLED, :non_member, Snippet::PRIVATE, false],
-
- [:internal, ProjectFeature::DISABLED, :member, Snippet::PUBLIC, false],
- [:internal, ProjectFeature::DISABLED, :member, Snippet::INTERNAL, false],
- [:internal, ProjectFeature::DISABLED, :member, Snippet::PRIVATE, false],
-
- [:internal, ProjectFeature::DISABLED, :author, Snippet::PUBLIC, false],
- [:internal, ProjectFeature::DISABLED, :author, Snippet::INTERNAL, false],
- [:internal, ProjectFeature::DISABLED, :author, Snippet::PRIVATE, false],
-
- # Private projects
- [:private, ProjectFeature::ENABLED, :unauthenticated, Snippet::PUBLIC, false],
- [:private, ProjectFeature::ENABLED, :unauthenticated, Snippet::INTERNAL, false],
- [:private, ProjectFeature::ENABLED, :unauthenticated, Snippet::PRIVATE, false],
-
- [:private, ProjectFeature::ENABLED, :external, Snippet::PUBLIC, true],
- [:private, ProjectFeature::ENABLED, :external, Snippet::INTERNAL, true],
- [:private, ProjectFeature::ENABLED, :external, Snippet::PRIVATE, true],
-
- [:private, ProjectFeature::ENABLED, :non_member, Snippet::PUBLIC, false],
- [:private, ProjectFeature::ENABLED, :non_member, Snippet::INTERNAL, false],
- [:private, ProjectFeature::ENABLED, :non_member, Snippet::PRIVATE, false],
-
- [:private, ProjectFeature::ENABLED, :member, Snippet::PUBLIC, true],
- [:private, ProjectFeature::ENABLED, :member, Snippet::INTERNAL, true],
- [:private, ProjectFeature::ENABLED, :member, Snippet::PRIVATE, true],
-
- [:private, ProjectFeature::ENABLED, :author, Snippet::PUBLIC, true],
- [:private, ProjectFeature::ENABLED, :author, Snippet::INTERNAL, true],
- [:private, ProjectFeature::ENABLED, :author, Snippet::PRIVATE, true],
-
- [:private, ProjectFeature::PRIVATE, :unauthenticated, Snippet::PUBLIC, false],
- [:private, ProjectFeature::PRIVATE, :unauthenticated, Snippet::INTERNAL, false],
- [:private, ProjectFeature::PRIVATE, :unauthenticated, Snippet::PRIVATE, false],
-
- [:private, ProjectFeature::PRIVATE, :external, Snippet::PUBLIC, true],
- [:private, ProjectFeature::PRIVATE, :external, Snippet::INTERNAL, true],
- [:private, ProjectFeature::PRIVATE, :external, Snippet::PRIVATE, true],
-
- [:private, ProjectFeature::PRIVATE, :non_member, Snippet::PUBLIC, false],
- [:private, ProjectFeature::PRIVATE, :non_member, Snippet::INTERNAL, false],
- [:private, ProjectFeature::PRIVATE, :non_member, Snippet::PRIVATE, false],
-
- [:private, ProjectFeature::PRIVATE, :member, Snippet::PUBLIC, true],
- [:private, ProjectFeature::PRIVATE, :member, Snippet::INTERNAL, true],
- [:private, ProjectFeature::PRIVATE, :member, Snippet::PRIVATE, true],
-
- [:private, ProjectFeature::PRIVATE, :author, Snippet::PUBLIC, true],
- [:private, ProjectFeature::PRIVATE, :author, Snippet::INTERNAL, true],
- [:private, ProjectFeature::PRIVATE, :author, Snippet::PRIVATE, true],
-
- [:private, ProjectFeature::DISABLED, :unauthenticated, Snippet::PUBLIC, false],
- [:private, ProjectFeature::DISABLED, :unauthenticated, Snippet::INTERNAL, false],
- [:private, ProjectFeature::DISABLED, :unauthenticated, Snippet::PRIVATE, false],
-
- [:private, ProjectFeature::DISABLED, :external, Snippet::PUBLIC, false],
- [:private, ProjectFeature::DISABLED, :external, Snippet::INTERNAL, false],
- [:private, ProjectFeature::DISABLED, :external, Snippet::PRIVATE, false],
-
- [:private, ProjectFeature::DISABLED, :non_member, Snippet::PUBLIC, false],
- [:private, ProjectFeature::DISABLED, :non_member, Snippet::INTERNAL, false],
- [:private, ProjectFeature::DISABLED, :non_member, Snippet::PRIVATE, false],
-
- [:private, ProjectFeature::DISABLED, :member, Snippet::PUBLIC, false],
- [:private, ProjectFeature::DISABLED, :member, Snippet::INTERNAL, false],
- [:private, ProjectFeature::DISABLED, :member, Snippet::PRIVATE, false],
-
- [:private, ProjectFeature::DISABLED, :author, Snippet::PUBLIC, false],
- [:private, ProjectFeature::DISABLED, :author, Snippet::INTERNAL, false],
- [:private, ProjectFeature::DISABLED, :author, Snippet::PRIVATE, false]
- ]
- end
-
- with_them do
- let!(:project) { create(:project, visibility_level: Gitlab::VisibilityLevel.level_value(project_type.to_s)) }
- let!(:project_feature) { project.project_feature.update_column(:snippets_access_level, feature_visibility) }
- let!(:user) { users[user_type] }
- let!(:snippet) { create(:project_snippet, visibility_level: snippet_type, project: project, author: author) }
- let!(:members) do
- project.add_developer(author)
- project.add_developer(member)
- project.add_developer(external) if project.private?
- end
-
- context "For #{params[:project_type]} project and #{params[:user_type]} users" do
- it 'should agree with the read_project_snippet policy' do
- expect(can?(user, :read_project_snippet, snippet)).to eq(outcome)
- end
-
- it 'should return proper outcome' do
- results = described_class.new(user, project: project).execute
-
- expect(results.include?(snippet)).to eq(outcome)
- end
- end
-
- context "Without a given project and #{params[:user_type]} users" do
- it 'should return proper outcome' do
- results = described_class.new(user).execute
- expect(results.include?(snippet)).to eq(outcome)
- end
-
- it 'returns no snippets when the user cannot read cross project' do
- allow(Ability).to receive(:allowed?).and_call_original
- allow(Ability).to receive(:allowed?).with(user, :read_cross_project) { false }
-
- snippets = described_class.new(user).execute
-
- expect(snippets).to be_empty
- end
- end
- end
- end
-
- context 'For personal snippets' do
- let!(:users) do
- {
- unauthenticated: nil,
- external: external,
- non_member: create(:user),
- author: author
- }
- end
-
- where(:snippet_visibility, :user_type, :outcome) do
- [
- [Snippet::PUBLIC, :unauthenticated, true],
- [Snippet::PUBLIC, :external, true],
- [Snippet::PUBLIC, :non_member, true],
- [Snippet::PUBLIC, :author, true],
-
- [Snippet::INTERNAL, :unauthenticated, false],
- [Snippet::INTERNAL, :external, false],
- [Snippet::INTERNAL, :non_member, true],
- [Snippet::INTERNAL, :author, true],
-
- [Snippet::PRIVATE, :unauthenticated, false],
- [Snippet::PRIVATE, :external, false],
- [Snippet::PRIVATE, :non_member, false],
- [Snippet::PRIVATE, :author, true]
- ]
- end
-
- with_them do
- let!(:user) { users[user_type] }
- let!(:snippet) { create(:personal_snippet, visibility_level: snippet_visibility, author: author) }
-
- context "For personal and #{params[:snippet_visibility]} snippets with #{params[:user_type]} user" do
- it 'should agree with read_personal_snippet policy' do
- expect(can?(user, :read_personal_snippet, snippet)).to eq(outcome)
- end
-
- it 'should return proper outcome' do
- results = described_class.new(user).execute
- expect(results.include?(snippet)).to eq(outcome)
- end
-
- it 'should return personal snippets when the user cannot read cross project' do
- allow(Ability).to receive(:allowed?).and_call_original
- allow(Ability).to receive(:allowed?).with(user, :read_cross_project) { false }
-
- results = described_class.new(user).execute
-
- expect(results.include?(snippet)).to eq(outcome)
- end
- end
- end
- end
-end