Commit 7da1a3d7 authored by Douwe Maan's avatar Douwe Maan

Merge branch 'api-refs-for-commit' into 'master'

API: Get refs for a particular commit

Closes #18014

See merge request gitlab-org/gitlab-ce!15026
parents c203c622 a724f7e3
---
title: 'API: Get references a commit is pushed to'
merge_request: 15026
author: Robert Schilling
type: added
...@@ -198,6 +198,41 @@ Example response: ...@@ -198,6 +198,41 @@ Example response:
} }
``` ```
## Get references a commit is pushed to
> [Introduced][ce-15026] in GitLab 10.6
Get all references (from branches or tags) a commit is pushed to.
The pagination parameters `page` and `per_page` can be used to restrict the list of references.
```
GET /projects/:id/repository/commits/:sha/refs
```
Parameters:
| Attribute | Type | Required | Description |
| --------- | ---- | -------- | ----------- |
| `id` | integer/string | yes | The ID or [URL-encoded path of the project](README.md#namespaced-path-encoding) owned by the authenticated user
| `sha` | string | yes | The commit hash |
| `type` | string | no | The scope of commits. Possible values `branch`, `tag`, `all`. Default is `all`. |
```bash
curl --header "PRIVATE-TOKEN: 9koXpg98eAheJpvBs5tK" "https://gitlab.example.com/api/v4/projects/5/repository/commits/5937ac0a7beb003549fc5fd26fc247adbce4a52e/refs?type=all"
```
Example response:
```json
[
{"type": "branch", "name": "'test'"},
{"type": "branch", "name": "add-balsamiq-file"},
{"type": "branch", "name": "wip"},
{"type": "tag", "name": "v1.1.0"}
]
```
## Cherry pick a commit ## Cherry pick a commit
> [Introduced][ce-8047] in GitLab 8.15. > [Introduced][ce-8047] in GitLab 8.15.
...@@ -500,3 +535,4 @@ Example response: ...@@ -500,3 +535,4 @@ Example response:
[ce-6096]: https://gitlab.com/gitlab-org/gitlab-ce/merge_requests/6096 "Multi-file commit" [ce-6096]: https://gitlab.com/gitlab-org/gitlab-ce/merge_requests/6096 "Multi-file commit"
[ce-8047]: https://gitlab.com/gitlab-org/gitlab-ce/merge_requests/8047 [ce-8047]: https://gitlab.com/gitlab-org/gitlab-ce/merge_requests/8047
[ce-15026]: https://gitlab.com/gitlab-org/gitlab-ce/merge_requests/15026
...@@ -156,6 +156,27 @@ module API ...@@ -156,6 +156,27 @@ module API
end end
end end
desc 'Get all references a commit is pushed to' do
detail 'This feature was introduced in GitLab 10.6'
success Entities::BasicRef
end
params do
requires :sha, type: String, desc: 'A commit sha'
optional :type, type: String, values: %w[branch tag all], default: 'all', desc: 'Scope'
use :pagination
end
get ':id/repository/commits/:sha/refs', requirements: API::COMMIT_ENDPOINT_REQUIREMENTS do
commit = user_project.commit(params[:sha])
not_found!('Commit') unless commit
refs = []
refs.concat(user_project.repository.branch_names_contains(commit.id).map {|name| { type: 'branch', name: name }}) unless params[:type] == 'tag'
refs.concat(user_project.repository.tag_names_contains(commit.id).map {|name| { type: 'tag', name: name }}) unless params[:type] == 'branch'
refs = Kaminari.paginate_array(refs)
present paginate(refs), with: Entities::BasicRef
end
desc 'Post comment to commit' do desc 'Post comment to commit' do
success Entities::CommitNote success Entities::CommitNote
end end
...@@ -165,7 +186,7 @@ module API ...@@ -165,7 +186,7 @@ module API
optional :path, type: String, desc: 'The file path' optional :path, type: String, desc: 'The file path'
given :path do given :path do
requires :line, type: Integer, desc: 'The line number' requires :line, type: Integer, desc: 'The line number'
requires :line_type, type: String, values: %w(new old), default: 'new', desc: 'The type of the line' requires :line_type, type: String, values: %w[new old], default: 'new', desc: 'The type of the line'
end end
end end
post ':id/repository/commits/:sha/comments', requirements: API::COMMIT_ENDPOINT_REQUIREMENTS do post ':id/repository/commits/:sha/comments', requirements: API::COMMIT_ENDPOINT_REQUIREMENTS do
......
...@@ -276,6 +276,10 @@ module API ...@@ -276,6 +276,10 @@ module API
expose :last_pipeline, using: 'API::Entities::PipelineBasic' expose :last_pipeline, using: 'API::Entities::PipelineBasic'
end end
class BasicRef < Grape::Entity
expose :type, :name
end
class Branch < Grape::Entity class Branch < Grape::Entity
expose :name expose :name
......
...@@ -465,6 +465,72 @@ describe API::Commits do ...@@ -465,6 +465,72 @@ describe API::Commits do
end end
end end
describe 'GET /projects/:id/repository/commits/:sha/refs' do
let(:project) { create(:project, :public, :repository) }
let(:tag) { project.repository.find_tag('v1.1.0') }
let(:commit_id) { tag.dereferenced_target.id }
let(:route) { "/projects/#{project_id}/repository/commits/#{commit_id}/refs" }
context 'when ref does not exist' do
let(:commit_id) { 'unknown' }
it_behaves_like '404 response' do
let(:request) { get api(route, current_user) }
let(:message) { '404 Commit Not Found' }
end
end
context 'when repository is disabled' do
include_context 'disabled repository'
it_behaves_like '403 response' do
let(:request) { get api(route, current_user) }
end
end
context 'for a valid commit' do
it 'returns all refs with no scope' do
get api(route, current_user), per_page: 100
refs = project.repository.branch_names_contains(commit_id).map {|name| ['branch', name]}
refs.concat(project.repository.tag_names_contains(commit_id).map {|name| ['tag', name]})
expect(response).to have_gitlab_http_status(200)
expect(response).to include_pagination_headers
expect(json_response).to be_an Array
expect(json_response.map { |r| [r['type'], r['name']] }.compact).to eq(refs)
end
it 'returns all refs' do
get api(route, current_user), type: 'all', per_page: 100
refs = project.repository.branch_names_contains(commit_id).map {|name| ['branch', name]}
refs.concat(project.repository.tag_names_contains(commit_id).map {|name| ['tag', name]})
expect(response).to have_gitlab_http_status(200)
expect(json_response.map { |r| [r['type'], r['name']] }.compact).to eq(refs)
end
it 'returns the branch refs' do
get api(route, current_user), type: 'branch', per_page: 100
refs = project.repository.branch_names_contains(commit_id).map {|name| ['branch', name]}
expect(response).to have_gitlab_http_status(200)
expect(json_response.map { |r| [r['type'], r['name']] }.compact).to eq(refs)
end
it 'returns the tag refs' do
get api(route, current_user), type: 'tag', per_page: 100
refs = project.repository.tag_names_contains(commit_id).map {|name| ['tag', name]}
expect(response).to have_gitlab_http_status(200)
expect(json_response.map { |r| [r['type'], r['name']] }.compact).to eq(refs)
end
end
end
describe 'GET /projects/:id/repository/commits/:sha' do describe 'GET /projects/:id/repository/commits/:sha' do
let(:commit) { project.repository.commit } let(:commit) { project.repository.commit }
let(:commit_id) { commit.id } let(:commit_id) { commit.id }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment