Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.com/gitlab-org/gitlab-foss.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'spec/requests/api/graphql/project/branch_rules_spec.rb')
-rw-r--r--spec/requests/api/graphql/project/branch_rules_spec.rb143
1 files changed, 108 insertions, 35 deletions
diff --git a/spec/requests/api/graphql/project/branch_rules_spec.rb b/spec/requests/api/graphql/project/branch_rules_spec.rb
index 1aaf0e9edc7..ed866305445 100644
--- a/spec/requests/api/graphql/project/branch_rules_spec.rb
+++ b/spec/requests/api/graphql/project/branch_rules_spec.rb
@@ -7,10 +7,9 @@ RSpec.describe 'getting list of branch rules for a project' do
let_it_be(:project) { create(:project, :repository, :public) }
let_it_be(:current_user) { create(:user) }
- let_it_be(:branch_name_a) { 'branch_name_a' }
- let_it_be(:branch_name_b) { 'wildcard-*' }
+ let_it_be(:branch_name_a) { TestEnv::BRANCH_SHA.each_key.first }
+ let_it_be(:branch_name_b) { 'diff-*' }
let_it_be(:branch_rules) { [branch_rule_a, branch_rule_b] }
-
let_it_be(:branch_rule_a) do
create(:protected_branch, project: project, name: branch_name_a)
end
@@ -21,7 +20,6 @@ RSpec.describe 'getting list of branch rules for a project' do
let(:branch_rules_data) { graphql_data_at('project', 'branchRules', 'edges') }
let(:variables) { { path: project.full_path } }
- # fields must use let as the all_graphql_fields_for also configures some spies
let(:fields) { all_graphql_fields_for('BranchRule') }
let(:query) do
<<~GQL
@@ -60,49 +58,124 @@ RSpec.describe 'getting list of branch rules for a project' do
context 'when the user does have read_protected_branch abilities' do
before do
project.add_maintainer(current_user)
- post_graphql(query, current_user: current_user, variables: variables)
end
- it_behaves_like 'a working graphql query'
+ describe 'queries' do
+ before do
+ # rubocop:disable RSpec/AnyInstanceOf
+ allow_any_instance_of(User).to receive(:update_tracked_fields!)
+ allow_any_instance_of(Users::ActivityService).to receive(:execute)
+ # rubocop:enable RSpec/AnyInstanceOf
+ allow_next_instance_of(Resolvers::ProjectResolver) do |resolver|
+ allow(resolver).to receive(:resolve)
+ .with(full_path: project.full_path)
+ .and_return(project)
+ end
+ allow(project.repository).to receive(:branch_names).and_call_original
+ allow(project.repository.gitaly_ref_client).to receive(:branch_names).and_call_original
+ end
+
+ it 'matching_branches_count avoids N+1 queries' do
+ query = <<~GQL
+ query($path: ID!) {
+ project(fullPath: $path) {
+ branchRules {
+ nodes {
+ matchingBranchesCount
+ }
+ }
+ }
+ }
+ GQL
+
+ control = ActiveRecord::QueryRecorder.new do
+ post_graphql(query, current_user: current_user, variables: variables)
+ end
+
+ # Verify the response includes the field
+ expect_n_matching_branches_count_fields(2)
+
+ create(:protected_branch, project: project)
+ create(:protected_branch, name: '*', project: project)
+
+ expect do
+ post_graphql(query, current_user: current_user, variables: variables)
+ end.not_to exceed_all_query_limit(control)
+
+ expect(project.repository).to have_received(:branch_names).at_least(2).times
+ expect(project.repository.gitaly_ref_client).to have_received(:branch_names).once
- it 'returns branch rules data' do
- expect(branch_rules_data.dig(0, 'node', 'name')).to be_present
- expect(branch_rules_data.dig(0, 'node', 'isDefault')).to be(true).or be(false)
- expect(branch_rules_data.dig(0, 'node', 'branchProtection')).to be_present
- expect(branch_rules_data.dig(0, 'node', 'createdAt')).to be_present
- expect(branch_rules_data.dig(0, 'node', 'updatedAt')).to be_present
-
- expect(branch_rules_data.dig(1, 'node', 'name')).to be_present
- expect(branch_rules_data.dig(1, 'node', 'isDefault')).to be(true).or be(false)
- expect(branch_rules_data.dig(1, 'node', 'branchProtection')).to be_present
- expect(branch_rules_data.dig(1, 'node', 'createdAt')).to be_present
- expect(branch_rules_data.dig(1, 'node', 'updatedAt')).to be_present
+ expect_n_matching_branches_count_fields(4)
+ end
+
+ def expect_n_matching_branches_count_fields(count)
+ branch_rule_nodes = graphql_data_at('project', 'branchRules', 'nodes')
+ expect(branch_rule_nodes.count).to eq(count)
+ branch_rule_nodes.each do |node|
+ expect(node['matchingBranchesCount']).to be_present
+ end
+ end
end
- context 'when limiting the number of results' do
- let(:branch_rule_limit) { 1 }
- let(:variables) { { path: project.full_path, n: branch_rule_limit } }
- let(:next_variables) do
- { path: project.full_path, n: branch_rule_limit, cursor: last_cursor }
+ describe 'response' do
+ before do
+ post_graphql(query, current_user: current_user, variables: variables)
end
it_behaves_like 'a working graphql query'
- it 'returns pagination information' do
- expect(branch_rules_data.size).to eq(branch_rule_limit)
- expect(has_next_page).to be_truthy
- expect(has_prev_page).to be_falsey
- post_graphql(query, current_user: current_user, variables: next_variables)
- expect(branch_rules_data.size).to eq(branch_rule_limit)
- expect(has_next_page).to be_falsey
- expect(has_prev_page).to be_truthy
+ it 'includes all fields', :aggregate_failures do
+ # Responses will be sorted alphabetically. Branch names for this spec
+ # come from an external constant so we check which is first
+ br_a_idx = branch_name_a < branch_name_b ? 0 : 1
+ br_b_idx = 1 - br_a_idx
+
+ branch_rule_a_data = branch_rules_data.dig(br_a_idx, 'node')
+ branch_rule_b_data = branch_rules_data.dig(br_b_idx, 'node')
+
+ expect(branch_rule_a_data['name']).to eq(branch_name_a)
+ expect(branch_rule_a_data['isDefault']).to be(true).or be(false)
+ expect(branch_rule_a_data['branchProtection']).to be_present
+ expect(branch_rule_a_data['matchingBranchesCount']).to eq(1)
+ expect(branch_rule_a_data['createdAt']).to be_present
+ expect(branch_rule_a_data['updatedAt']).to be_present
+
+ wildcard_count = TestEnv::BRANCH_SHA.keys.count do |branch_name|
+ branch_name.starts_with?('diff-')
+ end
+ expect(branch_rule_b_data['name']).to eq(branch_name_b)
+ expect(branch_rule_b_data['isDefault']).to be(true).or be(false)
+ expect(branch_rule_b_data['branchProtection']).to be_present
+ expect(branch_rule_b_data['matchingBranchesCount']).to eq(wildcard_count)
+ expect(branch_rule_b_data['createdAt']).to be_present
+ expect(branch_rule_b_data['updatedAt']).to be_present
end
- context 'when no limit is provided' do
- let(:branch_rule_limit) { nil }
+ context 'when limiting the number of results' do
+ let(:branch_rule_limit) { 1 }
+ let(:variables) { { path: project.full_path, n: branch_rule_limit } }
+ let(:next_variables) do
+ { path: project.full_path, n: branch_rule_limit, cursor: last_cursor }
+ end
+
+ it_behaves_like 'a working graphql query'
+
+ it 'returns pagination information' do
+ expect(branch_rules_data.size).to eq(branch_rule_limit)
+ expect(has_next_page).to be_truthy
+ expect(has_prev_page).to be_falsey
+ post_graphql(query, current_user: current_user, variables: next_variables)
+ expect(branch_rules_data.size).to eq(branch_rule_limit)
+ expect(has_next_page).to be_falsey
+ expect(has_prev_page).to be_truthy
+ end
+
+ context 'when no limit is provided' do
+ let(:branch_rule_limit) { nil }
- it 'returns all branch_rules' do
- expect(branch_rules_data.size).to eq(branch_rules.size)
+ it 'returns all branch_rules' do
+ expect(branch_rules_data.size).to eq(branch_rules.size)
+ end
end
end
end