Skip to content
Snippets Groups Projects
Commit a5d59e81 authored by Rutger Wessels's avatar Rutger Wessels
Browse files

Merge branch '431918-build-editbranchrule-mutation' into 'master'

Create branchRuleUpdate graphql mutation

See merge request https://gitlab.com/gitlab-org/gitlab/-/merge_requests/138672



Merged-by: default avatarRutger Wessels <rwessels@gitlab.com>
Approved-by: default avatarEduardo Bonet <ebonet@gitlab.com>
Approved-by: default avatarRutger Wessels <rwessels@gitlab.com>
Reviewed-by: default avatarEduardo Bonet <ebonet@gitlab.com>
Reviewed-by: default avatarRutger Wessels <rwessels@gitlab.com>
Co-authored-by: default avatarghinfey <ghinfey@gitlab.com>
parents 75bfdd51 4b0fd1d5
No related branches found
No related tags found
No related merge requests found
# frozen_string_literal: true
module Mutations
module BranchRules
class Update < BaseMutation
graphql_name 'BranchRuleUpdate'
include FindsProject
authorize :admin_project
argument :id, ::Types::GlobalIDType[::ProtectedBranch],
required: true,
description: 'Global ID of the protected branch.'
argument :name, GraphQL::Types::String,
required: true,
description: 'Branch name, with wildcards, for the branch rules.'
argument :project_path, GraphQL::Types::ID,
required: true,
description: 'Full path to the project that the branch is associated with.'
field :branch_rule,
Types::Projects::BranchRuleType,
null: true,
description: 'Branch rule after mutation.'
def resolve(id:, project_path:, name:)
protected_branch = ::Gitlab::Graphql::Lazy.force(GitlabSchema.object_from_id(id,
expected_type: ::ProtectedBranch))
raise_resource_not_available_error! unless protected_branch
project = authorized_find!(project_path)
protected_branch = ::ProtectedBranches::UpdateService.new(project, current_user,
{ name: name }).execute(protected_branch)
if protected_branch.errors.empty?
{
branch_rule: ::Projects::BranchRule.new(project, protected_branch),
errors: []
}
else
{ errors: errors_on_object(protected_branch) }
end
end
end
end
end
Loading
Loading
@@ -110,6 +110,7 @@ class MutationType < BaseObject
mount_mutation Mutations::Organizations::Update, alpha: { milestone: '16.7' }
mount_mutation Mutations::Projects::SyncFork, calls_gitaly: true, alpha: { milestone: '15.9' }
mount_mutation Mutations::Projects::Star, alpha: { milestone: '16.7' }
mount_mutation Mutations::BranchRules::Update, alpha: { milestone: '16.7' }
mount_mutation Mutations::Releases::Create
mount_mutation Mutations::Releases::Update
mount_mutation Mutations::Releases::Delete
Loading
Loading
Loading
Loading
@@ -1945,6 +1945,31 @@ Input type: `BoardListUpdateLimitMetricsInput`
| <a id="mutationboardlistupdatelimitmetricserrors"></a>`errors` | [`[String!]!`](#string) | Errors encountered during execution of the mutation. |
| <a id="mutationboardlistupdatelimitmetricslist"></a>`list` | [`BoardList`](#boardlist) | Updated list. |
 
### `Mutation.branchRuleUpdate`
WARNING:
**Introduced** in 16.7.
This feature is an Experiment. It can be changed or removed at any time.
Input type: `BranchRuleUpdateInput`
#### Arguments
| Name | Type | Description |
| ---- | ---- | ----------- |
| <a id="mutationbranchruleupdateclientmutationid"></a>`clientMutationId` | [`String`](#string) | A unique identifier for the client performing the mutation. |
| <a id="mutationbranchruleupdateid"></a>`id` | [`ProtectedBranchID!`](#protectedbranchid) | Global ID of the protected branch. |
| <a id="mutationbranchruleupdatename"></a>`name` | [`String!`](#string) | Branch name, with wildcards, for the branch rules. |
| <a id="mutationbranchruleupdateprojectpath"></a>`projectPath` | [`ID!`](#id) | Full path to the project that the branch is associated with. |
#### Fields
| Name | Type | Description |
| ---- | ---- | ----------- |
| <a id="mutationbranchruleupdatebranchrule"></a>`branchRule` | [`BranchRule`](#branchrule) | Branch rule after mutation. |
| <a id="mutationbranchruleupdateclientmutationid"></a>`clientMutationId` | [`String`](#string) | A unique identifier for the client performing the mutation. |
| <a id="mutationbranchruleupdateerrors"></a>`errors` | [`[String!]!`](#string) | Errors encountered during execution of the mutation. |
### `Mutation.buildForecast`
 
WARNING:
Loading
Loading
@@ -32484,6 +32509,12 @@ A `ProjectImportStateID` is a global ID. It is encoded as a string.
 
An example `ProjectImportStateID` is: `"gid://gitlab/ProjectImportState/1"`.
 
### `ProtectedBranchID`
A `ProtectedBranchID` is a global ID. It is encoded as a string.
An example `ProtectedBranchID` is: `"gid://gitlab/ProtectedBranch/1"`.
### `ReleaseID`
 
A `ReleaseID` is a global ID. It is encoded as a string.
Loading
Loading
@@ -149,7 +149,7 @@ def load_all_data!(repository)
return if @data == '' # don't mess with submodule blobs
 
# Even if we return early, recalculate whether this blob is binary in
# case a blob was initialized as text but the full data isn't
# case a blob was initialized as text but the full data isn'tspec/requests/api/graphql/mutations/branch_rules/update_spec.rb:
@binary = nil
 
return if @loaded_all_data
Loading
Loading
# frozen_string_literal: true
require 'spec_helper'
RSpec.describe 'BranchRuleUpdate', feature_category: :source_code_management do
include GraphqlHelpers
let_it_be(:project) { create(:project, :public) }
let_it_be(:user) { create(:user) }
let!(:branch_rule_1) { create(:protected_branch, project: project, name: name_1) }
let!(:branch_rule_2) { create(:protected_branch, project: project, name: name_2) }
let(:name_1) { "name_1" }
let(:name_2) { "name_2" }
let(:new_name) { "new name" }
let(:id) { branch_rule_1.to_global_id }
let(:project_path) { project.full_path }
let(:name) { new_name }
let(:params) do
{
id: id,
project_path: project_path,
name: name
}
end
let(:mutation) { graphql_mutation(:branch_rule_update, params) }
subject(:post_mutation) { post_graphql_mutation(mutation, current_user: user) }
def mutation_response
graphql_mutation_response(:branch_rule_update)
end
context 'when the user does not have permission' do
before_all do
project.add_developer(user)
end
it 'does not update the branch rule' do
expect { post_mutation }.not_to change { branch_rule_1 }
end
end
context 'when the user can update a branch rules' do
let(:current_user) { user }
before_all do
project.add_maintainer(user)
end
it 'updates the protected branch' do
post_mutation
expect(branch_rule_1.reload.name).to eq(new_name)
end
it 'returns the updated branch rule' do
post_mutation
expect(mutation_response).to have_key('branchRule')
expect(mutation_response['branchRule']['name']).to eq(new_name)
expect(mutation_response['errors']).to be_empty
end
context 'when name already exists for the project' do
let(:params) do
{
id: id,
project_path: project_path,
name: name_2
}
end
it 'returns an error' do
post_mutation
expect(mutation_response['errors'].first).to eq('Name has already been taken')
end
end
context 'when the protected branch cannot be found' do
let(:id) { "gid://gitlab/ProtectedBranch/#{non_existing_record_id}" }
it_behaves_like 'a mutation that returns top-level errors',
errors: [Gitlab::Graphql::Authorize::AuthorizeResource::RESOURCE_ACCESS_ERROR]
end
context 'when the project cannot be found' do
let(:project_path) { 'not a project path' }
it_behaves_like 'a mutation that returns top-level errors',
errors: [Gitlab::Graphql::Authorize::AuthorizeResource::RESOURCE_ACCESS_ERROR]
end
end
end
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment