Commit 8fb0db69 authored by Michael Kozono's avatar Michael Kozono

Merge branch...

Merge branch '7225-no-audit-event-for-adding-a-user-to-a-group-or-project-through-api' into 'master'

Add audit events to the adding members to project or group API endpoint

Closes #7225

See merge request gitlab-org/gitlab!21633
parents 6bd64158 7b8b39cf
---
title: Add audit events to the adding members to project or group API endpoint
merge_request: 21633
author:
type: changed
...@@ -32,6 +32,25 @@ module EE ...@@ -32,6 +32,25 @@ module EE
def can_view_group_identity?(members_source) def can_view_group_identity?(members_source)
can?(current_user, :read_group_saml_identity, members_source) can?(current_user, :read_group_saml_identity, members_source)
end end
override :create_member
def create_member(current_user, user, source, params)
member = source.add_user(user, params[:access_level], current_user: current_user, expires_at: params[:expires_at])
return false unless member
log_audit_event(member) if member.persisted? && member.valid?
member
end
def log_audit_event(member)
::AuditEventService.new(
current_user,
member.source,
action: :create
).for_member(member).security_event
end
end end
end end
end end
......
# frozen_string_literal: true
require 'spec_helper'
describe EE::API::Helpers::MembersHelpers do
subject(:members_helpers) { Class.new.include(described_class).new }
before do
allow(members_helpers).to receive(:current_user).and_return(create(:user))
end
shared_examples 'creates security_event' do |source_type|
context "with :source_type == #{source_type.pluralize}" do
it 'creates security_event' do
security_event = subject.log_audit_event(member)
expect(security_event.entity_id).to eq(source.id)
expect(security_event.entity_type).to eq(source_type.capitalize)
expect(security_event.details.fetch(:target_id)).to eq(member.id)
end
end
end
describe '#log_audit_event' do
it_behaves_like 'creates security_event', 'group' do
let(:source) { create(:group) }
let(:member) { create(:group_member, :owner, group: source, user: create(:user)) }
end
it_behaves_like 'creates security_event', 'project' do
let(:source) { create(:project) }
let(:member) { create(:project_member, project: source, user: create(:user)) }
end
end
end
...@@ -5,6 +5,7 @@ require 'spec_helper' ...@@ -5,6 +5,7 @@ require 'spec_helper'
describe API::Members do describe API::Members do
let(:group) { create(:group) } let(:group) { create(:group) }
let(:owner) { create(:user) } let(:owner) { create(:user) }
let(:project) { create(:project, group: group) }
before do before do
group.add_owner(owner) group.add_owner(owner)
...@@ -74,4 +75,39 @@ describe API::Members do ...@@ -74,4 +75,39 @@ describe API::Members do
end end
end end
end end
shared_examples 'POST /:source_type/:id/members' do |source_type|
let(:stranger) { create(:user) }
let(:url) { "/#{source_type.pluralize}/#{source.id}/members" }
context "with :source_type == #{source_type.pluralize}" do
it 'creates an audit event while creating a new member' do
params = { user_id: stranger.id, access_level: Member::DEVELOPER }
expect do
post api(url, owner), params: params
expect(response).to have_gitlab_http_status(201)
end.to change { AuditEvent.count }.by(1)
end
it 'does not create audit event if creating a new member fails' do
params = { user_id: 0, access_level: Member::DEVELOPER }
expect do
post api(url, owner), params: params
expect(response).to have_gitlab_http_status(404)
end.not_to change { AuditEvent.count }
end
end
end
it_behaves_like 'POST /:source_type/:id/members', 'project' do
let(:source) { project }
end
it_behaves_like 'POST /:source_type/:id/members', 'group' do
let(:source) { group }
end
end end
...@@ -41,6 +41,10 @@ module API ...@@ -41,6 +41,10 @@ module API
GroupMembersFinder.new(group).execute GroupMembersFinder.new(group).execute
end end
def create_member(current_user, user, source, params)
source.add_user(user, params[:access_level], current_user: current_user, expires_at: params[:expires_at])
end
def present_members(members) def present_members(members)
present members, with: Entities::Member, current_user: current_user present members, with: Entities::Member, current_user: current_user
end end
......
...@@ -101,12 +101,12 @@ module API ...@@ -101,12 +101,12 @@ module API
user = User.find_by_id(params[:user_id]) user = User.find_by_id(params[:user_id])
not_found!('User') unless user not_found!('User') unless user
member = source.add_user(user, params[:access_level], current_user: current_user, expires_at: params[:expires_at]) member = create_member(current_user, user, source, params)
if !member if !member
not_allowed! # This currently can only be reached in EE not_allowed! # This currently can only be reached in EE
elsif member.persisted? && member.valid? elsif member.persisted? && member.valid?
present_members member present_members(member)
else else
render_validation_error!(member) render_validation_error!(member)
end end
......
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