Refresh authorizations when transferring projects
This ensures that project authorizations are refreshed when moving a project from one namespace to another. When doing so the permissions for all users of both the old and new namespaces are refreshed. See #26194 for more information.
This commit is contained in:
parent
99fceff4f9
commit
ebae38394d
7 changed files with 75 additions and 3 deletions
|
@ -197,7 +197,12 @@ class Group < Namespace
|
|||
end
|
||||
|
||||
def refresh_members_authorized_projects
|
||||
UserProjectAccessChangedService.new(users_with_parents.pluck(:id)).execute
|
||||
UserProjectAccessChangedService.new(user_ids_for_project_authorizations).
|
||||
execute
|
||||
end
|
||||
|
||||
def user_ids_for_project_authorizations
|
||||
users_with_parents.pluck(:id)
|
||||
end
|
||||
|
||||
def members_with_parents
|
||||
|
|
|
@ -213,6 +213,10 @@ class Namespace < ActiveRecord::Base
|
|||
self.class.joins(:route).where('routes.path LIKE ?', "#{route.path}/%").reorder('routes.path ASC')
|
||||
end
|
||||
|
||||
def user_ids_for_project_authorizations
|
||||
[owner_id]
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def repository_storage_paths
|
||||
|
|
|
@ -25,9 +25,10 @@ module Projects
|
|||
end
|
||||
|
||||
def transfer(project, new_namespace)
|
||||
old_namespace = project.namespace
|
||||
|
||||
Project.transaction do
|
||||
old_path = project.path_with_namespace
|
||||
old_namespace = project.namespace
|
||||
old_group = project.group
|
||||
new_path = File.join(new_namespace.try(:path) || '', project.path)
|
||||
|
||||
|
@ -70,8 +71,11 @@ module Projects
|
|||
project.old_path_with_namespace = old_path
|
||||
|
||||
SystemHooksService.new.execute_hooks_for(project, :transfer)
|
||||
true
|
||||
end
|
||||
|
||||
refresh_permissions(old_namespace, new_namespace)
|
||||
|
||||
true
|
||||
end
|
||||
|
||||
def allowed_transfer?(current_user, project, namespace)
|
||||
|
@ -80,5 +84,14 @@ module Projects
|
|||
namespace.id != project.namespace_id &&
|
||||
current_user.can?(:create_projects, namespace)
|
||||
end
|
||||
|
||||
def refresh_permissions(old_namespace, new_namespace)
|
||||
# This ensures we only schedule 1 job for every user that has access to
|
||||
# the namespaces.
|
||||
user_ids = old_namespace.user_ids_for_project_authorizations |
|
||||
new_namespace.user_ids_for_project_authorizations
|
||||
|
||||
UserProjectAccessChangedService.new(user_ids).execute
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
---
|
||||
title: Refresh authorizations when transferring projects
|
||||
merge_request:
|
||||
author:
|
|
@ -300,4 +300,17 @@ describe Group, models: true do
|
|||
expect(group.members_with_parents).to include(master)
|
||||
end
|
||||
end
|
||||
|
||||
describe '#user_ids_for_project_authorizations' do
|
||||
it 'returns the user IDs for which to refresh authorizations' do
|
||||
master = create(:user)
|
||||
developer = create(:user)
|
||||
|
||||
group.add_user(master, GroupMember::MASTER)
|
||||
group.add_user(developer, GroupMember::DEVELOPER)
|
||||
|
||||
expect(group.user_ids_for_project_authorizations).
|
||||
to include(master.id, developer.id)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -218,4 +218,11 @@ describe Namespace, models: true do
|
|||
expect(group.descendants.to_a).to eq([nested_group, deep_nested_group, very_deep_nested_group])
|
||||
end
|
||||
end
|
||||
|
||||
describe '#user_ids_for_project_authorizations' do
|
||||
it 'returns the user IDs for which to refresh authorizations' do
|
||||
expect(namespace.user_ids_for_project_authorizations).
|
||||
to eq([namespace.owner_id])
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -83,4 +83,30 @@ describe Projects::TransferService, services: true do
|
|||
transfer_project(project, user, group)
|
||||
end
|
||||
end
|
||||
|
||||
describe 'refreshing project authorizations' do
|
||||
let(:group) { create(:group) }
|
||||
let(:owner) { project.namespace.owner }
|
||||
let(:group_member) { create(:user) }
|
||||
|
||||
before do
|
||||
group.add_user(owner, GroupMember::MASTER)
|
||||
group.add_user(group_member, GroupMember::DEVELOPER)
|
||||
end
|
||||
|
||||
it 'refreshes the permissions of the old and new namespace' do
|
||||
transfer_project(project, owner, group)
|
||||
|
||||
expect(group_member.authorized_projects).to include(project)
|
||||
expect(owner.authorized_projects).to include(project)
|
||||
end
|
||||
|
||||
it 'only schedules a single job for every user' do
|
||||
expect(UserProjectAccessChangedService).to receive(:new).
|
||||
with([owner.id, group_member.id]).
|
||||
and_call_original
|
||||
|
||||
transfer_project(project, owner, group)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
Loading…
Reference in a new issue