Commit ff896803 authored by J.D. Bean's avatar J.D. Bean Committed by Nick Thomas

Feature/add license to project API

parent 83e898a5
---
title: Add license data to projects endpoint
merge_request: 21606
author: J.D. Bean (@jdbean)
type: added
...@@ -451,6 +451,7 @@ GET /projects/:id ...@@ -451,6 +451,7 @@ GET /projects/:id
| --------- | ---- | -------- | ----------- | | --------- | ---- | -------- | ----------- |
| `id` | integer/string | yes | The ID or [URL-encoded path of the project](README.md#namespaced-path-encoding) | | `id` | integer/string | yes | The ID or [URL-encoded path of the project](README.md#namespaced-path-encoding) |
| `statistics` | boolean | no | Include project statistics | | `statistics` | boolean | no | Include project statistics |
| `license` | boolean | no | Include project license data |
| `with_custom_attributes` | boolean | no | Include [custom attributes](custom_attributes.md) in response (admins only) | | `with_custom_attributes` | boolean | no | Include [custom attributes](custom_attributes.md) in response (admins only) |
```json ```json
...@@ -508,6 +509,14 @@ GET /projects/:id ...@@ -508,6 +509,14 @@ GET /projects/:id
}, },
"archived": false, "archived": false,
"avatar_url": "http://example.com/uploads/project/avatar/3/uploads/avatar.png", "avatar_url": "http://example.com/uploads/project/avatar/3/uploads/avatar.png",
"license_url": "http://example.com/diaspora/diaspora-client/blob/master/LICENSE",
"license": {
"key": "lgpl-3.0",
"name": "GNU Lesser General Public License v3.0",
"nickname": "GNU LGPLv3",
"html_url": "http://choosealicense.com/licenses/lgpl-3.0/",
"source_url": "http://www.gnu.org/licenses/lgpl-3.0.txt"
},
"shared_runners_enabled": true, "shared_runners_enabled": true,
"forks_count": 0, "forks_count": 0,
"star_count": 0, "star_count": 0,
...@@ -572,6 +581,14 @@ If the project is a fork, and you provide a valid token to authenticate, the ...@@ -572,6 +581,14 @@ If the project is a fork, and you provide a valid token to authenticate, the
"http_url_to_repo":"https://gitlab.com/gitlab-org/gitlab-ce.git", "http_url_to_repo":"https://gitlab.com/gitlab-org/gitlab-ce.git",
"web_url":"https://gitlab.com/gitlab-org/gitlab-ce", "web_url":"https://gitlab.com/gitlab-org/gitlab-ce",
"avatar_url":"https://assets.gitlab-static.net/uploads/-/system/project/avatar/13083/logo-extra-whitespace.png", "avatar_url":"https://assets.gitlab-static.net/uploads/-/system/project/avatar/13083/logo-extra-whitespace.png",
"license_url": "https://gitlab.com/gitlab-org/gitlab-ce/blob/master/LICENSE",
"license": {
"key": "mit",
"name": "MIT License",
"nickname": null,
"html_url": "http://choosealicense.com/licenses/mit/",
"source_url": "https://opensource.org/licenses/MIT",
},
"star_count":3812, "star_count":3812,
"forks_count":3561, "forks_count":3561,
"last_activity_at":"2018-01-02T11:40:26.570Z", "last_activity_at":"2018-01-02T11:40:26.570Z",
...@@ -905,6 +922,14 @@ Example response: ...@@ -905,6 +922,14 @@ Example response:
"import_status": "none", "import_status": "none",
"archived": true, "archived": true,
"avatar_url": "http://example.com/uploads/project/avatar/3/uploads/avatar.png", "avatar_url": "http://example.com/uploads/project/avatar/3/uploads/avatar.png",
"license_url": "http://example.com/diaspora/diaspora-client/blob/master/LICENSE",
"license": {
"key": "lgpl-3.0",
"name": "GNU Lesser General Public License v3.0",
"nickname": "GNU LGPLv3",
"html_url": "http://choosealicense.com/licenses/lgpl-3.0/",
"source_url": "http://www.gnu.org/licenses/lgpl-3.0.txt"
},
"shared_runners_enabled": true, "shared_runners_enabled": true,
"forks_count": 0, "forks_count": 0,
"star_count": 1, "star_count": 1,
...@@ -983,6 +1008,14 @@ Example response: ...@@ -983,6 +1008,14 @@ Example response:
"import_status": "none", "import_status": "none",
"archived": true, "archived": true,
"avatar_url": "http://example.com/uploads/project/avatar/3/uploads/avatar.png", "avatar_url": "http://example.com/uploads/project/avatar/3/uploads/avatar.png",
"license_url": "http://example.com/diaspora/diaspora-client/blob/master/LICENSE",
"license": {
"key": "lgpl-3.0",
"name": "GNU Lesser General Public License v3.0",
"nickname": "GNU LGPLv3",
"html_url": "http://choosealicense.com/licenses/lgpl-3.0/",
"source_url": "http://www.gnu.org/licenses/lgpl-3.0.txt"
},
"shared_runners_enabled": true, "shared_runners_enabled": true,
"forks_count": 0, "forks_count": 0,
"star_count": 0, "star_count": 0,
...@@ -1101,6 +1134,14 @@ Example response: ...@@ -1101,6 +1134,14 @@ Example response:
}, },
"archived": true, "archived": true,
"avatar_url": "http://example.com/uploads/project/avatar/3/uploads/avatar.png", "avatar_url": "http://example.com/uploads/project/avatar/3/uploads/avatar.png",
"license_url": "http://example.com/diaspora/diaspora-client/blob/master/LICENSE",
"license": {
"key": "lgpl-3.0",
"name": "GNU Lesser General Public License v3.0",
"nickname": "GNU LGPLv3",
"html_url": "http://choosealicense.com/licenses/lgpl-3.0/",
"source_url": "http://www.gnu.org/licenses/lgpl-3.0.txt"
},
"shared_runners_enabled": true, "shared_runners_enabled": true,
"forks_count": 0, "forks_count": 0,
"star_count": 0, "star_count": 0,
...@@ -1197,6 +1238,14 @@ Example response: ...@@ -1197,6 +1238,14 @@ Example response:
}, },
"archived": false, "archived": false,
"avatar_url": "http://example.com/uploads/project/avatar/3/uploads/avatar.png", "avatar_url": "http://example.com/uploads/project/avatar/3/uploads/avatar.png",
"license_url": "http://example.com/diaspora/diaspora-client/blob/master/LICENSE",
"license": {
"key": "lgpl-3.0",
"name": "GNU Lesser General Public License v3.0",
"nickname": "GNU LGPLv3",
"html_url": "http://choosealicense.com/licenses/lgpl-3.0/",
"source_url": "http://www.gnu.org/licenses/lgpl-3.0.txt"
},
"shared_runners_enabled": true, "shared_runners_enabled": true,
"forks_count": 0, "forks_count": 0,
"star_count": 0, "star_count": 0,
......
...@@ -160,13 +160,27 @@ module API ...@@ -160,13 +160,27 @@ module API
# (fixed in https://github.com/rails/rails/pull/25976). # (fixed in https://github.com/rails/rails/pull/25976).
project.tags.map(&:name).sort project.tags.map(&:name).sort
end end
expose :ssh_url_to_repo, :http_url_to_repo, :web_url, :readme_url expose :ssh_url_to_repo, :http_url_to_repo, :web_url, :readme_url
expose :license_url, if: :license do |project|
license = project.repository.license_blob
if license
Gitlab::Routing.url_helpers.project_blob_url(project, File.join(project.default_branch, license.path))
end
end
expose :license, with: 'API::Entities::LicenseBasic', if: :license do |project|
project.repository.license
end
expose :avatar_url do |project, options| expose :avatar_url do |project, options|
project.avatar_url(only_path: false) project.avatar_url(only_path: false)
end end
expose :star_count, :forks_count expose :star_count, :forks_count
expose :last_activity_at expose :last_activity_at
expose :namespace, using: 'API::Entities::NamespaceBasic' expose :namespace, using: 'API::Entities::NamespaceBasic'
expose :custom_attributes, using: 'API::Entities::CustomAttribute', if: :with_custom_attributes expose :custom_attributes, using: 'API::Entities::CustomAttribute', if: :with_custom_attributes
...@@ -1208,11 +1222,14 @@ module API ...@@ -1208,11 +1222,14 @@ module API
expose :deployable, using: Entities::Job expose :deployable, using: Entities::Job
end end
class License < Grape::Entity class LicenseBasic < Grape::Entity
expose :key, :name, :nickname expose :key, :name, :nickname
expose :popular?, as: :popular
expose :url, as: :html_url expose :url, as: :html_url
expose(:source_url) { |license| license.meta['source'] } expose(:source_url) { |license| license.meta['source'] }
end
class License < LicenseBasic
expose :popular?, as: :popular
expose(:description) { |license| license.meta['description'] } expose(:description) { |license| license.meta['description'] }
expose(:conditions) { |license| license.meta['conditions'] } expose(:conditions) { |license| license.meta['conditions'] }
expose(:permissions) { |license| license.meta['permissions'] } expose(:permissions) { |license| license.meta['permissions'] }
......
...@@ -114,7 +114,8 @@ module API ...@@ -114,7 +114,8 @@ module API
options = options.reverse_merge( options = options.reverse_merge(
with: current_user ? Entities::ProjectWithAccess : Entities::BasicProjectDetails, with: current_user ? Entities::ProjectWithAccess : Entities::BasicProjectDetails,
statistics: params[:statistics], statistics: params[:statistics],
current_user: current_user current_user: current_user,
license: false
) )
options[:with] = Entities::BasicProjectDetails if params[:simple] options[:with] = Entities::BasicProjectDetails if params[:simple]
...@@ -230,13 +231,17 @@ module API ...@@ -230,13 +231,17 @@ module API
params do params do
use :statistics_params use :statistics_params
use :with_custom_attributes use :with_custom_attributes
optional :license, type: Boolean, default: false,
desc: 'Include project license data'
end end
get ":id" do get ":id" do
options = { options = {
with: current_user ? Entities::ProjectWithAccess : Entities::BasicProjectDetails, with: current_user ? Entities::ProjectWithAccess : Entities::BasicProjectDetails,
current_user: current_user, current_user: current_user,
user_can_admin_project: can?(current_user, :admin_project, user_project), user_can_admin_project: can?(current_user, :admin_project, user_project),
statistics: params[:statistics] statistics: params[:statistics],
license: params[:license]
} }
project, options = with_custom_attributes(user_project, options) project, options = with_custom_attributes(user_project, options)
......
...@@ -200,6 +200,24 @@ describe API::Projects do ...@@ -200,6 +200,24 @@ describe API::Projects do
expect(json_response.first).to include 'statistics' expect(json_response.first).to include 'statistics'
end end
it "does not include license by default" do
get api('/projects', user)
expect(response).to have_gitlab_http_status(200)
expect(response).to include_pagination_headers
expect(json_response).to be_an Array
expect(json_response.first).not_to include('license', 'license_url')
end
it "does not include license if requested" do
get api('/projects', user), license: true
expect(response).to have_gitlab_http_status(200)
expect(response).to include_pagination_headers
expect(json_response).to be_an Array
expect(json_response.first).not_to include('license', 'license_url')
end
context 'when external issue tracker is enabled' do context 'when external issue tracker is enabled' do
let!(:jira_service) { create(:jira_service, project: project) } let!(:jira_service) { create(:jira_service, project: project) }
...@@ -994,6 +1012,26 @@ describe API::Projects do ...@@ -994,6 +1012,26 @@ describe API::Projects do
}) })
end end
it "does not include license fields by default" do
get api("/projects/#{project.id}", user)
expect(response).to have_gitlab_http_status(200)
expect(json_response).not_to include('license', 'license_url')
end
it 'includes license fields when requested' do
get api("/projects/#{project.id}", user), license: true
expect(response).to have_gitlab_http_status(200)
expect(json_response['license']).to eq({
'key' => project.repository.license.key,
'name' => project.repository.license.name,
'nickname' => project.repository.license.nickname,
'html_url' => project.repository.license.url,
'source_url' => project.repository.license.meta['source']
})
end
it "does not include statistics by default" do it "does not include statistics by default" do
get api("/projects/#{project.id}", user) get api("/projects/#{project.id}", user)
......
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