Commit f1dd55e8 authored by Nick Thomas's avatar Nick Thomas

Merge branch '199065-on-demand-evidence-creation' into 'master'

Support On Demand Release Evidence

See merge request gitlab-org/gitlab!26591
parents d0df4853 342fd93a
---
title: On-demand Evidence creation
merge_request: 26591
author:
type: added
...@@ -6,6 +6,26 @@ module EE ...@@ -6,6 +6,26 @@ module EE
extend ActiveSupport::Concern extend ActiveSupport::Concern
prepended do prepended do
resource :projects, requirements: ::API::API::NAMESPACE_OR_PROJECT_REQUIREMENTS do
desc 'Create Evidence for a Release' do
detail 'This feature was introduced in GitLab 12.10.'
success Entities::Release
end
params do
requires :tag_name, type: String, desc: 'The name of the tag', as: :tag
end
post ':id/releases/:tag_name/evidence', requirements: ::API::Releases::RELEASE_ENDPOINT_REQUIREMENTS do
authorize_create_evidence!
if release.present?
CreateEvidenceWorker.perform_async(release.id)
status :accepted
else
status :not_found
end
end
end
helpers do helpers do
extend ::Gitlab::Utils::Override extend ::Gitlab::Utils::Override
...@@ -38,6 +58,11 @@ module EE ...@@ -38,6 +58,11 @@ module EE
release release
).security_event ).security_event
end end
override :authorize_create_evidence!
def authorize_create_evidence!
authorize_create_release!
end
end end
end end
end end
......
...@@ -6,13 +6,16 @@ describe API::Releases do ...@@ -6,13 +6,16 @@ describe API::Releases do
let(:project) { create(:project, :repository, :private) } let(:project) { create(:project, :repository, :private) }
let(:maintainer) { create(:user) } let(:maintainer) { create(:user) }
let(:reporter) { create(:user) } let(:reporter) { create(:user) }
let(:developer) { create(:user) }
let(:guest) { create(:user) } let(:guest) { create(:user) }
let(:non_project_member) { create(:user) }
let(:commit) { create(:commit, project: project) } let(:commit) { create(:commit, project: project) }
before do before do
project.add_maintainer(maintainer) project.add_maintainer(maintainer)
project.add_reporter(reporter) project.add_reporter(reporter)
project.add_guest(guest) project.add_guest(guest)
project.add_developer(developer)
project.repository.add_tag(maintainer, 'v0.1', commit.id) project.repository.add_tag(maintainer, 'v0.1', commit.id)
project.repository.add_tag(maintainer, 'v0.2', commit.id) project.repository.add_tag(maintainer, 'v0.2', commit.id)
...@@ -150,4 +153,71 @@ describe API::Releases do ...@@ -150,4 +153,71 @@ describe API::Releases do
end end
end end
end end
describe 'POST /projects/:id/releases/:tag_name/evidence' do
let(:tag_name) { 'v0.1' }
let!(:release) do
create(:release,
project: project,
tag: 'v0.1',
name: 'New release',
description: 'Super nice release')
end
it 'accepts the request' do
post api("/projects/#{project.id}/releases/#{tag_name}/evidence", maintainer)
expect(response).to have_gitlab_http_status(:accepted)
end
it 'creates the Evidence', :sidekiq_inline do
expect do
post api("/projects/#{project.id}/releases/#{tag_name}/evidence", maintainer)
end.to change { Releases::Evidence.count }.by(1)
end
context 'when tag_name is invalid' do
let(:tag_name) { 'v9.5.0' }
it 'returns a 404' do
post api("/projects/#{project.id}/releases/#{tag_name}/evidence", maintainer)
expect(response).to have_gitlab_http_status(:not_found)
end
end
context 'when user is a reporter' do
it 'forbids the request' do
post api("/projects/#{project.id}/releases/#{tag_name}/evidence", reporter)
expect(response).to have_gitlab_http_status(:forbidden)
end
end
context 'when user is a developer' do
it 'accepts the request' do
post api("/projects/#{project.id}/releases/#{tag_name}/evidence", developer)
expect(response).to have_gitlab_http_status(:accepted)
end
end
context 'when user is not a project member' do
it 'forbids the request' do
post api("/projects/#{project.id}/releases/#{tag_name}/evidence", non_project_member)
expect(response).to have_gitlab_http_status(:not_found)
end
context 'when project is public' do
let(:project) { create(:project, :repository, :public) }
it 'forbids the request' do
post api("/projects/#{project.id}/releases/#{tag_name}/evidence", non_project_member)
expect(response).to have_gitlab_http_status(:forbidden)
end
end
end
end
end end
...@@ -150,6 +150,10 @@ module API ...@@ -150,6 +150,10 @@ module API
authorize! :download_code, release authorize! :download_code, release
end end
def authorize_create_evidence!
# This is a separate method so that EE can extend its behaviour
end
def release def release
@release ||= user_project.releases.find_by_tag(params[:tag]) @release ||= user_project.releases.find_by_tag(params[:tag])
end end
......
...@@ -6,6 +6,7 @@ describe API::Releases do ...@@ -6,6 +6,7 @@ describe API::Releases do
let(:project) { create(:project, :repository, :private) } let(:project) { create(:project, :repository, :private) }
let(:maintainer) { create(:user) } let(:maintainer) { create(:user) }
let(:reporter) { create(:user) } let(:reporter) { create(:user) }
let(:developer) { create(:user) }
let(:guest) { create(:user) } let(:guest) { create(:user) }
let(:non_project_member) { create(:user) } let(:non_project_member) { create(:user) }
let(:commit) { create(:commit, project: project) } let(:commit) { create(:commit, project: project) }
...@@ -15,6 +16,7 @@ describe API::Releases do ...@@ -15,6 +16,7 @@ describe API::Releases do
project.add_maintainer(maintainer) project.add_maintainer(maintainer)
project.add_reporter(reporter) project.add_reporter(reporter)
project.add_guest(guest) project.add_guest(guest)
project.add_developer(developer)
project.repository.add_tag(maintainer, 'v0.1', commit.id) project.repository.add_tag(maintainer, 'v0.1', commit.id)
project.repository.add_tag(maintainer, 'v0.2', commit.id) project.repository.add_tag(maintainer, 'v0.2', commit.id)
...@@ -248,6 +250,24 @@ describe API::Releases do ...@@ -248,6 +250,24 @@ describe API::Releases do
.to match_array(release.sources.map(&:url)) .to match_array(release.sources.map(&:url))
end end
context 'with evidence' do
let!(:evidence) { create(:evidence, release: release) }
it 'returns the evidence' do
get api("/projects/#{project.id}/releases/v0.1", maintainer)
expect(json_response['evidences'].count).to eq(1)
end
it '#collected_at' do
Timecop.freeze(Time.now.round) do
get api("/projects/#{project.id}/releases/v0.1", maintainer)
expect(json_response['evidences'].first['collected_at'].to_datetime.to_i).to be_within(1.minute).of(release.evidences.first.created_at.to_i)
end
end
end
context 'when release has link asset' do context 'when release has link asset' do
let!(:link) do let!(:link) do
create(:release_link, create(:release_link,
......
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