summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--changelogs/unreleased/39880-merge-method-api.yml5
-rw-r--r--doc/api/projects.md28
-rw-r--r--lib/api/entities.rb1
-rw-r--r--lib/api/projects.rb2
-rw-r--r--spec/requests/api/projects_spec.rb41
5 files changed, 76 insertions, 1 deletions
diff --git a/changelogs/unreleased/39880-merge-method-api.yml b/changelogs/unreleased/39880-merge-method-api.yml
new file mode 100644
index 00000000000..dd44a752c4f
--- /dev/null
+++ b/changelogs/unreleased/39880-merge-method-api.yml
@@ -0,0 +1,5 @@
+---
+title: 'API: Add parameter merge_method to projects'
+merge_request: 18031
+author: Jan Beckmann
+type: added
diff --git a/doc/api/projects.md b/doc/api/projects.md
index f388fae42a9..a0cb5aa0820 100644
--- a/doc/api/projects.md
+++ b/doc/api/projects.md
@@ -16,6 +16,21 @@ Values for the project visibility level are:
* `public`:
The project can be cloned without any authentication.
+## Project merge method
+
+There are currently three options for `merge_method` to choose from:
+
+* `merge`:
+ A merge commit is created for every merge, and merging is allowed as long as there are no conflicts.
+
+* `rebase_merge`:
+ A merge commit is created for every merge, but merging is only allowed if fast-forward merge is possible.
+ This way you could make sure that if this merge request would build, after merging to target branch it would also build.
+
+* `ff`:
+ No merge commits are created and all merges are fast-forwarded, which means that merging is only allowed if the branch could be fast-forwarded.
+
+
## List all projects
Get a list of all visible projects across GitLab for the authenticated user.
@@ -94,6 +109,7 @@ GET /projects
"only_allow_merge_if_pipeline_succeeds": false,
"only_allow_merge_if_all_discussions_are_resolved": false,
"request_access_enabled": false,
+ "merge_method": "merge",
"statistics": {
"commit_count": 37,
"storage_size": 1038090,
@@ -173,6 +189,7 @@ GET /projects
"only_allow_merge_if_pipeline_succeeds": false,
"only_allow_merge_if_all_discussions_are_resolved": false,
"request_access_enabled": false,
+ "merge_method": "merge",
"statistics": {
"commit_count": 12,
"storage_size": 2066080,
@@ -278,6 +295,7 @@ GET /users/:user_id/projects
"only_allow_merge_if_pipeline_succeeds": false,
"only_allow_merge_if_all_discussions_are_resolved": false,
"request_access_enabled": false,
+ "merge_method": "merge",
"statistics": {
"commit_count": 37,
"storage_size": 1038090,
@@ -357,6 +375,7 @@ GET /users/:user_id/projects
"only_allow_merge_if_pipeline_succeeds": false,
"only_allow_merge_if_all_discussions_are_resolved": false,
"request_access_enabled": false,
+ "merge_method": "merge",
"statistics": {
"commit_count": 12,
"storage_size": 2066080,
@@ -467,6 +486,7 @@ GET /projects/:id
"only_allow_merge_if_all_discussions_are_resolved": false,
"printing_merge_requests_link_enabled": true,
"request_access_enabled": false,
+ "merge_method": "merge",
"statistics": {
"commit_count": 37,
"storage_size": 1038090,
@@ -550,6 +570,7 @@ POST /projects
| `public_jobs` | boolean | no | If `true`, jobs can be viewed by non-project-members |
| `only_allow_merge_if_pipeline_succeeds` | boolean | no | Set whether merge requests can only be merged with successful jobs |
| `only_allow_merge_if_all_discussions_are_resolved` | boolean | no | Set whether merge requests can only be merged when all the discussions are resolved |
+| `merge_method` | string | no | Set the merge method used |
| `lfs_enabled` | boolean | no | Enable LFS |
| `request_access_enabled` | boolean | no | Allow users to request member access |
| `tag_list` | array | no | The list of tags for a project; put array of tags, that should be finally assigned to a project |
@@ -586,6 +607,7 @@ POST /projects/user/:user_id
| `public_jobs` | boolean | no | If `true`, jobs can be viewed by non-project-members |
| `only_allow_merge_if_pipeline_succeeds` | boolean | no | Set whether merge requests can only be merged with successful jobs |
| `only_allow_merge_if_all_discussions_are_resolved` | boolean | no | Set whether merge requests can only be merged when all the discussions are resolved |
+| `merge_method` | string | no | Set the merge method used |
| `lfs_enabled` | boolean | no | Enable LFS |
| `request_access_enabled` | boolean | no | Allow users to request member access |
| `tag_list` | array | no | The list of tags for a project; put array of tags, that should be finally assigned to a project |
@@ -621,6 +643,7 @@ PUT /projects/:id
| `public_jobs` | boolean | no | If `true`, jobs can be viewed by non-project-members |
| `only_allow_merge_if_pipeline_succeeds` | boolean | no | Set whether merge requests can only be merged with successful jobs |
| `only_allow_merge_if_all_discussions_are_resolved` | boolean | no | Set whether merge requests can only be merged when all the discussions are resolved |
+| `merge_method` | string | no | Set the merge method used |
| `lfs_enabled` | boolean | no | Enable LFS |
| `request_access_enabled` | boolean | no | Allow users to request member access |
| `tag_list` | array | no | The list of tags for a project; put array of tags, that should be finally assigned to a project |
@@ -724,6 +747,7 @@ Example responses:
"only_allow_merge_if_pipeline_succeeds": false,
"only_allow_merge_if_all_discussions_are_resolved": false,
"request_access_enabled": false,
+ "merge_method": "merge",
"_links": {
"self": "http://example.com/api/v4/projects",
"issues": "http://example.com/api/v4/projects/1/issues",
@@ -801,6 +825,7 @@ Example response:
"only_allow_merge_if_pipeline_succeeds": false,
"only_allow_merge_if_all_discussions_are_resolved": false,
"request_access_enabled": false,
+ "merge_method": "merge",
"_links": {
"self": "http://example.com/api/v4/projects",
"issues": "http://example.com/api/v4/projects/1/issues",
@@ -877,6 +902,7 @@ Example response:
"only_allow_merge_if_pipeline_succeeds": false,
"only_allow_merge_if_all_discussions_are_resolved": false,
"request_access_enabled": false,
+ "merge_method": "merge",
"_links": {
"self": "http://example.com/api/v4/projects",
"issues": "http://example.com/api/v4/projects/1/issues",
@@ -971,6 +997,7 @@ Example response:
"only_allow_merge_if_pipeline_succeeds": false,
"only_allow_merge_if_all_discussions_are_resolved": false,
"request_access_enabled": false,
+ "merge_method": "merge",
"_links": {
"self": "http://example.com/api/v4/projects",
"issues": "http://example.com/api/v4/projects/1/issues",
@@ -1065,6 +1092,7 @@ Example response:
"only_allow_merge_if_pipeline_succeeds": false,
"only_allow_merge_if_all_discussions_are_resolved": false,
"request_access_enabled": false,
+ "merge_method": "merge",
"_links": {
"self": "http://example.com/api/v4/projects",
"issues": "http://example.com/api/v4/projects/1/issues",
diff --git a/lib/api/entities.rb b/lib/api/entities.rb
index b7a390696c7..e5ecd37e473 100644
--- a/lib/api/entities.rb
+++ b/lib/api/entities.rb
@@ -206,6 +206,7 @@ module API
expose :request_access_enabled
expose :only_allow_merge_if_all_discussions_are_resolved
expose :printing_merge_request_link_enabled
+ expose :merge_method
expose :statistics, using: 'API::Entities::ProjectStatistics', if: :statistics
diff --git a/lib/api/projects.rb b/lib/api/projects.rb
index 467bc78dad8..3d5b3c5a535 100644
--- a/lib/api/projects.rb
+++ b/lib/api/projects.rb
@@ -28,6 +28,7 @@ module API
optional :tag_list, type: Array[String], desc: 'The list of tags for a project'
optional :avatar, type: File, desc: 'Avatar image for project'
optional :printing_merge_request_link_enabled, type: Boolean, desc: 'Show link to create/view merge request when pushing from the command line'
+ optional :merge_method, type: String, values: %w(ff rebase_merge merge), desc: 'The merge method used when merging merge requests'
end
params :optional_params do
@@ -274,6 +275,7 @@ module API
:issues_enabled,
:lfs_enabled,
:merge_requests_enabled,
+ :merge_method,
:name,
:only_allow_merge_if_all_discussions_are_resolved,
:only_allow_merge_if_pipeline_succeeds,
diff --git a/spec/requests/api/projects_spec.rb b/spec/requests/api/projects_spec.rb
index d73a42f48ad..2ec29a79e93 100644
--- a/spec/requests/api/projects_spec.rb
+++ b/spec/requests/api/projects_spec.rb
@@ -452,7 +452,8 @@ describe API::Projects do
only_allow_merge_if_pipeline_succeeds: false,
request_access_enabled: true,
only_allow_merge_if_all_discussions_are_resolved: false,
- ci_config_path: 'a/custom/path'
+ ci_config_path: 'a/custom/path',
+ merge_method: 'ff'
})
post api('/projects', user), project
@@ -569,6 +570,22 @@ describe API::Projects do
expect(json_response['only_allow_merge_if_all_discussions_are_resolved']).to be_truthy
end
+ it 'sets the merge method of a project to rebase merge' do
+ project = attributes_for(:project, merge_method: 'rebase_merge')
+
+ post api('/projects', user), project
+
+ expect(json_response['merge_method']).to eq('rebase_merge')
+ end
+
+ it 'rejects invalid values for merge_method' do
+ project = attributes_for(:project, merge_method: 'totally_not_valid_method')
+
+ post api('/projects', user), project
+
+ expect(response).to have_gitlab_http_status(400)
+ end
+
it 'ignores import_url when it is nil' do
project = attributes_for(:project, import_url: nil)
@@ -823,6 +840,7 @@ describe API::Projects do
expect(json_response['shared_with_groups'][0]['group_access_level']).to eq(link.group_access)
expect(json_response['only_allow_merge_if_pipeline_succeeds']).to eq(project.only_allow_merge_if_pipeline_succeeds)
expect(json_response['only_allow_merge_if_all_discussions_are_resolved']).to eq(project.only_allow_merge_if_all_discussions_are_resolved)
+ expect(json_response['merge_method']).to eq(project.merge_method.to_s)
end
it 'returns a project by path name' do
@@ -1474,6 +1492,26 @@ describe API::Projects do
expect(json_response[k.to_s]).to eq(v)
end
end
+
+ it 'updates merge_method' do
+ project_param = { merge_method: 'ff' }
+
+ put api("/projects/#{project3.id}", user), project_param
+
+ expect(response).to have_gitlab_http_status(200)
+
+ project_param.each_pair do |k, v|
+ expect(json_response[k.to_s]).to eq(v)
+ end
+ end
+
+ it 'rejects to update merge_method when merge_method is invalid' do
+ project_param = { merge_method: 'invalid' }
+
+ put api("/projects/#{project3.id}", user), project_param
+
+ expect(response).to have_gitlab_http_status(400)
+ end
end
context 'when authenticated as project master' do
@@ -1491,6 +1529,7 @@ describe API::Projects do
wiki_enabled: true,
snippets_enabled: true,
merge_requests_enabled: true,
+ merge_method: 'ff',
description: 'new description' }
put api("/projects/#{project3.id}", user4), project_param